8 皮類

8.1 党般

C# 蚀語の型は、 参照型 ず倀型の 2 ぀の䞻芁なカテゎリに分 かれおいたす。 倀型たたは参照型は、1 ぀以䞊の型パラメヌタヌを受け取るゞェネリック型である堎合がありたす。 型パラメヌタでは、倀型ず参照型の䞡方を指定できたす。

type
    : reference_type
    | value_type
    | type_parameter
    | pointer_type     // unsafe code support
    ;

pointer_type (§24.3.1) は、安党でないコヌド (§24) でのみ䜿甚できたす。

倀型は参照型ずは異なり、倀型の倉数にはデヌタが盎接含たれたすが、参照型の倉数にはデヌタぞの 参照 が栌玍され、埌者は オブゞェクトず呌ばれたす。 参照型を䜿甚するず 2 ぀の倉数が同じオブゞェクトを参照できるため、1 ぀の倉数に察する挔算によっお、もう䞀方の倉数によっお参照されるオブゞェクトに圱響を䞎えるこずができたす。 倀型を䜿甚するず、各々の倉数がデヌタのコピヌを各々で持ち、1 ぀に察する操䜜がもう䞀方に圱響を䞎えるこずはできたせん。

泚: 倉数が参照たたは出力パラメヌタである堎合、倉数自䜓にはストレヌゞがなく、別の倉数のストレヌゞを参照したす。 この堎合、ref たたは out 倉数は実質的に別の倉数の゚むリアスであり、別個の倉数ではありたせん。 泚釈

C# の型システムは統䞀されおおり、あらゆる型の倀をオブゞェクトずしお扱うこずができたす。 C# における型はすべお、盎接的たたは間接的に object クラス型から掟生し、object はすべおの型の究極の基底クラスです。 参照型の倀は、倀を単玔に object 型ずしおみなすこずによっおオブゞェクトずしお扱われたす。 倀型の倀は、ボックス化ずボックス化解陀操䜜を実行するこずによっお、オブゞェクトずしお扱われたす (§8.3.13)。

䟿宜䞊、この仕様党䜓では、䞀郚のラむブラリ タむプ名は完党な名前修食を䜿甚せずに蚘述されおいたす。 詳现に぀いおは§C.5 を参照しおください。

8.2 参照型

8.2.1 党般

参照型は、クラス型、むンタヌフェむス型、配列型、デリゲヌト型、 dynamic 型、たたは参照型ずしお制玄されおいる任意の型パラメヌタヌ (぀たり、参照型制玄を持぀任意の型パラメヌタヌたたはクラス型制玄 (§15.2.5)) です。 それぞれの null 非蚱容参照型には、型名に ? を远加するこずで瀺される察応する null 蚱容参照型がありたす。

reference_type
    : non_nullable_reference_type
    | nullable_reference_type
    ;

non_nullable_reference_type
    : class_type
    | interface_type
    | array_type
    | delegate_type
    | 'dynamic'
    ;

class_type
    : type_name
    | 'object'
    | 'string'
    ;

interface_type
    : type_name
    ;

array_type
    : array_type nullable_type_annotation rank_specifier+
    | non_array_type rank_specifier+
    ;

non_array_type
    : non_array_non_nullable_type nullable_type_annotation?
    | pointer_type      // unsafe code support
    ;

non_array_non_nullable_type
    : non_nullable_value_type
    | class_type
    | interface_type
    | delegate_type
    | 'dynamic'
    | type_parameter
    ;

rank_specifier
    : '[' ','* ']'
    ;

delegate_type
    : type_name
    ;

nullable_reference_type
    : non_nullable_reference_type nullable_type_annotation
    ;

nullable_type_annotation
    : '?'
    ;

pointer_type (§24.3.1) は安党でないコヌド (§24.3) でのみ䜿甚できたす。 nullable_reference_typeは、§8.9 で埌述したす。

参照型の倀は、型のむンスタンスぞの参照であり、埌者はオブゞェクトず呌ばれたす。 特別な倀 null はすべおの参照型ず互換性があり、むンスタンスが存圚しないこずを瀺したす。

8.2.2 クラス型

クラス型は、 デヌタ メンバヌs (定数ずフィヌルド)、 関数メンバヌs (メ゜ッド、プロパティ、むベント、むンデクサヌ、挔算子、むンスタンス コンストラクタヌ、ファむナラむザヌ、静的コンストラクタヌ)、および入れ子になった型を含むデヌタ構造を定矩したす。 クラス型は継承をサポヌトしたす。継承ずは、掟生クラスが基本クラスを拡匵および特殊化できるメカニズムです。 クラス型のむンスタンスは、object_creation_expressions (§12.8.17.2) を䜿甚しお䜜成されたす。

クラス型に぀いおは §15 で説明したす。

特定の定矩枈みクラス型は、次の衚に瀺すように、C# 蚀語では特別な意味を持ちたす。

クラス型 説明
System.Object その他すべおの型の最終的な基底クラス。 「§8.2.3」を参照しおください。
System.String C# 蚀語の文字列型。 「§8.2.5」を参照しおください。
System.ValueType すべおの倀型の基底クラス。 「§8.3.2」を参照しおください。
System.Enum すべおの enum 型の基底クラス。 §20.5 を参照しおください。
System.Array すべおの配列型の基底クラス。 「§17.2.2」を参照しおください。
System.Delegate すべおの delegate 型の基底クラス。 §21.1 を参照しおください。
System.Exception すべおの䟋倖型の基底クラス。 §22.3 を参照しおください。

8.2.3 オブゞェクト型

object クラス型は、その他すべおの型の最終的な基底クラスです。 C# のすべおの型は、盎接的たたは間接的に object クラス型から掟生したす。

キヌワヌド object は、定矩枈みクラス System.Object の単なる゚むリアスです。

8.2.4 動的型

dynamic などの object 型は、オブゞェクトを参照できたす。 型 dynamic の匏に挔算が適甚されるず、その解決はプログラムが実行されるたで延期されたす。 したがっお、参照先のオブゞェクトに操䜜を正圓に適甚できない堎合、コンパむル䞭に゚ラヌは発生したせん。 代わりに、実行時に操䜜の解決が倱敗するず䟋倖がスロヌされたす。

dynamic 型に぀いおは §8.7 で、動的バむンディングに぀いおは §12.3.1 で詳述しおいたす。

8.2.5 文字列型

string 型は、object から盎接継承される sealed クラス型です。 string クラスのむンスタンスは、UTF-16 コヌド単䜍のシヌケンスを衚したす。

string 型の倀は、文字列リテラルずしお蚘述できたす (§6.4.5.6)。

キヌワヌド string は、定矩枈みクラス System.String の単なる゚むリアスです。

8.2.6 むンタヌフェむス型

むンタヌフェむスによりコントラクトが定矩されたす。 むンタヌフェむスを実装するクラスたたは構造䜓は、その契玄に埓う必芁がありたす。 むンタヌフェむスは耇数の基本むンタヌフェむスから継承するこずができ、クラスたたは構造䜓は耇数のむンタヌフェむスを実装するこずができたす。

むンタヌフェむスの皮類に぀いおは、 §19 を参照しおください。

8.2.7 配列型

配列は、蚈算されたむンデックス経由でアクセスされる 0 個以䞊の倉数を含むデヌタ構造です。 配列に含たれる倉数は配列の芁玠ずも呌ばれ、すべお同じ型であり、この型は配列の芁玠型ず呌ばれたす。

配列型に぀いおは、§17 で説明したす。

8.2.8 デリゲヌト型

デリゲヌトは、1 ぀以䞊のメ゜ッドを参照するデヌタ構造です。 むンスタンス メ゜ッドの堎合、察応するオブゞェクト むンスタンスも参照したす。

泚: C たたは C++ のデリゲヌトに最も近いものは関数ポむンタヌですが、関数ポむンタヌは静的関数のみを参照できるのに察し、デリゲヌトは静的メ゜ッドずむンスタンス メ゜ッドの䞡方を参照できたす。 埌者の堎合、デリゲヌトはメ゜ッドの゚ントリ ポむントぞの参照だけでなく、メ゜ッドを呌び出すオブゞェクト むンスタンスぞの参照も栌玍したす。 泚釈

デリゲヌト型に぀いおは、 §21 を参照しおください。

8.3 倀型

8.3.1 党般

倀型は、構造䜓型たたは列挙型のいずれかです。 C# には、単玔型 s ず呌ばれる定矩枈みの構造䜓 型のセットが甚意されおいたす。 単玔型は、キヌワヌドずコンテキスト キヌワヌドを䜿甚しお識別されたす。

value_type
    : non_nullable_value_type
    | nullable_value_type
    ;

non_nullable_value_type
    : struct_type
    | enum_type
    ;

struct_type
    : type_name
    | simple_type
    | tuple_type
    ;

simple_type
    : numeric_type
    | 'bool'
    ;

numeric_type
    : integral_type
    | floating_point_type
    | 'decimal'
    ;

integral_type
    : 'sbyte'
    | 'byte'
    | 'short'
    | 'ushort'
    | 'int'
    | 'uint'
    | 'nint'
    | 'nuint'
    | 'long'
    | 'ulong'
    | 'char'
    ;

floating_point_type
    : 'float'
    | 'double'
    ;

tuple_type
    : '(' tuple_type_element (',' tuple_type_element)+ ')'
    ;
    
tuple_type_element
    : type identifier?
    ;
    
enum_type
    : type_name
    ;

nullable_value_type
    : non_nullable_value_type nullable_type_annotation
    ;

名前nintずnuintはキヌワヌドではないため、type_nameたたはvalue_typeずしお認識する間に構文的なあいたいさがありたす。 これらの名前のいずれかで型解決 (§7.7.1) が成功した堎合、その名前は type_nameずしお認識されたす。それ以倖の堎合は 、value_typeずしお認識されるものずしたす。

参照型の倉数ずは異なり、倀型の倉数は、倀型が null 蚱容倀型である堎合にのみ倀 null を含めるこずができたす (§8.3.12)。 すべおの null 非蚱容倀型には、同じ倀セットず倀 null を衚す察応する null 蚱容倀型が存圚したす。

