typescript - 打字稿:一个类方法可以成为另一个方法的装饰器吗?
问题描述
可以像下面这样工作吗?
class A {
private mySecretNumber = 2;
decorate (f: (x :number) => number) {
return (x: number) => f(this.mySecretNumber * x);
}
@(this.decorate)
method (x: number) {
return x + 1;
}
}
我试过@this['decorate'],
@A['decorate']
, @A.decorate
,找不到任何东西。
这是我的用例示例:https ://kutt.it/uOxVgM 。理想情况下,我只会装饰getAbc()
和get123()
。
解决方案
你的问题有很多微妙之处。
第一件事是,是的,您确实可以将方法用作装饰器,但不能通过编写@this.decorate
(在转译期间,this
将是globalThis
代替A
)或@A.decorate
(decorate
不是静态方法,因此A.decorate
不存在)。这部分问题的正确答案是@A.prototype.decorate
;这将准确定位您的想法。
第二件事是,当将装饰器应用于类的方法时,装饰器的参数不是方法函数本身,而是它实际上有 3 个参数:一个目标对象(A.prototype
在我们的例子中),一个字符串 (方法的名称,"method"
在我们的例子中)和一个属性描述符对象。它也不会返回一个新函数,但如果不是 void,它应该返回一个新的属性描述符。所以在装饰器函数内部,你应该尝试修改目标对象,而不是尝试返回一个新函数。
把事情放在一起,一个工作的例子将是:
class A {
private mySecretNumber = 2;
decorate(target: any, propertyKey: string, descriptor: PropertyDescriptor) {
var f = descriptor.value;
// Don't use arrow function here, otherwise "this"
// will not be the current A instance.
descriptor.value = function(x: number) {
return f(this.mySecretNumber * x);
};
Object.defineProperty(target, propertyKey, descriptor);
}
@A.prototype.decorate
method(x: number) {
return x + 1;
}
}
var a = new A();
console.log(a.method(3)); // 7
更新:
根据您的用例,我将使用以下方法。基本上,您使用静态装饰器来加载decorate
可以在子类中实现的抽象方法。我修改了上面的例子,让你知道它是如何完成的。
abstract class A {
protected abstract decorate(x: number): number;
static decorate(target: any, propertyKey: string, descriptor: PropertyDescriptor) {
var f = descriptor.value;
descriptor.value = function(x: number) {
return f(this.decorate(x));
};
Object.defineProperty(target, propertyKey, descriptor);
}
@A.decorate
method(x: number) {
return x + 1;
}
}
class B extends A {
private mySecretNumber = 2;
protected decorate(x: number) { return this.mySecretNumber * x; }
}
var b = new B();
console.log(b.method(3)); // 7
推荐阅读
- typescript - LitElement - 模板中的 ForEach 子项
- matlab - Matlab 测试运行器跳过尝试导入不存在文件的测试函数
- c# - 错误 26 - 定位服务器/指定实例时出错
- ios - 如何在具有动态高度和宽度的自定义 UITableView 单元格中垂直重叠和隐藏标签以减小单元格大小并节省空间
- elasticsearch - 如何在桶排序弹性搜索查询中添加多个字段
- python - 如何为 dank memer 等不同用户设置不同的冷却时间?
- performance - 如何在 CockroachDB 中构建多租户系统以确保良好的性能?
- java - 使用外键保存对象不会返回数据库中的 ID
- c++ - C++17 to_string() 用逗号转换浮点数
- ios - 应用商店连接,首先在应用购买中添加