4

私は次のようなクラスを持っています:

class SomeTests {
  private Guid[] someGuids = new Guid[] { ... }

  public void ThoseGuidsShouldAlwaysBeThere() {
    foreach (Guid g in someGuids) { // error appears here
        // ...
    }
  }
}

意味的には、コードを再コンパイルする前を除いて、更新されるべきではないのでsomeGuids、私はなりたいです。ただし、キーワードconstを追加すると、エラー CS0168が生成されます。constnull is not valid in this context.

そのエラーのMSDNページを読むと、コンパイラは私がこれをしていると考えているようです:

foreach (Guid g in null) {

ここで追加によってこの問題がどのように発生するのか、および意味の問題を解決する方法がわかりませんconst(リストは読み取り専用であり、書き込み可能ではありません)。リストではなく配列として保持することで「ほぼ」十分です。

4

2 に答える 2

3

この使用法のreadonlyキーワードは少し誤解を招くものです。コレクションが変更されるのではなく、再インスタンス化されるのを防ぐものと見なしてください。

例:

 private readonly Guid[] someGuids = new Guid[] { Guid.NewGuid() };

 //This will not compile because it is read-only.
 someGuids = new Guid[] { Guid.NewGuid() };

 //This still compiles, and the first member will be changed
 someGuids[0] = Guid.NewGuid();

代わりに、キーワードSystem.Collections.ObjectModel.ReadOnlyCollection<T>と組み合わせて使用​​することを検討することをお勧めします。readonly

例:

    public readonly ReadOnlyCollection<Guid> someGuids = new
       ReadOnlyCollection<Guid>(new Guid[] { Guid.NewGuid(), Guid.NewGuid() });

コレクションを再インスタンス化することも、そのメンバーを変更することもできなくなります。

于 2012-12-20T18:04:17.510 に答える
2

定数を作成しようとするとGuid[]、「文字列以外の参照型の const フィールドは null でのみ初期化できます」というエラーが表示されます。

readonly代わりに作ってください:

private readonly Guid[] someGuids = new Guid[] { Guid.NewGuid() };

コンストラクターで値を割り当てることreadonlyもできます。

public SomeTests()
{
    someGuids = new[] { Guid.NewGuid(), Guid.NewGuid() };
}

Jeffery がコメントで述べたように、この解決策はsomeGuids再割り当てを防ぎますが、アイテムは引き続き変更できます。Jeffery は、彼の回答でこの問題に取り組んでいます。

于 2012-12-20T17:22:53.003 に答える