Подтвердить что ты не робот

Как заставить класс реализовать подпись вызова в Typescript?

Я определил следующий интерфейс в typescript:

interface MyInterface {
    () : string;
}

Этот интерфейс просто вводит сигнатуру вызова, которая не принимает никаких параметров и возвращает строку. Как реализовать этот тип в классе? Я пробовал следующее:

class MyType implements MyInterface {
    function () : string {
        return "Hello World.";
    }
}

Компилятор продолжает говорить мне, что

Класс 'MyType' объявляет интерфейс 'MyInterface', но не реализует его: Type 'MyInterface' требует сигнатуры вызова, но Type 'MyType' не имеет одного

Как реализовать подпись вызова?

4b9b3361

Ответ 1

Классы не могут соответствовать этому интерфейсу. Самое близкое, что вы можете получить, я думаю, это класс, который будет генерировать код, который функционально соответствует интерфейсу (но не в соответствии с компилятором).

class MyType implements MyInterface {
  constructor {
    return "Hello";
  }
}
alert(MyType());

Это сгенерирует рабочий код, но компилятор будет жаловаться, что MyType не может быть вызван, потому что он имеет подпись new() = 'string' (даже если вы вызываете его с помощью new, он вернет объект).

Чтобы создать что-то, что в действительности соответствует интерфейсу без жалобы компилятора, вам нужно будет сделать что-то вроде этого:

var MyType = (() : MyInterface => {
  return function() { 
    return "Hello"; 
  }
})();
alert(MyType());

Ответ 2

Примеры кода в этом ответе предполагают следующее объявление:

var implementation: MyInterface;

Предоставление реализации вызываемого интерфейса

В качестве ответа на принятый ответ, как это было предложено некоторыми из его комментаторов, функция, соответствующая сигнатуре вызова интерфейса, неявно реализует интерфейс. Таким образом, вы можете использовать любую подходящую функцию в качестве реализации.

Например:

implementation = () => "Hello";

Вам не нужно явно указывать, что функция реализует интерфейс. Однако, если вы хотите быть явным, вы можете использовать cast:

implementation = <MyInterface>() => "Hello";

Предоставление возможности повторного использования

Если вы хотите создать многоразовую реализацию интерфейса, как обычно, с интерфейсом Java или С#, просто сохраните функцию где-нибудь доступную для ее потребителей.

Например:

function Greet() {
    return "Hello";
}

implementation = Greet;

Предоставление параметризованной реализации

Вы можете захотеть параметризовать реализацию так же, как вы можете параметризовать класс. Вот один из способов сделать это:

function MakeGreeter(greeting: string) {
    return () => greeting;
}

implementation = MakeGreeter("Hello");

Если вы хотите, чтобы результат был введен как интерфейс, просто укажите тип возвращаемого значения или измените возвращаемое значение.