admin管理员组

文章数量:1384803

My goal is to have an interface with a static method that returns a new instance of a class.

I have the following code that has a type error. How can I resolve this? Playground

interface New {
  new (): this
}

class Hello implements New {
  //  ^^^^^ Class 'Hello' incorrectly implements interface 'New'.
  //          Type 'Hello' provides no match for the signature 'new (): this'.

  static new () {
    return new Hello()
  }
}

I've tried several variants, all seem to have the same error. For instance:

interface New<T> {
  new (): T
}

class Hello implements New<Hello> {
  //  ^^^^^ Class 'Hello' incorrectly implements interface 'New<Hello>'.
  //          Type 'Hello' provides no match for the signature 'new (): Hello'.

  static new () {
    return new Hello()
  }
}

^^ Playground

My goal is to have an interface with a static method that returns a new instance of a class.

I have the following code that has a type error. How can I resolve this? Playground

interface New {
  new (): this
}

class Hello implements New {
  //  ^^^^^ Class 'Hello' incorrectly implements interface 'New'.
  //          Type 'Hello' provides no match for the signature 'new (): this'.

  static new () {
    return new Hello()
  }
}

I've tried several variants, all seem to have the same error. For instance:

interface New<T> {
  new (): T
}

class Hello implements New<Hello> {
  //  ^^^^^ Class 'Hello' incorrectly implements interface 'New<Hello>'.
  //          Type 'Hello' provides no match for the signature 'new (): Hello'.

  static new () {
    return new Hello()
  }
}

^^ Playground

Share Improve this question asked Mar 18 at 5:02 NickNick 6,4904 gold badges34 silver badges75 bronze badges 3
  • 1 You use an interface to describe class instances, not class constructors or static methods within classes. – Sani Huttunen Commented Mar 18 at 6:58
  • This question seems to be confused, or based on several false premises. Your new(): T is a construct signature, not a method named new. You can't implement that with a method named new. If you want a method named new you need to quote it like "new"(): T. But then you run into the fact that the interface describes the instance, not static class members. And then you have the issue that polymorphic this cannot be satisfied by new Hello() (what about subclasses)? – jcalz Commented Mar 18 at 14:36
  • (see prev comment) Please edit this question to clear up these multiple problems, or ask a question about one of them. Presumably the main issue is the static/instance distinction and the existing answers address that. But maybe you're really having a problem with "new" vs new or polymorphic this? Pick the primary issue and remove the others and we can help (and you can ask about the others in other questions if you have multiple problems). – jcalz Commented Mar 18 at 14:38
Add a comment  | 

2 Answers 2

Reset to default 0

First of all, interface does not support static methods.

Secondly, there may be no need to wrap a static method inside a type construct like interface when we can have a free method which is essentially static in nature. Please read Why No Static Classes? for the same kind of reasoning.

// Unnecessary "static" class
class MyStaticClass {
  static doSomething() {}
}

// Preferred (alternative 1)
function doSomething() {}

Proposed solution:

Please refer to Using Class Types in Generics.

The sample code demoes the same.

class A {}

function create<Type>(c: { new (): Type }): Type {
  return new c();
}

const a = create(A);

The problem you cannot type a static part of a class with an interface which is an unfortunate limitation of TS (has its reasons?). Something similar you want to achieve is to introduce New class and implement the new method on it. Also I would avoid using new since it's also a keyword. Usually create is used and Base with a base class:

Playground

interface New {
  
}
class New {
  static new<C extends new() => InstanceType<C>>(this: C){
    return new this
  }
}

class Hello extends New {

}

const hello = Hello.new(); // const hello: Hello

本文标签: typescriptClass incorrectly implements interface that returns thisStack Overflow