5

私が最初にオブジェクト指向プログラミング言語で働き始めたとき、私は次の規則を教えられました:

クラスでフィールドを宣言するときは、まだ初期化しないでください。コンストラクターでそれを行います。

C#の例:

public class Test
{
    private List<String> l;

    public Test()
    {
        l = new List<String>();
    }
}

しかし、最近誰かが私にそれをする理由を尋ねたとき、私は理由を思い付くことができませんでした。私はC#(または他のプログラミング言語、さらに言えば、これはすべてのオブジェクト指向言語で実行できると信じているため)の内部動作に精通していません。

では、なぜこれ行われるのですか?セキュリティですか?プロパティ?

4

6 に答える 6

14
  • 複数のコンストラクターがある場合は、フィールドを異なる値に初期化することをお勧めします

  • コンストラクターでフィールドを初期化する場合、コンストラクターの残りの部分に関して、いつ正確に初期化されるかについて混乱することはありません。これは、単一のクラスでは些細なことのように思えるかもしれませんが、コンストラクターコードが各レベルで実行され、スーパークラスフィールドにアクセスする継承階層がある場合は、それほど重要ではありません。

于 2009-03-26T12:44:53.067 に答える
10

C#コンパイラは、インラインで実行する非静的メンバーの初期化を取得し、コンストラクタに移動します。言い換えれば、これは:

class Test
{
    Object o = new Object();
}

これにコンパイルされます:

class Test
{
    Object o;

    public Test()
    {
        this.o = new Object();
    }
}

他の言語のコンパイラがこれをどのように処理するかはわかりませんが、C#に関する限り、スタイルの問題であり、自由に実行できます。 静的フィールドの処理方法が異なることに注意してください。 詳細については、この記事をお読みください

于 2009-03-26T12:43:29.233 に答える
2

これを行う理由の 1 つは、すべての初期化コードを 1 つの場所に配置することで、他のユーザーがクラスを読むのに便利だからです。そうは言っても、主な理由は 2 つあります。(1) TDD/単体テストを使用して、クラスの動作を定義します。パラメーターなしのコンストラクターの機能を知りたい場合は、私がパラメーターなしのコンストラクターで作成したテストを実際に読む必要があります。(2) C# 3.0 では、通常、自動プロパティとパラメーターなしのコンストラクターによるインライン初期化を使用して、オブジェクトをインスタンス化します。これははるかに柔軟で、コードが使用されている場所にプロパティの定義を配置します。これはコンストラクターの初期化をオーバーライドするため、ほとんど配置しません。もちろん、これは C# にのみ適用されます。

元。(2の)

  var foo = new Foo { Bar = "baz" };

  public class Foo
  {
       public string Bar { get; set; }

       public Foo() { }
  }
于 2009-03-26T12:49:24.413 に答える
1

コンストラクターには、内部変数の初期化に使用されるパラメーターがある場合があります。たとえば、配列のサイズ

于 2009-03-26T12:46:15.983 に答える
0

私はいつもクラスをオブジェクトのファクトリとして、コンストラクタを生産ラインの最後のストップとして考えるのが好きです。クラスで宣言されたフィールドは、オブジェクトを説明する青写真ですが、コンストラクターの呼び出しを通じてそのようなオブジェクトが注文される前に、青写真はオブジェクトに実現されません...また、誰かが指摘したように、すべての初期化をコンストラクターは読みやすさを向上させるだけでなく、初期化の動的性を提供します(これは、処理しているパラメーターのないコンストラクターではない可能性があります)。

また、一部の言語では、コンストラクターを使用してオブジェクトを元の状態にリセットする場合があります。そのため、コンストラクターでオブジェクトをインスタンス化する必要があります。

于 2009-03-26T13:31:05.093 に答える
0

両方のオプションを提供しないという説得力のある理由は聞いていません。本当の理由は、構文解析の観点から言語構造を単純化することに関係していると思います。これは、割り当てステートメントの解析に言語構文規則の 75% が必要な C 派生言語で特に当てはまります。それを許可し、それがどのように機能するかを正確に定義するのはいいことだと思います。継承と複数のコンストラクターを挿入すると複雑さが増すというマイケルのコメントに同意しますが、機能を追加したからといって、それを使用する必要があるわけではありません。私の投票は実際にはあまり加算されませんが、両方をサポートするために投票します.

于 2009-03-26T12:50:18.343 に答える