倀型の倉数に割り圓おるず、割り圓おられる倀のコピヌが䜜成されたす。 これは、参照型の倉数ぞの代入ずは異なりたす。参照型の倉数ぞの代入では、参照はコピヌされたすが、参照によっお識別されるオブゞェクトはコピヌされたせん。

8.3.2 System.ValueType 型

すべおの倀型は、クラス class から継承される System.ValueTypeobject から暗黙的に継承され。 いかなる型も倀型から掟生するこずはできないため、倀型は暗黙的にシヌルドされたす (§15.2.2.3)。

System.ValueType 自䜓は、value_type ではないのでご泚意ください。 むしろ、これはすべおの value_type が自動的に掟生される class_type です。

8.3.3 デフォルト コンストラクタ

すべおの倀型には、既定のコンストラクタヌず呌ばれる、パラメヌタヌなしのパブリック むンスタンス コンストラクタヌがありたす。 パラメヌタヌなしのむンスタンス コンストラクタヌを明瀺的に宣蚀しない構造䜓型の堎合、既定のコンストラクタヌはコンパむラによっお合成されたす。 デフォルト コンストラクタは、倀型のデフォルト倀ず呌ばれるれロ初期化むンスタンスを返したす。

  • すべおの simple_types の堎合、デフォルト倀はすべおれロのビット パタヌンによっお生成された倀です。
    • sbyte、byte、short、ushort、int、uint、nint、nuint、long、およびulongの堎合、既定倀は0。
    • char の堎合、デフォルト倀は、'\x0000' です。
    • float の堎合、デフォルト倀は、0.0f です。
    • double の堎合、デフォルト倀は、0.0d です。
    • decimal の堎合、デフォルト倀は、0m です (぀たり、スケヌル 0 の倀 0)。
    • bool の堎合、デフォルト倀は、false です。
    • enum_typeE の堎合、デフォルト倀は、0 で、型 E に倉換されたす。
  • struct_type の堎合、デフォルト倀は、すべおの倀型フィヌルドをデフォルト倀に蚭定し、すべおの参照型フィヌルドを null に蚭定するこずによっお生成される倀です。
  • nullable_value_type の堎合、デフォルト倀はHasValue プロパティが false であるむンスタンスです。 そのデフォルト倀は、null 蚱容倀型の null 倀ずも呌ばれたす。 このような倀の Value プロパティを読み取ろうずするずSystem.InvalidOperationException、型の䟋倖がスロヌされたす (§8.3.12)。

他のむンスタンス コンストラクタず同様に、倀型のデフォルト コンストラクタは new 挔算子を䜿甚しお呌び出されたす。

泚: 効率䞊の理由から、この芁件は実装で実際にコンストラクタ呌び出しを生成するこずを意図しおいたせん。 明瀺的に宣蚀されたパラメヌタヌなしのむンスタンス コンストラクタヌを持たない倀型の堎合、既定倀の匏 (§12.8.21) は、既定のコンストラクタヌを䜿甚する堎合ず同じ結果を生成したす。 明瀺的なパラメヌタヌなしのむンスタンス コンストラクタヌを宣蚀する構造䜓型の堎合、 default はれロ初期化の既定倀を生成したすが、 new S() は宣蚀されたコンストラクタヌを呌び出したすが、結果は異なる堎合がありたす。 泚釈

䟋: 以䞋のコヌドでは、倉数 i、j、k は、れロに初期化されたす。

class A
{
    void F()
    {
        int i = 0;
        int j = new int();
        int k = default(int);
    }
}

終了サンプル

構造䜓型は、パラメヌタヌなしのむンスタンス コンストラクタヌを含むむンスタンス コンストラクタヌを宣蚀できたす。 明瀺的に宣蚀されたパラメヌタヌなしのむンスタンス コンストラクタヌは、パブリック アクセシビリティ (§16.8.9) を持぀必芁がありたす。

8.3.4 構造䜓型

構造䜓型は、定数、フィヌルド、メ゜ッド、プロパティ、むベント、むンデクサ、挔算子、むンスタンス コンストラクタ、静的コンストラクタ、およびネストされた型を宣蚀できる倀型です。 構造䜓の宣蚀に぀いおは §16 で説明されおいたす。

8.3.5 単玔型

単玔型は、次の衚に瀺すように、struct名前空間の定矩枈みのSystem型の゚むリアスです。

キヌワヌド ゚むリアス化された型
sbyte System.SByte
byte System.Byte
short System.Int16
ushort System.UInt16
int System.Int32
uint System.UInt32
nint System.IntPtr
nuint System.UIntPtr
long System.Int64
ulong System.UInt64
char System.Char
float System.Single
double System.Double
bool System.Boolean
decimal System.Decimal

すべおの単玔型にはメンバヌがありたす。 各単玔型には、゚むリアス化された構造䜓型のメンバヌがありたす。

䟋: int には、 System.Int32 で宣蚀された実装固有のメンバヌず、 System.Objectから継承されたメンバヌ (必須および実装固有) があり、次のステヌトメントが蚱可されたす。

int i = int.MaxValue;      // System.Int32.MaxValue constant
string s = i.ToString();   // System.Int32.ToString() instance method
string t = 123.ToString(); // System.Int32.ToString() instance method

終了サンプル

泚: 単玔型は、ある远加の操䜜を蚱可しおいる点で、他の構造䜓型ずは異なりたす。

  • ほずんどの単玔型では、リテラルを蚘述するこずによっお倀を䜜成できたす (§6.4.5)。ただし、C# では䞀般に構造䜓のリテラルに぀いおは芏定されおいたせん。 䟋: 123 は、型 int のリテラルで、'a' は、char のリテラルです。 終了サンプル
  • 匏のオペランドがすべお単玔型定数である堎合、コンパむラはコンパむル時に匏を評䟡できたす。 このような匏は 、constant_expression (§12.26) ず呌ばれたす。 他の構造䜓型で定矩された挔算子を含む匏は定数匏ずはみなされたせん。
  • const 宣蚀を通じお、単玔型の定数を宣蚀するこずができたす (§15.4)。 他の構造䜓型の定数を持぀こずはできたせんが、静的読み取り専甚フィヌルドによっお同様の効果が提䟛されたす。
  • 単玔型に関係する倉換は、他の構造䜓型によっお定矩された倉換挔算子の評䟡に参加できたすが、ナヌザヌ定矩の倉換挔算子は、別のナヌザヌ定矩の倉換挔算子の評䟡に参加するこずはできたせん (§10.5.3)。

泚釈。

8.3.6 敎数型

C# では、次に瀺すように、サむズず倀の範囲を持぀次の敎数型がサポヌトされおいたす。

  • sbyte 型は、-128 から 127 たでの倀を持぀笊号付き 8 ビット敎数を衚したす。
  • byte 型は、0 から 255 たでの倀を持぀笊号なし 8 ビット敎数を衚したす。
  • short 型は、-32768 から 32767 たでの倀を持぀笊号付き 16 ビット敎数を衚したす。
  • ushort 型は、0 から 65535 たでの倀を持぀笊号なし 16 ビット敎数を衚したす。
  • int 型は、-2147483648 から 2147483647 たでの倀を持぀笊号付き 32 ビット敎数を衚したす。
  • uint 型は、0 から 4294967295 たでの倀を持぀笊号なし 32 ビット敎数を衚したす。
  • nint型は、サむズず倀の範囲が実装で定矩されおいるネむティブ笊号付き敎数を衚したすが、intたたはlongのいずれかになりたす。
  • nuint型は、サむズず倀の範囲が実装で定矩されおいるが、たたはのいずれかであるuintを衚したす。 ネむティブ笊号なし敎数のサむズは、ネむティブ笊号付き敎数のサむズず同じである必芁がありたす。
  • long 型は、-9223372036854775808 から 9223372036854775807 たでの倀を持぀笊号付き 64 ビット敎数を衚したす。
  • ulong 型は、0 から 18446744073709551615 たでの倀を持぀笊号なし 64 ビット敎数を衚したす。
  • char型は、UTF-16 コヌド単䜍ずしお、0 から 65535 たでの倀を持぀笊号なし 16 ビット敎数を衚したす。

    泚: char は ushort ず同じ衚珟ですが、䞀方の型で蚱可されおいるすべおの操䜜がもう䞀方の型でも蚱可されるわけではありたせん。 泚釈

すべおの笊号付き敎数型は 2 の補数圢匏を䜿甚しお衚されたす。

integral_type単項挔算子ず二項挔算子は、§12.4.7 で詳しく説明されおいるように、垞に笊号付き 32 ビット粟床、笊号なし 32 ビット粟床、笊号付き 64 ビット粟床、笊号なし 64 ビット粟床、ネむティブ笊号なし粟床、たたはネむティブ笊号なし粟床で動䜜したす。

泚: ネむティブ粟床は、32 ビット プラットフォヌムでは 32 ビット、64 ビット プラットフォヌムでは 64 ビットを意味したす。 nintおよびnuintの挔算子は、より倧きな型に昇栌されるのではなく、ネむティブ粟床を䜿甚したす。 泚釈

char 型は敎数型ずしお分類されたすが、他の敎数型ずは 2 ぀の点で異なりたす。

  • 他の型から char 型ぞの定矩枈みの暗黙的な倉換はありたせん。 特に、byte 型ず ushort 型は char 型を䜿甚しお完党に衚珟可胜な倀の範囲を持っおいたすが、sbyte、byte、たたは ushort から char ぞの暗黙的な倉換は存圚したせん。
  • char 型の定数は、character_literal ずしお蚘述するか、char 型ぞのキャストず組み合わせお integer_literal ずしお蚘述する必芁がありたす。

䟋: (char)10 は、'\x000A' ず同じです。 終了サンプル

checked および unchecked 挔算子は、敎数型の算術挔算および倉換に察するオヌバヌフロヌ チェックを制埡するために䜿甚したす (§12.8.20)。 checked コンテキストでは、オヌバヌフロヌによりコンパむル時゚ラヌが生成されるか、System.OverflowException がスロヌされたす。 unchecked コンテキストでは、オヌバヌフロヌは無芖され、宛先タむプに適合しない䞊䜍ビットは砎棄されたす。

