それらはスタック上の不変の値タイプです。それらをconstにできない理由は何ですか?
参照:
値型コンストラクターはanything-たとえば、時刻に基づいてロジックを切り替える可能性があるためです。定数値型は知的に理にかなっていますが、コンストラクターが自由に実行できる柔軟性があるため、実際にはカスタム値型を処理できません。 (定数はcompile time、で評価されることに注意してください。つまり、コンストラクターはコンパイル時に実行する必要があります。)
C#のconstは、それが決定できることを意味しますコンパイル時。これが、int
やstring
などのプリミティブ型のみがconstになることができる理由です。
C出身の場合は、readonly
キーワードの方が適している可能性があります。
C#コンパイラが構造体型のconst
値を生成するには、そのすべてのフィールドにどの値を入れるかを知っている必要があります。 C#コンパイラは、Decimal
のような特定の型のフィールドを初期化する方法を本質的に知っていますが、ほとんどの値型ではそのような知識はありません。
すべてのstruct
フィールドが公開されているコンテキストで、コンパイラーが構造体型の定数値を宣言する手段を提供することは可能です。構造体のフィールドがprivate
の場合、その型の定数は構造体内でのみ宣言できます。フィールドがinternal
の場合、定数はアセンブリ内の任意の場所で宣言できます。 public
であれば、どこでも宣言できます。
私はそのような機能を見たいのですが、主流の.net言語がそれを実装することを期待していません。コンパイラが本質的に知っている型の名前付き定数は、他の定数式に参加できますが、static readonly
変数は参加できません。 NumRows
が4に等しい定数の場合、NumRows
が外部アセンブリで定義されていても、Arr[3*NumRows+7]
のような式はArr[19]
で置き換えることができます。これにより、そのような定数はstatic readonly
変数よりも大幅に有利になります。ただし、定数がコンパイラーが本質的に認識しない型である場合、定数式に参加する能力は非常に制限され、そもそも定数であることの利点が事実上打ち消されます。値型定数に公開フィールドがある場合、コンパイラーがそのフィールドの値を定数として使用することは可能ですが、.net言語の作成者は公開フィールドを持つ構造に哲学的に反対しているため、私は期待していません。それらが可能であっても、そのような使用を許可します。
static readonly
変数よりも定数を優先する使用例がいくつかありますが、そのようなケースの多くは、既存のタイプを使用して許容できる範囲で処理できます。たとえば、ライブラリはconst Int64
を公開してそのバージョンに関する情報をエンコードし、その値をGetLinkedVersionInfo
メソッドのデフォルトパラメータ値として使用する場合があります。問題の値は、コンパイル時に呼び出しコードに「組み込まれる」ため、メソッドは呼び出し元がリンクされているライブラリのバージョンを報告し、実行しているバージョンに互換性の問題があるかどうかを識別できます。
単純な可変構造体でreadonly
キーワードをテストしました。
_struct Test
{
public int value;
public void setInt(int val)
{
value = val;
}
}
static class Program
{
public static readonly Test t = new Test();
static void Main()
{
Console.WriteLine(t.value); // Outputs "0"
t.setInt(10);
//t.value = 10; //Illegal, will not let you assign field of a static struct
Console.WriteLine(t.value); // Still outputs "0"
}
}
_
readonly
構造体は技術的にはコンパイル時定数ではありませんが、ランタイムはそれを変更させません。ステップ実行でもsetInt()
メソッドをスローしましたが、値の変更のように見えますが、Mainの変更は表示されません。
構造体自体は「読み取り専用」メモリに配置され、変更できないようになっていると思います。ポインターを一定に保つクラスとは異なり、クラスフィールド自体を自由に変更できます。
つまり、可変構造体であっても、_static readonly
_は事実上const
であるように見えます。