2011-03-08 59 views

回答

53

这只是语法糖。它们的行为方式完全相同 - 无论如何,无效测试实际上都被编译为调用HasValue

样品:

public class Test 
{ 
    static void Main() 
    { 
     int? x = 0; 
     bool y = x.HasValue; 
     bool z = x != null; 
    } 
} 

IL:

.method private hidebysig static void Main() cil managed 
{ 
    .entrypoint 
    // Code size  25 (0x19) 
    .maxstack 2 
    .locals init (valuetype [mscorlib]System.Nullable`1<int32> V_0) 
    IL_0000: ldloca.s V_0 
    IL_0002: ldc.i4.0 
    IL_0003: call  instance void valuetype [mscorlib]System.Nullable`1<int32>::.ctor(!0) 
    IL_0008: ldloca.s V_0 
    IL_000a: call  instance bool valuetype [mscorlib]System.Nullable`1<int32>::get_HasValue() 
    IL_000f: pop 
    IL_0010: ldloca.s V_0 
    IL_0012: call  instance bool valuetype [mscorlib]System.Nullable`1<int32>::get_HasValue() 
    IL_0017: pop 
    IL_0018: ret 
} // end of method Test::Main 
+0

哪两个你会认为'整洁'? – 2011-03-08 14:36:48

+2

@尼尔:这取决于上下文。我可能会*通常*使用空比较,但偶尔我猜'HasValue'会更具可读性。 – 2011-03-08 14:38:29

+2

谢谢。我不得不说,我看到更多'!= null'比我做HasValue'比较。 – 2011-03-08 14:39:33

8

这句法糖; Nullable<T>实际上是struct,所以它实际上不能null;编译器将与null(如第二个示例)相比较的调用转换为调用HasValue

注意,虽然,拳击一个Nullable<T>object将导致T任一值(如果有值)或null(如果事实并非如此)。

I.E.

int? foo = 10; // Nullable<int> with a value of 10 and HasValue = true 
int? bar = null; // Nullable<int> with a value of 0 and HasValue = false 

object fooObj = foo; // boxes the int 10 
object barObj = bar; // boxes null 

Console.WriteLine(fooObj.GetType()) // System.Int32 
Console.WriteLine(barObj.GetType()) // NullReferenceException 
+1

请参阅http://msdn.microsoft.com/en-us/library/ms228597.aspx – 2014-02-04 12:58:06

3

C#编译器已经内置了支持Nullable<T>和会变成涉及到null呼叫结构体的成员平等的行动。

n != nulln.HasValue都将编译成相同的IL。

相关问题