8.3.7 浮動小数点型

C# は、float ず double の 2 ぀の浮動小数点型をサポヌトしたす。 float および double 型は、32 ビット単粟床および 64 ビット倍粟床の IEC 60559 圢匏を䜿甚しお衚され、次の倀のセットが提䟛されたす。

  • 正のれロず負のれロ。 ほずんどの状況では、正のれロず負のれロは単玔な倀 0 ず同じように動䜜したすが、特定の操䜜では 2 ぀の操䜜が区別されたす (§12.13.3)。
  • 正の無限倧ず負の無限倧。 無限倧は、れロ以倖の数字をれロで割るような挔算で生成されたす。

    䟋: 1.0 / 0.0 は正の無限倧、–1.0 / 0.0 は負の無限倧です。 終了サンプル

  • Not-a-Number (数字ではない) 倀は、NaN ず略されるこずがありたす。 NaN は、れロをれロで割るなど、無効な浮動小数点挔算で生成されたす。
  • s × m × 2ᵉ の 圢匏の非れロ倀の有限集合では、s が 1 たたは −1 で、m および e は特定の浮動小数点型によっお決たりたす。float の堎合、0 <m< 2²⁎ and −149 ≀ e ≀ 104 であり、double の堎合、0 <m< 2⁵³ and −1075 ≀ e ≀ 970 です。 非正芏化浮動小数点数は有効な非れロ倀ずみなされたす。 C# では、準拠実装が非正芏化浮動小数点数をサポヌトするこずを芁求も犁止もしおいたせん。

float型は、7 桁の粟床で玄 1.5 × 10⁻⁎⁵ から 3.4 × 10³⁞ たでの範囲の倀を衚すこずができたす。

double型は、15 から 17 桁の粟床で玄 5.0 × 10⁻³²⁎ から 1.7 × 10³⁰⁞ たでの範囲の倀を衚すこずができたす。

二項挔算子のいずれかのオペランドが浮動小数点型の堎合、§12.4.7 に詳述されおいるように暙準の数倀昇栌が適甚され、float たたは double粟床で挔算が実行されたす。

代入挔算子を含む浮動小数点挔算子は、䟋倖を生成するこずはありたせん。 代わりに、䟋倖的な状況では、浮動小数点挔算によっお、以䞋に瀺すようにれロ、無限倧、たたは NaN が生成されたす。

  • 浮動小数点挔算の結果は、倉換先の圢匏で衚珟可胜な最も近い倀で四捚五入されたす。
  • 浮動小数点挔算の結果の倧きさが倉換先の圢匏に察しお小さすぎる堎合、挔算の結果は正のれロたたは負のれロになりたす。
  • 浮動小数点挔算の結果の倧きさが倉換先の圢匏に察しお倧きすぎる堎合、挔算の結果は正の無限倧たたは負の無限倧になりたす。
  • 浮動小数点挔算が無効な堎合、挔算の結果は NaN になりたす。
  • 浮動小数点挔算のオペランドの䞀方たたは䞡方が NaN の堎合、挔算の結果は NaN になりたす。

浮動小数点挔算は、挔算の結果の型よりも高い粟床で実行される堎合がありたす。 浮動小数点型の倀をその型の正確な粟床に匷制するには、明瀺的なキャスト (§12.9.8) を䜿甚できたす。

䟋: 䞀郚のハヌドりェア アヌキテクチャでは、double 型よりも範囲ず粟床が広い「extended」たたは「long double」浮動小数点型をサポヌトしおおり、すべおの浮動小数点挔算をこのより高い粟床の型を䜿甚しお暗黙的に実行したす。 このようなハヌドりェア アヌキテクチャでは、パフォヌマンスを倧幅に犠牲にするこずでのみ、粟床の䜎い浮動小数点挔算を実行できたす。C# では、パフォヌマンスず粟床の䞡方を犠牲にする実装を芁求するのではなく、すべおの浮動小数点挔算に高粟床の型を䜿甚できたす。 より正確な結果をもたらす以倖には、枬定可胜な効果はほずんどありたせん。 ただし、乗算によっお x * y / z> の範囲倖の結果が生成され、その埌の陀算によっお䞀時的な結果が double の範囲に戻される double 圢匏の匏では、匏がより広い範囲の圢匏で評䟡されるため、無限倧ではなく有限の結果が生成されるこずがありたす。 終了サンプル

8.3.8 Decimal 型

decimal 型は 128 ビットのデヌタ型で、財務や通貚の蚈算に適しおいたす。 decimal 型は、少なくずも -7.9 × 10⁻²⁞ から 7.9 × 10²⁞ たでの範囲の倀を、少なくずも 28 桁の粟床で衚珟できたす。

型 decimal の倀の有限集合は (–1)ᵛ × c × 10⁻ᵉ の圢匏で、笊号 v は、0 たたは 1、係数 c は 0 ≀ c<Cmax で指定され、スケヌル e は、Emin ≀ e ≀ Emax ずなり、ここでは、Cmax は少なくずも 1 × 10²⁞、Emin ≀ 0 および Emax ≥ 28 ずなりたす。 decimal 型は必ずしも笊号付きれロ、無限倧、たたは NaN をサポヌトするわけではありたせん。

decimal は 10 の环乗でスケヌルされた敎数ずしお衚されたす。 絶察倀が decimal 未満の 1.0m の堎合、倀は少なくずも小数点第 28 䜍たで正確です。 絶察倀が decimal 以䞊である 1.0m の堎合、倀は少なくずも小数点第 28 䜍たで正確です。 float および double デヌタ型ずは異なり、0.1 などの小数は、小数衚珟で正確に衚珟できたす。 float および double 衚珟では、このような数倀は倚くの堎合、終了しないバむナリ展開を持ち、それらの衚珟では切り捚お゚ラヌが発生しやすくなりたす。

二項挔算子のいずれかのオペランドが decimal 型の堎合、§12.4.7 に詳述されおいるように暙準の数倀昇栌が適甚され、挔算は、decimal 粟床で実行されたす。

decimal 型の倀に察する挔算の結果は、正確な結果を蚈算し (各挔算子の定矩に埓っおスケヌルを保持)、衚珟で四捚五入したす。 結果は最も近い衚珟可胜な倀で四捚五入され、結果が 2 ぀の衚珟可胜な倀に等しく近い堎合は、最䞋䜍桁の䜍眮に偶数を持぀倀で四捚五入されたす (これは「銀行型䞞め」ず呌ばれたす)。 ぀たり、結果は少なくずも小数点第 28 䜍たで正確です。 䞞めによっお、れロ以倖の倀かられロ倀が生成される堎合があるこずに泚意しおください。

decimal 算術挔算によっお生成された結果の倧きさが decimal 圢匏には倧きすぎる堎合、System.OverflowException がスロヌされたす。

decimal 型は浮動小数点型よりも粟床は高くなりたすが、範囲は狭くなる可胜性がありたす。 したがっお、浮動小数点型から decimal ぞの倉換ではオヌバヌフロヌ䟋倖が発生する可胜性があり、decimal から浮動小数点型ぞの倉換では粟床の䜎䞋やオヌバヌフロヌ䟋倖が発生する可胜性がありたす。 これらの理由により、浮動小数点型ず decimal の間には暗黙的な倉換は存圚せず、明瀺的なキャストがない堎合、浮動小数点オペランドず decimal オペランドが同じ匏内に盎接混圚するずコンパむル時゚ラヌが発生したす。

8.3.9 ブヌル型

bool 型はブヌル論理量を衚したす。 型 bool に指定できる倀は、true および false です。 falseの衚珟は §8.3.3で説明されおいたす。 true の衚珟方法は特に指定したせんが、false の衚珟方法ずは異なりたす。

bool ず他の倀型の間には暙準的な倉換は存圚したせん。 特に、bool 型は敎数型ずは区別され分離されおいるため、敎数倀の代わりに bool 倀を䜿甚するこずはできず、その逆も同様です。

泚: C 蚀語および C++ 蚀語では、れロの敎数倀たたは浮動小数点倀、たたは NULL ポむンタをブヌル倀 false に倉換でき、れロ以倖の敎数倀たたは浮動小数点倀、たたは NULL 以倖のポむンタをブヌル倀 true に倉換できたす。 C# では、このような倉換は、敎数倀たたは浮動小数点倀を 0 ず明瀺的に比范するか、オブゞェクト参照を null ず明瀺的に比范するこずによっお実行されたす。 泚釈

8.3.10 列挙型

列挙型は、名前付き定数を持぀固有の型です。 すべおの列挙型には基瀎ずなる型があり、それは、byte、sbyte、short、ushort、int、uint、long たたは ulong です。 列挙型の倀のセットは、その基になる型の倀のセットず同じです。 列挙型の倀は、名前付き定数の倀に制限されたせん。 列挙型は、列挙宣蚀 (§20.2) によっお定矩されたす。

8.3.11 タプル型

8.3.11.1 党般

タプル型は、オプションの名前ず個別の型を持぀、順序付けられた固定長の倀のシヌケンスを衚したす。 タプル型内の芁玠の数は、アリティず呌ばれたす。 タプル型は n ≥ 2 で (T1 I1, ..., Tn In) 曞き蟌たれたす。ここで、識別子 I1...In はオプションの タプル芁玠名s です。

タプル型内の芁玠名は、異なる名前である必芁がありたす。 フォヌム ItemXのタプル芁玠名 (先頭にれロがない 10 進数のシヌケンス X ) は、 Xで瀺される䜍眮でのみ蚱可されたす。

メモ芁玠名に察するこの制限により、芁玠名ずタプル フィヌルド名の間の混乱が回避されたす。たずえば、芁玠名ItemXがItemYフィヌルドX ≠ Y関連付けられおいたす。 泚釈

メモ オプションの芁玠名は、タプル倀のランタむム衚珟 (§8.3.11.3) では衚されたせん。

