在打字稿(javascript)中向类方法添加方法

时间:2018-10-05 17:09:58

标签: javascript typescript methods

我想在方法中添加方法:

class MyClass {
    public foo(text: string): string {
        return text + ' FOO!'
    }

    // Some magical code which adds the method `bar` to `foo`.
}

const obj = new MyClass();
console.log(obj.foo('thing'));
console.log(obj.foo.bar('other thing'));

这可能吗?我找到了similar case的函数:

function Sum(x: number) { /*...*/ }
namespace Sum {
    export function empty() { /*...*/ }
}

有没有办法对一个类的方法做同样的事情?

我想在类中添加代码,而不是在创建对象后进行猴子修补。

3 个答案:

答案 0 :(得分:2)

您可以访问类原型上的函数,并随便使用它。我认为它不是特别漂亮,但是您可以执行以下操作:

class MyClass {
  constructor(myName) {
    this.myName = myName
    this.constructor.prototype.foo.bar = (function(a) {
      console.log(this.myName, "calling foo.bar with:", a)
    }).bind(this)
  }
  foo(text) {
    return text + ' FOO!'
  }

}

const obj = new MyClass("Mark");
obj.foo.bar('thing')
console.log(obj.foo('test'))

答案 1 :(得分:0)

并非完全符合您的要求,但最终结果有效:

28.0.0

编辑我阅读了您对我的评论的回答。我认为实现目标的更简单方法是使用默认参数,例如:

class MyClass {
  public foo: MyChildClass = new MyChildClass();
}

class MyChildClass {
  public bar(text: string): string{
    return text;
  }
}

const obj = new MyClass();
console.log(obj.foo.bar('thing'));

现在,您的解决方案具有的优势是,由于具有附加的功能名称,您可以在呼叫站点上清楚地看到您正在请求旁路或快照。通过使用具有可选属性的接口替换foo的参数,可以在打字稿中获得相似的结果。在其他语言中,我们将这种技术称为参数:

function foo(text: string, snapshot = false): string{
  if(snapshot){
    return 'snapshot';
  }
  return text;
}

console.debug(foo('test'));
console.debug(foo('test', true));

答案 2 :(得分:0)

更新:这可以使用交叉点类型完全解决:

class MyClass {

    constructor() {
        this.foo = function () {
            return "this is a"
        };

        this.foo.bar = function() {
            return "this is b"
        };
    }

    public foo: Function & { bar?: () => string };
}

const obj = new MyClass();

console.log(obj.foo());
console.log(obj.foo.bar());

Test it in the Typescript Playgroung

之所以可能这样做,是因为通过在类方法的类型定义中使用&符号,我们可以对Function类型和简单类型的Object进行融合具有1个属性bar,它本身就是另一个函数。但是,必须在第二种类型中将此属性声明为可选属性,这是因为Typescript会抱怨在类的构造函数内部的第一次赋值中,它不满足此额外的类型。但是实际上,构造函数中的下一个表达式通过分配bar的{​​{1}}属性来完成它。

---答案很老,请不要使用它,这并不能完全满足OP的要求

为类成员'foo'定义一个getter访问器方法,而不是方法,该方法将返回带有函数'bar'的对象

foo