使用Java,我们可以创建ActionListener类的实例,该实例具有一个抽象方法,就像这样(已经有一段时间了):
new ActionListener(){
@Override
public void actionPerformed(ActionEvent e) {
// whatever
}
}
使用TypeScript,这是我能找到的最接近的
export abstract class ActionListener {
constructor(f: any) {
this.actionPerformed = f;
}
abstract actionPerformed(input: string): string;
}
new ActionListener(input => {
});
至少有2个问题:
如果在TS中使用抽象方法,则该类必须抽象(我认为在Java中,您可以有稍后可以实现的抽象方法)。
我不知道如何将输入函数f的类型绑定到解析方法的类型。
有人知道TS是否有办法吗?
也许我们不能在TS中使用abstract
,而必须这样做:
type ActionPerformed = (input: string) => string;
export class ActionListener {
parse: ActionPerformed;
constructor(f: ActionPerformed) {
this.parse = f;
}
}
new ActionListener(input => {
return 'foo';
});
答案 0 :(得分:5)
使用Java,我们可以创建具有抽象方法的ActionListener类的实例
不,您不能创建具有抽象方法的类的实例。调用该抽象方法时应该发生什么?
您可以 做的是,您可以创建实现该抽象方法的抽象类的子类,也可以创建该子类的实例 < / em>。这正是您的Java代码正在做的事情。您的Java代码不是 not 实例化ActionListener
的对象。您的Java代码正在创建ActionListener
的子类,该子类将覆盖actionPerformed
,并实例化该子类 。
现在,TypeScript当然支持子类化,因此您可以在TypeScript中做同样的事情:创建一个子类,重写/实现该方法,然后实例化该子类 :
new (class extends ActionListener {
actionPerformed(input: string): string {
return "Hello"
}
})(input => {
// Whatever
});
或者您可以这样做:
new (class implements ActionListener {
actionPerformed(input: string): string {
return "Hello"
}
});
答案 1 :(得分:1)
这在JavaScript或TypeScript中不是必需的。 Java没有将函数作为一流对象的概念,lambda只是实现了功能接口的实例化对象的糖。
这样,JS / TS中的惯用方式是在这里没有类,而只是传递一个回调函数:
interface ActionListener {
(ev: Event) => void;
}
function iNeedAnActionHandler(actionListener: ActionListener) {
// do stuff
const ev = new Event(); // whatever
actionListener(ev);
}
不需要笨拙的类和接口实现即可传递回调。