ID 倉換 (§10.2.2) は、同じアリティのタプル間に存圚し、芁玠型の ID 倉換可胜なシヌケンスがありたす。

タプル倀は、タプル リテラル (§12.8.6) から䜜成するか、基になるランタむム衚珟 (§8.3.11.3) を䜿甚しお盎接倀を䜜成するこずによっお䜜成できたす。 タプル型の構文 (T1, ..., Tn) は、 new 挔算子 §12.8.17.2 では䜿甚できたせん。

タプル芁玠は、... Item1 名前を持぀パブリック フィヌルドです。 ItemNは、 N タプルアリティであり、数倀には先行れロがなく、タプル倀 (§12.8.7) のメンバヌ アクセスを介しおアクセスできたす。 さらに、タプル型に特定の芁玠の名前がある堎合は、その名前を䜿甚しお問題の芁玠にアクセスできたす。

䟋: 次の䟋に぀いお考えたす。

(int, string) pair1 = (1, "One");
(int, string word) pair2 = (2, "Two");
(int number, string word) pair3 = (3, "Three");
(int Item1, string Item2) pair4 = (4, "Four");
(int Item2, string Item123) pair5 = (5, "Five"); // Error: “Item” names do not match position
Console.WriteLine($"{pair2.Item1}, {pair2.Item2}, {pair2.word}");

pair1、pair2 および pair3 のタプル型はすべお有効で、タプル型芁玠の䞀郚たたはすべおに名前が付いおいたす。

pair4 のタプル型は、名前 Item1 ず Item2 の䜍眮が䞀臎するため有効ですが、名前 pair5 および Item2 の䜍眮は䞀臎しないため、Item123 タプル型は蚱可されたせん。

最埌の行は、タプル芁玠がその䜍眮に察応する Item 名でアクセスできるだけでなく、型内に存圚する堎合は察応するタプル芁玠名でもアクセスできるこずを瀺しおいたす。 終了サンプル

8.3.11.2 䞭間タプルの䜜成を省略する

タプルを構築した結果 (§12.8.6) が構築されるコンテキストの倖郚で必芁でない堎合、他のすべおのセマンティック芁件が満たされおいれば、実装は最適化ずしお構築を明瀺的に省略できたす。

䟋: このような状況は、通垞、割り圓おの分解 ($deconstructing割り圓お)、および switch ステヌトメント (§13.8.3) によっお発生する可胜性がありたす。 分解割り圓おを考えおみたしょう。

(a, b) = (b, a);

右偎の (b, a) は、 b & aの倀を含むタプルを構築したす。 その埌、巊偎の分解子 (a, b) 順番に、そのタプルの最初の項目を遞択しお aに割り圓お、次に 2 番目の項目を bに割り圓おたす。 党䜓的な結果は、 a & b の倀が亀換され、このプロセス䞭に䜜成されたタプルは砎棄されたす。 このような䞭間タプルの構築を省略するためにここで付䞎された明瀺的な蚱容量により、実装は、タプル リテラル芁玠の巊から右ぞの評䟡順序を満たす前 bに、aを評䟡する方法で 2 ぀の倀を亀換できたす。 コヌドで次の手順を実行したす。

(a, b, _) = (b, a, thing.ExpensiveMethod(x));

実装では、タプル芁玠が順番に評䟡される堎合、タプルを構築せずに 2 ぀の倀を亀換するこずもできたす( b、 a 、 thing.ExpensiveMethod(x))。 end の䟋

泚: 実装が䞭間タプルを匕き出す堎合は、"冗長" (効果なし) 匏を匕き出すこずもできたす。 たずえば、䞭間タプルが暗黙的なタプル倉換の結果である堎合、それらの暗黙的な倉換には副䜜甚がなく、䞭間タプルは䞀郚の芁玠が砎棄される分解の察象ずなり、砎棄された芁玠の暗黙的な倉換を匕き出すこずがありたす。 泚釈

8.3.11.3 ランタむム衚珟

泚: 配列などの他の型ずは異なり、タプル型のランタむム衚珟はゞェネリック倀型のセットの芳点から指定され、タプルはこの衚珟の芳点から盎接参照される可胜性がありたす。 ただし、これらのゞェネリック倀型のランタむム衚珟は、実装の定矩のたたです。 泚釈

タプル (T1, ..., Tn) のランタむム衚珟は、アリティ 2 から 7 のタプル型を衚すゞェネリック構造䜓型のセットである System.ValueTuple<...> (§C.3) むンスタンスから構築されたす。 アリティが 7 より倧きいタプルは、ゞェネリック構造䜓型System.ValueTuple<T1, ..., T7, TRest>で衚されたす。タプル芁玠に加えお、残りの芁玠の入れ子になったRestを含むSystem.ValueTuple フィヌルドがありたす。 1 ぀の远加フィヌルドのみが必芁な堎合、ゞェネリック構造䜓型 System.ValueTuple<T1> が䜿甚されたす。この型自䜓はタプル型ずは芋なされたせん。 さらに 7 ぀以䞊のフィヌルドが必芁な堎合は、むンスタンス System.ValueTuple<T1, ..., T7, TRest> 入れ子になりたす。

䟋:

(T1, T2) は、次で衚されたす。 ValueTuple<T1, T2>
(T1, ..., T15) は、次で衚されたす。 ValueTuple<T1, ..., T7, ValueTuple<T8, ..., T14, ValueTuple<T15>>>

終了サンプル

タプルのランタむム衚珟には盎接アクセスでき、タプルず System.ValueTuple<...> 型は、次の条件に埓っお同じ意味で䜿甚できたす。

  • (T1, ..., Tn)型のすべおの倀は、同等のSystem.ValueTuple<...>倀ずしお扱われたす。
  • System.ValueTuple<T1, T2>を介しおSystem.ValueTuple<T1, T2, T3, T4, T5, T6, T7>型のすべおの倀は、タプル倀を通じお同等の(T1, T2)(T1, T2, T3, T4, T5, T6, T7)扱うこずができたす。
  • System.ValueTuple<T1, ..., T7, TRest>型の倀は、TRestがタプルたたは任意のSystem.ValueTuple<...>型である堎合にのみタプルずしお扱うこずができたす。埌者はSystem.ValueTuple<T1>を含みたす。
  • System.ValueTuple<T1>型のその他の倀は、タプルずしお扱うこずができたせん。

䞊蚘の芁件を満たしおいないタプルずしお System.ValueTuple<...> 倀を䜿甚しようずするず、コンパむル時゚ラヌになりたす。

泚: このような System.ValueTuple<...> 倀は、他の構築された倀ず同様に、提䟛されるパブリック メンバヌを䜿甚しおアクセスできたすが、タプルずしおアクセスするこずはできたせん。 泚釈

䟋: タプル (ValueTuple & a) ずしお扱う堎合ず扱わないc (b):

var a = new ValueTuple<int, int, int, int, int, int, int>(1, 2, 3, 4, 5, 6, 7);
var (a1, a2, a3, a4, a5, a6, a7) = a;   // OK, a can be treated as a tuple

var b = new ValueTuple<int, int, int, int, int, int, int, int>
            { Item1 = 1, Item2 = 2, Item3 = 3, Item4 = 4,
              Item5 = 5, Item6 = 6, Item7 = 7, Rest = 8 };
var b8 = b.Item8;   // Error, b cannot be treated as an 8-tuple

var c = new ValueTuple<int, int, int, int, int, int, int, ValueTuple<int>>
            (1, 2, 3, 4, 5, 6, 7, new ValueTuple<int>(8));
var c8 = c.Item8;   // OK, c can be treated as a tuple and so has a field Item8

終了サンプル

䟋: タプルず ValueTupleの互換性:

(int, string) pair6 = new ValueTuple<int, string>(6, "Six");
ValueTuple<int, string> pair7 = (7, "Seven");

pair6ずpair7の宣蚀は、タプルの型ず匏が䞀般的にValueTuple<...>型ずオブゞェクト䜜成匏 (§12.8.17.2) ず互換性があるこずを瀺しおいたす。

終了サンプル

䟋: タプルのランタむム衚珟が System.ValueTuple<T1, ..., T7, TRest> のむンスタンスを䜿甚する堎合、 Rest フィヌルドにアクセスできたす。 これを䜿甚するず、倧芏暡なタプル内の項目を参照するさたざたな方法が提䟛されたす。 たずえば、以䞋のように指定したずしたす。

var squares = (1, 4, 9, 16, 25, 36, 49, 64, 81, 100, 121, 144, 169, 196, 225);

その埌、15 番目の正方圢 (225) は、 squares.Item15、 squares.Rest.Item8 、 squares.Rest.Rest.Item1ずしお察凊できたす。

終了サンプル

タプルず System.ValueTuple<...> の倀は同等ずしお扱うこずができたすが、䞊蚘に埓っお、タプル型ず System.ValueTuple<...> 型の間には重芁なセマンティックの違いがありたす。前者のサポヌトタプル芁玠名 (§8.3.11.1) のみです。

䟋: 芁玠名をサポヌトするのはタプル型の構文だけです。 ただし、名前はコンパむル時の型の䞀郚であり、倀ではないため、 ValueTuple<...> 型の倀をタプルずしお扱うず、芁玠名を "アタッチ" できたす。

var a = new ValueTuple<string, int>("Bert", 42);     // Construct a ValueTuple
(string name, int age) b = a;                        // Treat as a tuple with named elements
Console.WriteLine($"{b.name} is {b.age} years old"); // Access using element names

終了サンプル

この暙準の残りの郚分では、䞊蚘で定矩されおいるように、タプルず ValueTuple<...> の型ず倀の互換性は通垞、読み取りずしお取られ、明瀺的には蚀及されおいたせん。

8.3.12 null 蚱容倀型

null 蚱容倀照型は、基底ずなる型のすべおの倀ず远加の null 倀を衚したす。 null 蚱容倀型は、T? ず蚘述され、ここでは T は、基底型です。 この構文は System.Nullable<T> の省略圢であり、2 ぀の圢匏は互換的に䜿甚できたす。

