假设我有一个函数返回这样的函数:
function createGreeter(logger) {
return function greet(greeting) {
logger.log(greeting + ', ' + this.name);
}
}
和一个类
class Person {
constructor(name) {this.name = name;}
}
如果我想为使用控制台作为记录器的Person
类分配一个问候方法,我可以想到几种方法:
1.
class Person {
constructor(name) {this.name = name;}
greet(greeting) {
return createGreeter(console).call(this, greeting);
}
}
2.
class Person {
constructor(name) {this.name = name;}
}
Person.prototype.greet = createGreeter(console);
但是,我认为这两个都有些丑陋。1)创建一个简单地绑定this
并调用功能的不必要的包装器方法,以及2)在我看来会使类API较不清楚的班级主体外部修改原型。
是否没有更清晰/较短的语法来对外部功能与类方法的外部函数结合。我在想:
class Person {
constructor(name) {this.name = name;}
greet: createGreeter(console)
}
...类似于您如何在对象中分配一个函数。但这显然不起作用。有类似的东西(现在还是即将到来)?
另外,我想知道返回闭合的内存消耗和/或性能方面,如1)如果返回的功能很大。每当在Person
对象上调用招呼方法时,即使我们始终希望将相同的参数(console
)传递给它,也会创建一个新功能对象。因此,另一种方法可能是在类别定义之前声明const consoleGreeter = createGreeter(console)
并将其实现为return consoleGreeter.call(this, greeting)
,但是值得吗?
class Person {
constructor(name) {this.name = name;}
}
Person.prototype.greet = createGreeter(console);
是做到这一点的正确方法,除非还有其他问题(在打字稿中会出现问题)。
这也可以使用班级字段来完成,这是第三阶段提案,可能会降落在ES2018:
class Person {
greet = createGreeter(console);
}
这是
的快捷方式class Person {
constructor() {
this.greet = createGreeter(console);
}
}
第一个摘要一次评估createGreeter(console)
,然后将方法分配给类原型。第二片片段每次实例化并将方法分配给类实例时都会对其进行评估。
好的,所以这是bind
外部方法的替代品 class
class Person {
constructor(name) {this.name = name;}
get greet() { return createGreeter(console) }
}
刚刚检查,this
也工作正常。
这将达到相同的效果#1,因为每次访问方法时都会调用包装器。如果您可以提高可读性...
function createGreeter(logger) {
return function greet(greeting) {
logger.log(`${greeting}, ${this.name}`);
};
}
class Person {
constructor(name) {
this.name = name;
}
get greet() {
return createGreeter(console);
}
}
let person = new Person('Patrick');
person.greet('Hello');