C# 可空类型

2018-01-22 17:10 更新

C# 可空类型

引用类型可以使用空引用表示不存在的值。

值类型通常不能表示空值。

例如:

string s = null; // OK, Reference Type
int i = null;    // Compile Error, Value Type cannot be null

要在值类型中表示 null ,必须使用一个称为可空类型的特殊结构。

可空类型用值类型表示,后跟?符号:

int? i = null; // OK, Nullable Type
Console.WriteLine (i == null); // True

Nullable< T> 是不可变结构,只有两个字段,代表 Value HasValue


隐式和显式可空转换

从T到T的转换?是隐式的,并且从T?到T是显式的。

例如:

int? x = 5; // implicit
int y = (int)x; // explicit

显式转换直接等同于调用可为空的对象的Value属性。

因此,如果 HasValue 为false,则抛出 InvalidOperationException

装箱和拆箱可空值

T?被装箱时,堆上的装箱值包含 T ,而不是 T?

这个优化是可能的,因为装箱的值是可以表达null的引用类型。

C#还允许使用as操作符取消装箱可空类型。如果转换失败,结果将为null:

object o = "string";
int? x = o as int?;
Console.WriteLine (x.HasValue); // False

运算符优化

Nullable <T> struct不定义操作符,例如<,>,甚至==。尽管如此,下面的代码编译并正确执行:

int? x = 5;
int? y = 10;
bool b = x < y; // true

如果 x y 都有值,则通过int的小于运算符进行比较;否则,返回false。

运算符提升意味着你可以在 T 上隐式使用T的运算符。

这里有些例子:


int? x = 1;
int? y = null;

// Equality operator examples
Console.WriteLine (x == y); // False
Console.WriteLine (x == null); // False
Console.WriteLine (x == 1); // True
Console.WriteLine (y == null); // True
Console.WriteLine (y == 1); // False
Console.WriteLine (y != 1); // True


// Relational operator examples
Console.WriteLine (x < 6); // True
Console.WriteLine (y < 6); // False
Console.WriteLine (y > 6); // False


// All other operator examples
Console.WriteLine (x + 5); // 6
Console.WriteLine (x + y); // null

编译器根据运算符的类别不同地处理空逻辑。

等式运算符(==和!=)

这意味着两个空值是相等的:


Console.WriteLine ( null == null); // True
Console.WriteLine ((bool?)null == (bool?)null); // True

如果恰好一个操作数为空,则操作数不等。

如果两个操作数都不为空,则比较它们的值。

关系运算符

null 值与空值或非空值进行比较返回false。

所有其他运算符(+, - ,*,/,%,&,|,^,<<,>>,+,++, - ,!,〜)在任何操作数为空时返回null。

混合可空和不可为空的运算符

您可以混合和匹配可空类型和非可空类型:


int? a = null;
int b = 1;
int? c = a + b; // c is null - equivalent to a + (int?)b

bool? 用 & 和 | 运算符

当提供的bool?类型的操作数&|运算符将null视为未知值。所以,null | true为true。

类似地, null & false为false。

以下示例枚举其他组合:


bool? n = null;
bool? f = false;
bool? t = true;
Console.WriteLine (n | n); // (null)
Console.WriteLine (n | f); // (null)
Console.WriteLine (n | t); // True
Console.WriteLine (n & n); // (null)
Console.WriteLine (n & f); // False
Console.WriteLine (n & t); // (null)

空合并运算符

?? 运算符是空合并运算符,它可以与可空类型和引用类型一起使用。

如果操作数是非空的,返回它;否则,或返回默认值。

例如:


int? x = null;
int y = x ?? 5; // y is 5

int? a = null, b = 1, c = 2;
Console.WriteLine (a ?? b ?? c); // 1 (first non-null value)

?? 运算符等效于调用具有显式默认值的 GetValueOrDefault 值。

以上内容是否对您有帮助:
在线笔记
App下载
App下载

扫描二维码

下载编程狮App

公众号
微信公众号

编程狮公众号