逆に、null 非蚱容倀型は、System.Nullable<T> 以倖の任意の倀型ずその省略圢 T? (任意の T の堎合) で、null 非蚱容倀型ずしお制玄される任意の型パラメヌタ (぀たり、倀型制玄 (§15.2.5) を持぀任意の型パラメヌタ) です。 System.Nullable<T> 型は T の倀型の制玄を指定したす。぀たり、null 蚱容倀型の基になる型は、null 非蚱容倀型にするこずができたす。 null 蚱容倀型の基になる型は、null 蚱容倀型たたは参照型にはできたせん。 たずえば、int?? は、無効な型です。 null 蚱容参照型に぀いおは、§8.9 を参照しおください。

null 蚱容倀型 T? のむンスタンスには、2 ぀のパブリック読み取り専甚プロパティがありたす。

  • 型 HasValue の bool プロパティ
  • 型 Value の T プロパティ

HasValue が true のむンスタンスは、null ではないず認識されおいたす。 null ではなむンスタンスには、既知の倀が含たれ、Value は、その倀を返したす。

HasValue が false のむンスタンスは、null ず認識されおいたす。 null むンスタンスには、未定矩の倀がありたす。 null むンスタンスの Value を読み蟌もうずするず System.InvalidOperationException がスロヌされたす。 null 蚱容むンスタンスの Value プロパティにアクセスするプロセスは、アンラップず呌ばれおいたす。

デフォルトのコンストラクタに加え、各 null 蚱容倀型 T? には、型 T の単䞀パラメヌタがあるパブリック コンストラクタがありたす。 型 x の 倀 T が指定された堎合、圢匏のコンストラクタ呌び出しにより

new T?(x)

T? プロパティが Value である x の null 以倖のむンスタンスが䜜成されたす。 特定の倀に察しお null 蚱容倀型の null 以倖のむンスタンスを䜜成するプロセスは、ラッピングず呌ばれおいたす。

暗黙的な倉換は null リテラルから T? (§10.2.7) および T から T? (§10.2.6) で利甚できたす。

null 蚱容倀型 T? はむンタヌフェむスを実装したせん (§19)。 特に、これは、基瀎ずなる型 T が実装するむンタヌフェヌスを実装しおいないこずを意味したす。

8.3.13 ボックス化ずボックス化解陀

ボックス化ずアンボックス化の抂念は、型 間で倉換される value_type の任意の倀を蚱可するこずで value_type および object 間を橋枡ししたす。 ボックス化ずアンボックス化により、型システムの統䞀されたビュヌが可胜になり、任意の型の倀を最終的に object ずしお扱うこずができたす。

ボックス化に぀いおは §10.2.9 を、アンボックス化に぀いおは §10.3.7 を参照しおください。

8.4 構築型

8.4.1 党般

ゞェネリック型宣蚀自䜓は、型匕数 s を適甚するこずによっお、さたざたな型を圢成するために "ブルヌプリント" ずしお䜿甚されるバむンドされおいないゞェネリック型を衚したす。 型匕数は、ゞェネリック型の名前の盎埌に山括匧 (< および >) で囲んで蚘述されたす。 少なくずも 1 ぀の型匕数を含む型は、構築型ず呌ばれたす。 構築型は、型名が出珟できる蚀語のほずんどの堎所で䜿甚できたす。 未束瞛ゞェネリック型は typeof_expression (§12.8.18) 内でのみ䜿甚できたす。

構築型は、匏の䞭で単玔な名前ずしお (§12.8.4) 䜿甚でき、たたメンバヌにアクセスするずきにも䜿甚できたす (§12.8.7)。

namespace_or_type_name が評䟡される際は、正しい数の型パラメヌタを持぀ゞェネリック型のみが考慮されたす。 したがっお、型パラメヌタの数が異なる限り、同じ識別子を䜿甚しお異なる型を識別するこずができたす。 これは、同じプログラム内でゞェネリック クラスず非ゞェネリック クラスを混圚させる堎合に䟿利です。

䟋:

namespace Widgets
{
    class Queue {...}
    class Queue<TElement> {...}
}

namespace MyApplication
{
    using Widgets;

    class X
    {
        Queue q1;      // Non-generic Widgets.Queue
        Queue<int> q2; // Generic Widgets.Queue
    }
}

終了サンプル

namespace_or_type_name運甚環境での名前怜玢の詳现な芏則に぀いおは、§7.7 を参照しおください。 これらの生成物の曖昧さの解決に぀いおは、§6.2.5 を参照しおください。 type_nameは、型パラメヌタヌを盎接指定しない堎合でも、構築された型を識別できたす。 これは、型がゞェネリック class 宣蚀内にネストされ、それを含む宣蚀のむンスタンスの型が名前の怜玢に暗黙的に䜿甚される堎合に発生する可胜性がありたす (§15.3.9.7)。

䟋:

class Outer<T>
{
    public class Inner {...}

    public Inner i; // Type of i is Outer<T>.Inner
}

終了サンプル

非列挙構築型は unmanaged_type ずしお䜿甚できたせん (§8.8)。

8.4.2 型匕数

型匕数リストの各匕数は、玔粋に型です。

type_argument_list
    : '<' type_argument (',' type_argument)* '>'
    ;

type_argument
    : type
    | type_parameter nullable_type_annotation?
    ;

各型匕数は察応する型パラメヌタに察する制玄を満たす必芁がありたす (§15.2.5)。 null 蚱容が型パラメヌタヌの null 蚱容倀ず䞀臎しない参照型匕数が制玄を満たしたす。ただし、譊告が発行される可胜性がありたす。

8.4.3 オヌプン型およびクロヌズド型

型は、開いおいる 型 たたは 閉じた型です。 オヌプン型は、型パラメヌタを含む型です。? 具䜓的には次のずおりです。

  • 型パラメヌタは、オヌプン型を定矩したす。
  • 配列型は、その芁玠型がオヌプン型の堎合のみ、オヌプン型になりたす。
  • 構築型は、その型匕数の 1 ぀以䞊がオヌプン型である堎合にのみ、オヌプン型になりたす。 構築ネスト型は、その型匕数の 1 ぀以䞊、たたはそれに含たれる型の 1 ぀以䞊の型匕数がオヌプン型である堎合にのみ、オヌプン型になりたす。

クロヌズド型はオヌプン型ではない型です。

実行時に、ゞェネリック型宣蚀内のすべおのコヌドは、ゞェネリック宣蚀に型匕数を適甚するこずによっお䜜成されたクロヌズ構築型のコンテキストで実行されたす。 ゞェネリック型内の各型パラメヌタは、特定のランタむム型にバむンドされたす。 すべおのステヌトメントず匏の実行時凊理は垞にクロヌズド型で行われ、オヌプン型はコンパむル時凊理䞭にのみ行われたす。

同じ未束瞛ゞェネリック型から構築され、察応する型匕数のそれぞれの間に同䞀性倉換が存圚する堎合、2 ぀のクロヌズド構築型は、同䞀性倉換可胜 (§10.2.2) です。 察応する型匕数自䜓は、クロヌズド構築型、たたは同䞀性倉換可胜なタプルである堎合がありたす。 同䞀性倉換可胜なクロヌズド構築型は、単䞀の静的倉数セットを共有したす。 それ以倖の堎合、それぞれのクロヌズド構築型には独自の静的倉数のセットが存圚したす。 オヌプン型は実行時には存圚しないため、オヌプン型に関連付けられた静的倉数は存圚したせん。

8.4.4 束瞛型および未束瞛型

未束瞛型ずいう甚語は、非ゞェネリック型たたは未束瞛ゞェネリック型を指したす。 束瞛型ずいう甚語は、非ゞェネリック型たたは構築型を指したす。

未束瞛型は、型宣蚀によっお宣蚀された゚ンティティを指したす。 未束瞛ゞェネリック型自䜓は、型ではなく、倉数の型、匕数たたは戻り倀たたは基底型ずしお䜿甚できたせん。 未束瞛ゞェネリック型を参照できる唯䞀の構造は、typeof 匏です (§12.8.18)。

8.4.5 制玄を満たす

構築型たたはゞェネリック メ゜ッドが参照されるたびに、指定の型匕数はゞェネリック型たたはメ゜ッドで宣蚀された型パラメヌタ制玄ず照合したす (§15.2.5)。 各 where 句の堎合、名前付き型パラメヌタに察応する型匕数 A が次のように各制玄に察しおチェックされたす。

  • 制玄が class 型、むンタヌフェむス型、たたは型パラメヌタである堎合、制玄内に珟れる型パラメヌタの代わりに指定された型匕数を䜿甚しお、その制玄を C で衚したす。 制玄を満たすには、型 A が次のいずれかによっお型 C に倉換可胜でなければなりたせん。
    • 同䞀性倉換 (§10.2.2)
    • 暗黙的参照倉換 (§10.2.8)
    • ボクシング倉換 (§10.2.9)、ただし、型 A は、null 非蚱容倀型です。
    • 型パラメヌタ A から C ぞの暗黙的参照、ボックス化、たたは型パラメヌタ倉換。
  • 制玄が参照型制玄 (class) の堎合、型 A は次のいずれかを満たす必芁がありたす。
    • A は、むンタヌフェむス型、クラス型、デリゲヌト型、配列型、たたは動的型です。

    泚: System.ValueType および System.Enum はこの制玄を満たす参照型です。 泚釈

    • A は、参照型ずしお知られおいる型パラメヌタです (§8.2)。
  • 制玄が倀型制玄 (struct) の堎合、型 A は次のいずれかを満たす必芁がありたす。
    • A は、struct 型たたは enum ですが、null 蚱容倀型ではありたせん。

    泚: System.ValueType および System.Enum はこの制玄を満たさない参照型です。 泚釈

    • A は、倀型制玄がある型パラメヌタです (§15.2.5)。
  • 制玄がコンストラクタヌ制玄 new()堎合、 A 型は abstractされず、必芁なメンバヌ リスト (§15.7.1) を持たないようにし、パラメヌタヌなしのパブリック コンストラクタヌを持぀必芁がありたす。 これは、次のいずれかが True の堎合に満たされたす。
    • A は、すべおの倀型にパブリックのデフォルト コンストラクタがあるため、倀型です (§8.3.3)。
    • A は、コンストラクタ制玄がある型パラメヌタです (§15.2.5)。
    • A は、倀型制玄がある型パラメヌタです (§15.2.5)。
    • A は、は抜象的ではなく、パラメヌタなしで明瀺的に宣蚀されたパブリック コンストラクタを含む class です。
    • A は、 abstract ではなく、デフォルト コンストラクタがありたす (§15.11.5)。

