182

C# ライクな構文が好きなので、従来の JS から TypeScript に移行したいと考えていました。私の問題は、TypeScript で静的クラスを宣言する方法がわからないことです。

C# では、静的クラスを使用して変数とメソッドを整理し、それらを名前付きクラスにまとめて、オブジェクトをインスタンス化する必要はありません。バニラ JS では、単純な JS オブジェクトでこれを行っていました。

var myStaticClass = {
    property: 10,
    method: function(){}
}

TypeScript では、むしろ私の C シャープなアプローチを採用したいのですが、TS には静的クラスが存在しないようです。この問題の適切な解決策は何ですか?

4

15 に答える 15

244

抽象クラスは、TypeScript 1.6 以降、TypeScript の第一級市民となっています。抽象クラスをインスタンス化することはできません。

次に例を示します。

export abstract class MyClass {         
    public static myProp = "Hello";

    public static doSomething(): string {
      return "World";
    }
}

const okay = MyClass.doSomething();

//const errors = new MyClass(); // Error
于 2012-11-04T19:54:38.953 に答える
188

TypeScript は C# ではないため、必ずしも TypeScript で C# と同じ概念を期待する必要はありません。問題は、なぜ静的クラスが必要なのかということです。

C# では、静的クラスは単なるクラスであり、サブクラス化することはできず、静的メソッドのみを含める必要があります。C# では、クラス外で関数を定義することはできません。ただし、TypeScript ではこれが可能です。

関数/メソッドを名前空間 (つまり、グローバルではない) に配置する方法を探している場合は、TypeScript のモジュールの使用を検討できます。

module M {
    var s = "hello";
    export function f() {
        return s;
    }
}

外部から Mf() にアクセスできますが、s にはアクセスできず、モジュールを拡張できません。

詳細については、TypeScript の仕様を参照してください。

于 2012-11-03T19:24:49.347 に答える
75

クラスの静的プロパティとメソッドの定義は、Typescript 言語仕様の 8.2.1 で説明されています。

class Point { 
  constructor(public x: number, public y: number) { 
    throw new Error('cannot instantiate using a static class');
  } 
  public distance(p: Point) { 
    var dx = this.x - p.x; 
    var dy = this.y - p.y; 
    return Math.sqrt(dx * dx + dy * dy); 
  } 
  static origin = new Point(0, 0); 
  static distance(p1: Point, p2: Point) { 
    return p1.distance(p2); 
  } 
}

wherePoint.distance()は静的 (または「クラス」) メソッドです。

于 2012-11-03T19:31:26.613 に答える
1

http://www.basarat.com/2013/04/typescript-static-constructors-for.htmlを参照してください。

これは、静的コンストラクターを「偽造」する方法です。危険がないわけではありません - 参照されているコードプレックスの項目を参照してください。

class Test {
    static foo = "orig";

    // Non void static function
    static stat() {
        console.log("Do any static construction here");
        foo = "static initialized";
        // Required to make function non void
        return null;
    }
    // Static variable assignment
    static statrun = Test.stat();
}

// Static construction will have been done:
console.log(Test.foo);
于 2014-05-23T02:03:14.937 に答える
1

public static readonly メンバーで抽象クラスを使用して、探しているものと非常によく似たものを実現できます。小さなデータをまとめて整理するために、C# や C/C++のようなものを探していると思います。struct

抽象クラスの優れた点は、

  • それらはインスタンス化できず、
  • および からのみ派生できます。
  • それらは、それらで定義されたメソッドの一部またはすべての基本実装を提供できます。

この手法を使用して、enum(たとえば、スイッチをオンにすることはできません) をいくらか模倣することもできますが、単なる文字列や数値以上のプロパティを持つことができます。

// you can omit the public keyword because it's the default in TS, I left it here for clarity

export abstract class RequestTypes {
  public static readonly All = 'All types';
  public static readonly Partners = 'Partners';
  public static readonly Articles = 'Articles';
}
于 2021-07-05T14:09:47.117 に答える
0

私は似たようなものを探していて、Singleton Pattern.

参考:シングルトンパターン

さまざまな種類のファイルをロードする BulkLoader クラスに取り組んでおり、Singleton パターンを使用したいと考えていました。このようにして、メイン アプリケーション クラスからファイルをロードし、ロードしたファイルを他のクラスから簡単に取得できます。

以下は、TypeScript とシングルトン パターンを使用してゲームのスコア マネージャーを作成する方法の簡単な例です。

クラスSingletonClass {

private static _instance:SingletonClass = new SingletonClass();

private _score:number = 0;

constructor() {
    if(SingletonClass._instance){
        throw new Error("Error: Instantiation failed: Use SingletonDemo.getInstance() instead of new.");
    }
    SingletonClass._instance = this;
}

public static getInstance():SingletonClass
{
    return SingletonClass._instance;
}

public setScore(value:number):void
{
    this._score = value;
}

public getScore():number
{
    return this._score;
}

public addPoints(value:number):void
{
    this._score += value;
}

public removePoints(value:number):void
{
    this._score -= value;
}   }

次に、他のクラスのどこでも、次の方法でシングルトンにアクセスできます。

var scoreManager = SingletonClass.getInstance();
scoreManager.setScore(10); scoreManager.addPoints(1);
scoreManager.removePoints(2); console.log( scoreManager.getScore() );
于 2016-05-09T17:34:24.820 に答える
0

次のように Typescript でクラスを作成できます。

export class Coordinate {
        static x: number;
        static y: number;
        static gradient() {
            return y/x;
        }
    }

インスタンス化を「せずに」そのプロパティとメソッドを参照します。

Coordinate.x = 10;
Coordinate.y = 10;
console.log(`x of ${Coordinate.x} and y of ${Coordinate.y} has gradient of ${Coordinate.gradient()}`);

ちなみに、補間構文 ${} と組み合わせてバッククォート `` を使用すると、コードとテキストを簡単に混在させることができます :-)

于 2020-12-11T18:50:54.707 に答える