2017-03-13 8 views
0

私はまだTypeScriptで新しくなっているので、他のSOの質問とドキュメントは、私が始めたときと同じように混乱することがあります。私はこれをできるだけ簡単なものにするつもりです。もし重複していたら、私にそれを指摘してください。TypeScript "Function"型とメソッドの署名を宣言する

私は本質的に、タイプFunctionのメンバの作成とクラス内のメソッドシグネチャの定義との間にどのような違いがあるのだろうかと思っています。以下の例を考えてみましょう:

export abstract class MyBase { 
    protected abstract method1(); 
    protected abstract method2(): void; 
    protected abstract method3: Function; 
} 

私の理解では、1と2の間の差は2 voidを持っているかが指定されているものは何でもタイプながら1 anyの戻り値の型を持っているということであるということです。

1と3の違いはわかりません。 1つはありますか?

最後に、1と2の関係で、関数型が汎用ではないのはなぜですか?我々はこれを持っている可能性があります(ただし、我々はできません)のように言い換えると、それはそうです:

protected abstract method4: Function<void>; 

答えて

1

Iは1と3の違いは何であるかそうかわかりません。

大きな違い:

declare function method1(); //() => any 
declare const method3: Function; // ALL Functions 

パラメータの数だけに基づいて:1と2の間の関係を考えると

method1(123); // Error 
method3(123); // Okay 

が、なぜに許可されていない関数型でありますジェネリックですか?

これはC#と同じではありません。 FunctionはネイティブJavaScript関数の型名です。

1

クラスでこれらのメソッドの違い

  1. 戻り値の型 - 彼らの戻り値の型が異なります。 method1 & method3の戻り値タイプはanyですが、methods2の戻り値タイプはvoidです。あなたは以下のようにtsc --declaration出力.d.tsを使用して宣言ファイルを見ることができます:

    export declare abstract class MyBase { 
        protected abstract method1(): any; 
        protected abstract method2(): void; 
        protected abstract method3: Function; 
    } 
    
  2. 静的メソッド対ダイナミック - method1 & method2prototypeを経由して列挙が、method3ができない、のですることができますそれはプロパティであり、メソッドではありません。また、Superclass.prototypeに決して追加することはできません。スーパークラスのコンストラクタでは、this.method3=()=>{}のみを使用してmethod3を割り当てます。したがって、propertiesとサブクラスとして列挙された動的メソッドも、サブクラスでその動的メソッドを継承しますが、superを使用して上書きすることはできません。そうした場合、TypeScriptコンパイラはエラーを報告し、呼び出すと実行時エラーがスローされます。私が言ったことを説明するためのテストはここにあります。

提案:あなたは、静的な技術、method3のために使用されていない動的な技術を用いた方法を宣言する必要があります。動的手法を使用する場合は、Superclassメソッドを再利用することはできません。

class Superclass { 
     method1() { 
     } 

     method2 = function() { 
     }; 
     method3 = function() { 

     }; 
    } 
    class Subclass extends Superclass { 
     method1() { 
      super.method1(); 
     } 

     method3 = function() { 
      super.method3(); 
     } 
    } 

    test("methods as property can't be enumerated as prototype",() => { 
     expect(Object.keys(Superclass.prototype)).not.toContain('method3'); 
     expect(Object.keys(new Superclass())).toContain('method3'); 
    }); 
     expect(Object.keys(new Superclass())).toContain('method3'); 

    test("methods as prototype can be enumerated as prototype",() => { 
     expect(Object.keys(Superclass.prototype)).toContain('method1'); 
     expect(Object.keys(new Superclass())).not.toContain('method1'); 
    }); 

    test("methods as property can be inherited in subclass",() => { 
     let it = new Subclass(); 
     it.method2();//works fine 
    }); 

    test("methods as property can't be overrided so you can't call `super`",() => { 
     let it = new Subclass(); 
     expect(()=>it.method3()).toThrow(); 
    }); 
関連する問題