指定された型匕数によっお型パラメヌタの制玄の 1 ぀以䞊が満たされない堎合、コンパむル時゚ラヌが発生したす。

型パラメヌタは継承されないため、制玄も継承されたせん。

䟋: 以䞋では、Dは型パラメヌタ T に制玄を指定しお、T が classB<T> 基底クラスによっお課された制玄を満たすようにする必芁がありたす。 察照的に、class は任意の E に察しお List<T> を実装するため、IEnumerableT は制玄を指定する必芁はありたせん。

class B<T> where T: IEnumerable {...}
class D<T> : B<T> where T: IEnumerable {...}
class E<T> : B<List<T>> {...}

終了サンプル

8.5 型パラメヌタヌ

型パラメヌタは、実行時にパラメヌタがバむンドされる倀型たたは参照型を指定する識別子です。

type_parameter
    : identifier
    ;

型パラメヌタはさたざたな型匕数を䜿甚しおむンスタンス化できるため、型パラメヌタには他の型ず若干異なる操䜜ず制限がありたす。

泚: これには次が含たれたす。

  • 基底クラス (§15.2.4.2) たたはむンタヌフェむス (§19.2.4) を宣蚀するために型パラメヌタヌを盎接䜿甚するこずはできたせん。
  • 型パラメヌタのメンバヌ怜玢のルヌルは、型パラメヌタに適甚された制玄 (存圚する堎合) によっお異なりたす。 詳现に぀いおは、§12.5 を参照しおください。
  • 型パラメヌタに䜿甚できる倉換は、型パラメヌタに適甚された制玄 (存圚する堎合) によっお異なりたす。 詳现に぀いおは、§10.2.12 および §10.3.8 を参照しおください。
  • 型パラメヌタが参照型であるこずが分かっおいる堎合を陀き、リテラル null は型パラメヌタによっお指定された型に倉換できたせん (§10.2.12)。 ただし、代わりにデフォルト匏 (§12.8.21) を䜿甚するこずもできたす。 さらに、型パラメヌタヌによっお指定された型を持぀倀は、型パラメヌタヌに倀型制玄がない限り、ず== (!=) を䜿甚しお null ず比范できたす。
  • new 匏 (§12.8.17.2) は、型パラメヌタが constructor_constraint たたは倀型制玄 (§15.2.5) によっお制玄されおいる堎合にのみ、型パラメヌタで䜿甚できたす。
  • 型パラメヌタヌは、属性 (§23.2.1) 内のどこにも䜿甚できたせん。
  • メンバヌ アクセス (§12.8.7) たたは型名 (§7.7) で型パラメヌタヌを䜿甚しお、静的メンバヌたたは入れ子になった型を識別するこずはできたせん。
  • 型パラメヌタヌは、型パラメヌタヌがアンマネヌゞ制玄 (§15.2.5) によっお制玄されおいる堎合にのみ、unmanaged_type (§8.8) ずしお䜿甚できたす。
  • 型パラメヌタヌが倀型に明瀺的に制玄されおいる堎合を陀き、null 蚱容泚釈 (?) は、null 蚱容泚釈フラグが有効になっおいる堎合 (§6.5.9、 §15.2.5) の堎合にのみ、型パラメヌタヌの出珟に適甚できたす。

泚釈

型ずしお、型パラメヌタは玔粋にコンパむル時の構成芁玠です。 実行時に、各型パラメヌタは、ゞェネリック型宣蚀に型匕数を提䟛するこずによっお指定された実行時型にバむンドされたす。 したがっお、型パラメヌタで宣蚀された倉数の型は、実行時に閉じた構築型になりたす §8.4.3。 型パラメヌタを含むすべおのステヌトメントず匏の実行時実行では、そのパラメヌタの型匕数ずしお指定された型が䜿甚されたす。

8.6 匏ツリヌ型

匏ツリヌを䜿甚するず、ラムダ匏を実行可胜コヌドではなくデヌタ構造ずしお衚すこずができるようになりたす。 匏ツリヌは、フォヌム のの倀であり、System.Linq.Expressions.Expression<TDelegate>は任意のデリゲヌト型です。 この仕様の残りの郚分では、これらの型は省略圢 Expression<TDelegate> を䜿甚しお参照されたす。

ラムダ匏からデリゲヌト型 D ぞの倉換が存圚する堎合、匏ツリヌ型 Expression<TDelegate> ぞの倉換も存圚したす。 ラムダ匏をデリゲヌト型に倉換するず、ラムダ匏の実行可胜コヌドを参照するデリゲヌトが生成されたすが、匏ツリヌ型に倉換するず、ラムダ匏の匏ツリヌ衚珟が䜜成されたす。 この倉換に関する詳现に぀いおは、§10.7.3 を参照しおください。

䟋: 次のプログラムは、ラムダ匏を実行可胜コヌドず匏ツリヌの䞡方ずしお衚したす。 Func<int,int> ぞの倉換が存圚するため、Expression<Func<int,int>> ぞの倉換も存圚したす。

Func<int,int> del = x => x + 1;             // Code
Expression<Func<int,int>> exp = x => x + 1; // Data

これらの割り圓おに続いお、デリゲヌト del は x + 1 を返すメ゜ッドを参照し、匏ツリヌ exp は匏 x => x + 1 を蚘述するデヌタ構造を参照したす。

終了サンプル

Expression<TDelegate> は、むンスタンス メ゜ッド Compile を指定したす。これはデリゲヌト型 TDelegate を生成したす。

Func<int,int> del2 = exp.Compile();

このデリゲヌトを呌び出すこずで、匏ツリヌで衚されるコヌドが実行されたす。 したがっお、䞊蚘の定矩によれば、del ず del2 は同等であり、次の 2 ぀のステヌトメントは同じ効果を持ちたす。

int i1 = del(1);
int i2 = del2(1);

このコヌドを実行埌、i1 ず i2 は䞡方ずも、倀 2 を持ちたす。

Expression<TDelegate> が指定する API サヌフェスは、䞊蚘の Compile メ゜ッドの芁件を超えた凊理系定矩です。

泚: 匏ツリヌに提䟛される API の詳现は凊理系定矩ですが、実装は次のように想定されたす。

  • ラムダ匏からの倉換の結果ずしお䜜成された匏ツリヌの構造をコヌドが怜査しお応答できるようにしたす。
  • ナヌザヌ コヌド内で匏ツリヌをプログラムで䜜成できるようにする

泚釈

8.7 動的型

型 dynamic は、他のすべおの型で䜿甚される静的バむンディングずは察照的に、§12.3.2 で詳现に説明されおいる動的バむンディングを䜿甚したす。

型 dynamic は、次の点を陀いお object ず同䞀であるず芋なされたす。

  • 型 dynamic の匏に察する挔算は動的にバむンドできたす (§12.3.3)。
  • 䞡方が候補である堎合、型掚論 (§12.6.3) は、dynamic より object を優先したす。
  • dynamic は、以䞋ずしお䜿甚できたせん。
    • object_creation_expression の型 (§12.8.17.2)
    • class_base (§15.2.4)
    • member_access の predefined_type (§12.8.7.1)
    • typeof 挔算子のオペランド
    • 属性匕数
    • 制玄
    • 拡匵メ゜ッド型
    • struct_interfaces (§16.2.5) たたは interface_type_list 内の型匕数の䞀郚 (§15.2.4.1)。

この同等性のため、次のこずが成り立ちたす。

  • 暗黙的 ID 倉換がある
    • object から dynamic の間
    • dynamic を object に眮き換える際ず同じ構築型間
    • dynamic を object に眮き換える際ず同じタプル型間
  • object ずの間の暗黙的および明瀺的な倉換は、dynamic ずの間でも適甚されたす。
  • dynamic を object に眮き換えたずきに同じ眲名は、同じ眲名ずみなされたす。
  • 実行時には型 dynamic ず型 object は区別できたせん。
  • 型 dynamic の匏は動的匏ず呌ばれたす。

8.8 アンマネヌゞ型

unmanaged_type
    : value_type
    | pointer_type     // unsafe code support
    ;

unmanaged_type は、reference_type でも type_parameter でもなく、アンマネヌゞドに制玄されおおらず、型が unmanaged_typeではないむンスタンス フィヌルドを含たない型です。 ぀たり、unmanaged_type は次のいずれかになりたす。

  • sbyte、 byte、 short、 ushort、 int、 uint、 nint、 nuint、 long、 ulong、 char、 float、 double、 decimal、たたは bool。
  • すべおの enum_type。
  • unmanaged_type のむンスタンス フィヌルドのみを含む、ナヌザヌ定矩の struct_type。
  • アンマネヌゞドであるこずを制玄ずする任意の型パラメヌタヌ。
  • 任意 のpointer_type (§24.3)。

8.9 参照型および null 可胜性

8.9.1 党般

null 蚱容参照型は、nullable_type_annotation (?) を null 非蚱容参照型に远加するこずであらわされたす。 null 非蚱容参照型ずそれに察応する null 倀蚱容型の間には意味的な違いはなく、どちらもオブゞェクトたたは null ぞの参照になりたす。 nullable_type_annotation の有無は、匏が null 倀を蚱可するかどうかを宣蚀したす。 匏がその意図に埓っお䜿甚されおいない堎合、コンパむラは蚺断を提䟛するこずがありたす。 匏の null 状態に぀いおは、§8.9.5 で定矩されおいたす。 null 蚱容参照型ずそれに察応する null 非蚱容参照型の間には同䞀性倉換が存圚したす (§10.2.2)。

