如果您希望您的类支持事件,从EventEmitter继承似乎是一种常见做法。例如,Google在Puppeteer中这样做,WebSocket模块这样做,mongoose也是如此,只是其中之一。
但这真的是好的做法吗?我的意思是,它看起来很好,很干净,但从面向对象编程的角度来看,它似乎是错误的。例如:
const EventEmitter = require('events')
class Rectangle extends EventEmitter {
constructor(x,y,w,h) {
super()
this.position = {x:x, y:y}
this.dimensions = {w:w, h:h}
}
setDimensions(w,h) {
this.dimensions = {w:w, h:h}
this.emit('dimensionsChanged')
}
}
让它看起来好像Rectangle在其核心是一个EventEmitter,即使事件功能是次要的。
如果你决定
Rectangle
现在需要继承一个名为Shape
的新类,会怎样呢?class Shape {
constructor(x,y) {
this.position = {x:x, y:y}
}
}
class Rectangle extends Shape {
constructor(x,y,w,h) {
super(x,y)
this.dimensions = {w:w, h:h}
}
}
现在你需要让
Shape
继承自EventEmitter类。即使只有一个从Shape
继承的类实际上需要事件处理。这样做是否更加合理?
class Shape {
constructor(x,y) {
this.position = {x, y}
}
}
const EventEmitter = require('events')
class Rectangle extends Shape {
constructor(x,y,w,h) {
super(x,y)
this.dimensions = {w, h}
this.em = new EventEmitter()
}
setDimensions(w,h) {
this.dimensions = {w:w, h:h}
this.em.emit('dimensionsChanged')
}
}
const rectangle = new Rectangle(1,2,3,4)
rectangle.em.on('dimensionsChanged', ()=>{console.log('dimensions changed')})
rectangle.setDimensions(10,20)