什么是新的?()在打字稿中意味着什么?

时间:2015-12-31 19:55:04

标签: generics typescript

我在typescript playground中有这段代码:

interface IFoo {
    new?():string;

}

class Foo implements IFoo {
    new() {
     return 'sss'; 
    }

}

我必须把"?"在接口方法new中,否则会显示编译错误。我无法弄清楚原因。

更新:   原始问题不是一个使用new的好方法,所以我发布了一个更现实和实用的方法来使用上面提到的new():

interface IUser {
  id: number;
  name: string;
}

interface UserConstructable {
  new (id: number, name: string, ...keys: any[]): IUser;
}

class User implements IUser {
  constructor(public id: number, public name: string) {

  }
}

class Employee implements IUser {
  constructor(public id: number, public name: string, 
    private manager: string) {

  }
}


class UserFactory {
   private static _idx: number = 0;
   static makeUser(n: UserConstructable): IUser {
      let newId = UserFactory._idx++;

      return new n(newId, 'user-' + newId, 'manager-' + newId);
   } 
}

console.log(UserFactory.makeUser(User));
console.log(UserFactory.makeUser(User));
console.log(UserFactory.makeUser(Employee));

2 个答案:

答案 0 :(得分:3)

让我们把它分成几个部分......我知道你已经知道其中的一些,但我试图完成。

1..2.3..4
new?():string;
  1. 在此特定情况下,new不是关键字,只是方法名称...由于此列表中的下一项...

  2. ?使这个可选(即您可以在不实现此方法的情况下实现接口)。

  3. ()表示new是一种方法。

  4. 返回类型是一个字符串

  5. 实施例

    class Foo implements IFoo {
        new() {
            return 'sss'; 
        }
    }
    
    class Bar implements IFoo {
        // Because new is optional, you don't have to implement it
    }
    

    如果省略?,那么您使用new作为关键字 - 但TypeScript会将示例中的代码解释为一种简单的方法。

    但总的来说,我避免使用被称为保留字的内容来命名成员。

答案 1 :(得分:1)

在javascript中,函数是对象,因此typescript接口也应该能够匹配函数。这就是为什么我们得到那些奇怪的接口。

interface SomeFunc {
  (key: string): boolean;
  (key: number): boolean;
}

该接口只匹配接受字符串或数字的函数,并返回布尔值。

现在考虑构造函数的情况(即ES5中的类 - )。

function MyClass() {
  this.prop = value;
}
let myClass = new MyClass;

我们需要一种方法来创建一个匹配MyClass函数签名的接口。这是我们在接口中获得new函数的地方。

interface IFoo {
  new (key: string): {key:string};
}

function someFunction(key: string) { // doesn't match IFoo
  return {key};
}

var someObject = { // still doesn't match IFoo
  new(key: string) { 
    return {key};
  },
};

function MyClass(key: string) { // matches IFoo! must be called like `new MyClass()`
  this.key = key;
}

所以你可以说函数new的签名必须与类构造函数的签名匹配。

interface IFoo {
  new(key: string): {};
}
class Foo implements IFoo { // works ok
  constructor(key: string) { // you can't return anything
  }
}

我认为你想要做的是:

interface IFoo {
  new: () => string;
}

即。 IFoo应该有一个名为new的属性,它是一个返回字符串的函数。