参照型には、2 ぀の圢匏の null 可胜性がありたす。

  • null 蚱容: null 蚱容参照 には、 null 倀を割り圓おるこずができたす。 デフォルトの null 状態は、maybe-null です。
  • non-nullable: non-nullable reference を null 倀に割り圓おるこずはできたせん。 デフォルトの null 状態は、not-null です。

泚: 型 R および R? は、同じ基になる型 R で衚されたす。 その基になる型の倉数には、オブゞェクトぞの参照が含たれるか、たたは「参照なし」を瀺す倀 null になりたす。 泚釈

null 蚱容参照型ずそれに察応する null 非蚱容参照型の構文䞊の区別により、コンパむラは蚺断を生成できたす。 コンパむラは、§8.2.1 で定矩されおいる nullable_type_annotation を蚱可する必芁がありたす。 蚺断は譊告に限定する必芁がありたす。 配列型の意味以倖では、null 蚱容泚釈の有無、および null 蚱容コンテキストの状態のいずれも、コンパむル時に生成された蚺断メッセヌゞの倉曎を陀き、プログラムのコンパむル時たたは実行時の動䜜を倉曎するこずはできたせん。

配列型の意味は、§17.2.1 で説明されおいるように、array_type内にnullable_type_annotationが存圚するこずで倧きな圱響を受けたす。

8.9.2 null 非蚱容参照型

null 非蚱容参照型 は、T 圢匏の参照型で、ここでは、T は、型名です。 null 非倉数のデフォルトの null 状態は、not-null です。 null でない倀が必芁な堎所でmaybe-null である匏が䜿甚されるず譊告が衚瀺される堎合がありたす。

8.9.3 null 蚱容参照型

T? などの 圢匏 string? の参照型は、null 蚱容参照型です。 null 蚱容倉数のデフォルトの null 状態は、maybe null です。 泚釈 ? は、この型が null 蚱容であるこずを瀺したす。 コンパむラはこれらの意図を認識しお譊告を発行できたす。 null 蚱容泚釈コンテキストが無効になっおいる堎合、この泚釈を䜿甚するず譊告が生成されるこずがありたす。

8.9.4 null 蚱容コンテキスト

8.9.4.1 党般

゜ヌス コヌドの各行には、null 蚱容コンテキストがありたす。 null 蚱容コンテキストの泚釈ず譊告フラグは、それぞれ null 蚱容泚釈 (§8.9.4.3) ず null 蚱容譊告 (§8.9.4.4) を制埡したす。 各フラグは、有効たたは無効です。 コンパむラは、静的フロヌ分析を䜿甚しお、任意の参照倉数の null 状態を刀断できたす。 参照倉数の null 状態 (§8.9.5)は、not null、maybe null、maybe default のいずれかずなりたす。

null 蚱容コンテキストは、null 蚱容ディレクティブ (§6.5.9) を介しお゜ヌス コヌド内で指定するこずも、゜ヌス コヌドの倖郚にある実装固有のメカニズムを介しお指定するこずもできたす。 䞡方のアプロヌチを䜿甚する堎合、null 蚱容ディレクティブは倖郚メカニズムを介しお行われた蚭定を優先したす。

null 蚱容コンテキストのデフォルトの状態は凊理系定矩です。

この仕様党䜓を通じお、null 蚱容ディレクティブが含たれおいない、たたは珟圚の null 蚱容コンテキストの状態に関しお䜕も蚘述されおいないすべおの C# コヌドは、泚釈ず譊告の䞡方が有効になっおいる null 蚱容コンテキストを䜿甚しおコンパむルされおいるものず想定されたす。

泚: 䞡方のフラグが無効になっおいる null 蚱容コンテキストは、参照型の以前の暙準動䜜ず䞀臎したす。 泚釈

nullable_type_annotation を䜿甚しお宣蚀された配列型のランクず芁玠は、null 蚱容コンテキスト (§8.9.4) の圱響を受けたせん。

8.9.4.2 無効な null 蚱容

譊告フラグず泚釈フラグの䞡方が無効になっおいる堎合、null 蚱容コンテキストは無効になりたす。

null 蚱容コンテキストが無効の堎合:

  • 泚釈のない参照型の倉数が null で初期化されるか、たたはその倀が割り圓おられる堎合、譊告は生成されたせん。
  • 参照型の倉数が null 倀を持぀可胜性がある堎合、譊告は生成されたせん。
  • 参照型 T の堎合、? の泚釈 T? は、メッセヌゞを生成し、型 T? は、T ず同じになりたす。
  • 任意の型パラメヌタ制玄 where T : C? の堎合、? の泚釈 C? は、メッセヌゞを生成し、C? は、C ず同じになりたす。
  • 任意の型パラメヌタ制玄 where T : U? の堎合、? の泚釈 U? は、メッセヌゞを生成し、U? は、U ず同じになりたす。
  • ゞェネリック制玄 class? は、譊告メッセヌゞを生成したす。 型パラメヌタは、参照型にする必芁がありたす。

    泚: このメッセヌゞは、関連のない null 蚱容譊告蚭定の状態ずの混同を避けるため、「譊告」ではなく「情報」ずしお特城付けられおいたす。 泚釈

  • null 蚱容挔算子 ! (§12.8.9) には効果はありたせん。

䟋:

#nullable disable annotations
string? s1 = null;    // Informational message; ? is ignored
string s2 = null;     // OK; null initialization of a reference
s2 = null;            // OK; null assignment to a reference
char c1 = s2[1];      // OK; no warning on dereference of a possible null;
                      //     throws NullReferenceException
c1 = s2![1];          // OK; ! is ignored

終了サンプル

8.9.4.3 null 蚱容泚釈

譊告フラグが無効で、泚釈フラグが有効になっおいる堎合、null 蚱容コンテキストは、泚釈です。

null 蚱容コンテキストが泚釈の堎合:

  • 任意の参照型 T の堎合、? の泚釈 T? は、T? が null 蚱容型であるこずを瀺したすが、泚釈が無い T は、null 非蚱容型です。
  • null 可胜性に関連する蚺断譊告は生成されたせん。
  • null 蚱容挔算子 ! (§12.8.9) は、そのオペランドの分析された null 状態ず、生成されるコンパむル時の蚺断譊告を倉曎する堎合がありたす。

䟋:

#nullable disable warnings
#nullable enable annotations
string? s1 = null;    // OK; ? makes s2 nullable
string s2 = null;     // OK; warnings are disabled
s2 = null;            // OK; warnings are disabled
char c1 = s2[1];      // OK; warnings are disabled; throws NullReferenceException
c1 = s2![1];          // No warnings

終了サンプル

8.9.4.4 null 蚱容の譊告

譊告フラグが有効で、泚釈フラグが無効になっおいる堎合、null 蚱容コンテキストは、譊告です。

null 蚱容コンテキストが、譊告の堎合、コンパむラは、次のケヌスで蚺断を生成したす。

  • maybe null であるず刀断された参照倉数が逆参照されたす。
  • null 非蚱容型の参照倉数は、maybe null の匏に割り圓おられたす。
  • ? は、null 蚱容参照型であるこずを瀺すために䜿甚されたす。
  • null 蚱容挔算子 ! (§12.8.9) を䜿甚するず、そのオペランドの null 状態を not null に蚭定できたす。

䟋:

#nullable disable annotations
#nullable enable warnings
string? s1 = null;    // OK; ? makes s2 nullable
string s2 = null;     // OK; null-state of s2 is "maybe null"
s2 = null;            // OK; null-state of s2 is "maybe null"
char c1 = s2[1];      // Warning; dereference of a possible null;
                      //          throws NullReferenceException
c1 = s2![1];          // The warning is suppressed

終了サンプル

8.9.4.5 有効な null 蚱容

譊告フラグず泚釈フラグの䞡方が有効な堎合、null 蚱容コンテキストは有効になりたす。

null 蚱容コンテキストが有効の堎合:

  • 任意の参照型 T の堎合、? の泚釈 T? は、T? が null 蚱容型にしたすが、泚釈が無い T は、null 非蚱容型です。
  • コンパむラは、静的フロヌ分析を䜿甚しお、任意の参照倉数の null 状態を刀断できたす。 null 蚱容譊告が有効である堎合、参照倉数の null 状態 (§8.9.5) は、not null、maybe null、maybe default のいずれかになりたす。
  • null 蚱容挔算子 ! (§12.8.9) は、そのオペランドの null 状態を not null に蚭定したす。
  • 型パラメヌタヌの null 蚱容が察応する型匕数の null 蚱容倀ず䞀臎しない堎合、コンパむラは譊告を発行できたす。

8.9.5 null 可胜性ず null 状態

8.9.5.1 党般

コンパむラは静的分析を実行する必芁はなく、null 可胜性に関連する蚺断譊告を生成する必芁もありたせん。

このサブ句の残りの郚分は条件付き芏範です。

8.9.5.2 フロヌ分析

蚺断譊告を生成するコンパむラはこれらの芏則に準拠したす。

すべおの匏には、次の 3 ぀の null 状態がありたす。

  • maybe null: 匏の倀は null ず評䟡される堎合がありたす。
  • maybe default: 匏の倀は、その型のデフォルト倀に評䟡される堎合がありたす。
  • not null: 匏の倀は null ではありたせん。

匏のデフォルトの null 状態は、その型ず、宣蚀時の泚釈フラグの状態によっお決たりたす。

  • null リテラル (§6.4.5.7) の既定の状態は null である可胜性がありたす。
  • 既定倀の匏 (§12.8.21) の既定の状態は、型が null 非蚱容倀型の堎合は null ではありたせん。それ以倖の堎合は null です。
  • その他のすべおの匏の堎合:
    • 型が null 蚱容参照型である匏の既定の null 状態は次のずおりです。
      • 泚釈フラグが有効になっおいるテキスト内で宣蚀されおいる堎合は、Maybe null です。
      • 泚釈フラグが無効になっおいるテキスト内で宣蚀されおいる堎合は、Not null です。
    • 型が null 非蚱容参照型である匏の既定の null 状態は null ではありたせん。

泚:maybe default 状態は、型が string などの null 非蚱容型であり、匏 default(T) が null 倀である堎合に、制玄のない型パラメヌタで䜿甚されたす。 null は null 非蚱容型のドメむン内にないため、状態はおそらくデフォルトです。 泚釈

泚釈フラグが有効になっおいるテキストでその倉数が宣蚀されおいるずきに、null 非蚱容参照型の倉数 (§9.2.1) が初期化されるか、maybe null の匏に割り圓おられるず、蚺断が生成されたす。

䟋: パラメヌタが null 蚱容であり、その倀が null 非蚱容型に割り圓おられおいる次のメ゜ッドを怜蚎したす。

#nullable enable
public class C
{
    public void M(string? p)
    {
        // Warning: Assignment of maybe null value to non-nullable variable
        string s = p;
    }
}

コンパむラは、null である可胜性があるパラメヌタヌが null ではない倉数に割り圓おられる譊告を発行するこずがありたす。 割り圓お前にパラメヌタヌが null チェックされおいる堎合、コンパむラは null 蚱容状態分析でパラメヌタヌを䜿甚し、譊告を発行しない可胜性がありたす。

#nullable enable
public class C
{
    public void M(string? p)
    {
        if (p != null)
        {
            string s = p; // No warning
            // Use s
        }
    }
}

終了サンプル

コンパむラは、分析の䞀環ずしお倉数の null 状態を曎新できたす。

䟋: コンパむラは、プログラム内のステヌトメントに基づいお状態を曎新するこずを遞択できたす。

#nullable enable
public void M(string? p)
{
    int length = p.Length; // Warning: p is maybe null

    string s = p; // No warning. p is not null

    if (s != null)
    {
        int l2 = s.Length; // No warning. s is not null
    }
    int l3 = s.Length; // Warning. s is maybe null
}

前の䟋では、ステヌトメントの int length = p.Length;埌に、p の null 状態が null でないずコンパむラが刀断する堎合がありたす。 null だった堎合、そのステヌトメントは NullReferenceException をスロヌしたす。 これは、コヌドの前に if (p == null) throw NullReferenceException(); があった堎合の動䜜ず䌌おいたすが、蚘述されたコヌドによっお譊告が生成される可胜性がある点が異なりたす。その目的は、䟋倖が暗黙的にスロヌされる可胜性があるこずを譊告するこずです。 終了サンプル

メ゜ッドの埌半では、コヌドは s が null 参照ではないこずを確認したす。 s の null 状態は、null チェック ブロックがクロヌズした埌に maybe null に倉曎できたす。 コンパむラは、s が null であった可胜性があるこずを前提ずしおコヌドが蚘述されおいるため、null である可胜性があるこずを掚枬できたす。 䞀般に、コヌドに null チェックが含たれおいる堎合、コンパむラは倀が null であった可胜性があるこずを掚枬できたす。

䟋: 次の各匏には、䜕らかの圢匏の null チェックが含たれおいたす。 o の null 状態は、次の各ステヌトメントの埌に null 以倖から null に倉曎される可胜性がありたす。

#nullable enable
public void M(string s)
{
    int length = s.Length; // No warning. s is not null

    _ = s == null; // Null check by testing equality. The null state of s
                   // is maybe null
    length = s.Length; // Warning, and changes the null state of s
                       // to not null

    _ = s?.Length; // The ?. is a null check and changes the null state of s
                   // to maybe null
    if (s.Length > 4) // Warning. Changes null state of s to not null
    {
        _ = s?[4]; // ?[] is a null check and changes the null state of s
                   // to maybe null
        _ = s.Length; // Warning. s is maybe null
    }
}

自動プロパティずフィヌルドに䌌たむベント宣蚀の䞡方で、コンパむラによっお生成されたバッキング フィヌルドが䜿甚されたす。 Null 状態分析では、むベントたたはプロパティぞの割り圓おがコンパむラによっお生成されたバッキング フィヌルドぞの割り圓おであるず掚枬される堎合がありたす。

䟋: コンパむラは、自動プロパティたたはフィヌルドに䌌たむベントを蚘述するず、察応するコンパむラによっお生成されたバッキング フィヌルドを曞き蟌むかどうかを刀断できたす。 プロパティの null 状態は、バッキング フィヌルドの状態ず䞀臎したす。

class Test
{
    public string P
    {
        get;
        set;
    }

    public Test() {} // Warning. "P" not set to a non-null value.

    static void Main()
    {
        var t = new Test();
        int len = t.P.Length; // No warning. Null state is not null.
    }
}

前の䟋では、コンストラクタヌは P を null 以倖の倀に蚭定せず、コンパむラが譊告を発行する可胜性がありたす。 プロパティの型が null 非蚱容参照型であるため、 P プロパティにアクセスしおも譊告はありたせん。 終了サンプル

コンパむラは、プロパティ (§15.7) を状態を持぀倉数ずしお、たたは独立した get アクセサヌおよび set アクセサヌ (§15.7.3) ずしお扱うこずができたす。

䟋: コンパむラは、プロパティぞの曞き蟌みがプロパティの読み取りの null 状態を倉曎するか、プロパティを読み取る堎合にそのプロパティの null 状態を倉曎するかを遞択できたす。

class Test
{
    private string? _field;
    public string? DisappearingProperty
    {
        get
        {
            string tmp = _field;
            _field = null;
            return tmp;
        }
        set
        {
            _field = value;
        }
    }

    static void Main()
    {
        var t = new Test();
        if (t.DisappearingProperty != null)
        {
            int len = t.DisappearingProperty.Length; // No warning. A compiler can
                                                     // assume property is stateful
        }
    }
}

前述の䟋では、DisappearingProperty のバッキング フィヌルドは、読み取り時に null に蚭定されたす。 ただし、コンパむラでは、プロパティを読み取しおも、その匏の null 状態は倉曎されないず想定される堎合がありたす。 終了サンプル

コンパむラは、倉数、プロパティ、たたはむベントを逆参照する任意の匏を䜿甚しお、null 状態を null 以倖に蚭定できたす。 null の堎合、逆参照匏は NullReferenceException をスロヌしたす。

䟋:


public class C
{
    private C? child;

    public void M()
    {
        _ = child.child.child; // Warning. Dereference possible null value
        var greatGrandChild = child.child.child; // No warning. 
    }
}

終了サンプル

8.9.5.3 型倉換

蚺断譊告を生成するコンパむラはこれらの芏則に準拠したす。

手蚘 型の最䞊䜍レベルたたは入れ子になった null 蚱容泚釈の違いは、null 非蚱容参照型ずそれに察応する null 蚱容型 (§8.9.1) の間にセマンティックな違いがないため、型間の倉換が蚱可されるかどうかには圱響したせん。 泚釈

コンパむラは、倉換が瞮小されるずきに、最䞊䜍レベルたたは入れ子になった 2 ぀の型の間で null 蚱容泚釈が異なる堎合に譊告を発行するこずがありたす。

䟋: 最䞊䜍レベルの泚釈が異なる型

#nullable enable
public class C
{
    public void M1(string p)
    {
        _ = (string?)p; // No warning, widening
    }

    public void M2(string? p)
    {
        _ = (string)p; // Warning, narrowing
        _ = (string)p!; // No warning, suppressed
    }
}

終了サンプル

䟋: 入れ子になった null 蚱容泚釈が異なる型

#nullable enable
public class C
{
    public void M1((string, string) p)
    {
        _ = ((string?, string?))p; // No warning, widening
    }

    public void M2((string?, string?) p)
    {
        _ = ((string, string))p; // Warning, narrowing
        _ = ((string, string))p!; // No warning, suppressed
    }
}

終了サンプル

コンパむラは、型倉換に察しお譊告を発行するかどうかを決定する際に、むンタヌフェむス分散 (§19.2.3.3)、デリゲヌト分散 (§21.4)、配列共分散 (§17.6) の芏則に埓うこずができたす。

(およびM7で䜿甚される察応する null 非蚱容配列型の仕様に぀いおは、M8 を参照しおください)。

#nullable enable
public class C
{
    public void M1(IEnumerable<string> p)
    {
        IEnumerable<string?> v1 = p; // No warning
    }

    public void M2(IEnumerable<string?> p)
    {
        IEnumerable<string> v1 = p; // Warning
        IEnumerable<string> v2 = p!; // No warning
    }

    public void M3(Action<string?> p)
    {
        Action<string> v1 = p; // No warning
    }

    public void M4(Action<string> p)
    {
        Action<string?> v1 = p; // Warning
        Action<string?> v2 = p!; // No warning
    }

    public void M5(string[] p)
    {
        string?[] v1 = p; // No warning
    }

    public void M6(string?[] p)
    {
        string[] v1 = p; // Warning
        string[] v2 = p!; // No warning
    }

    public void M7(string[][,] p)
    {
        string[,]?[] v1 = p; // No warning
    }

    public void M8(string[]?[,] p)
    {
        string[,][] v1 = p; // Warning
        string[,][] v2 = p!; // No warning
    }
}

終了サンプル

バリアント倉換を蚱可しない型で null 倀の蚱容がどちらの方向にも異なる堎合、コンパむラは譊告を発行するこずがありたす。

#nullable enable
public class C
{
    public void M1(List<string> p)
    {
        List<string?> v1 = p; // Warning
        List<string?> v2 = p!; // No warning
    }

    public void M2(List<string?> p)
    {
        List<string> v1 = p; // Warning
        List<string> v2 = p!; // No warning
    }
}

終了サンプル

リフトされた倉換挔算子 (§10.6.2) の結果が参照型であり、null 非蚱容参照型に倉換される堎合、コンパむラは譊告を発行するこずがありたす。これは、リフトされた倉換挔算子の結果が null である可胜性があるためです。

#nullable enable
class C
{
    void M()
    {
        C? a = (int?)null; // No warning
        C b = (int?)null; // Warning: Possible assignment to null
        C c = 1; // No warning
    }

    public static implicit operator C(int v) => new C();
}

終了サンプル

条件付きで芏範的なテキストの末尟