C# 可空布尔函数的性质

C# 可空布尔函数的性质,c#,boolean,nullable,C#,Boolean,Nullable,为什么第二个案例没有编译?有没有办法通过超载或其他方式来完成这项工作 bool b1 = true; bool? b2 = false; if (b1) //does compile { //do sth. } if (b2) //doesn't compile { //do sth. } if (b2 == true) //does compile { //do sth. } 因为b2不是类型bool,它是bool?,相当于Nullable 您应该尝试以下方法:

为什么第二个案例没有编译?有没有办法通过超载或其他方式来完成这项工作

bool b1 = true;
bool? b2 = false;

if (b1) //does compile
{
    //do sth.
}

if (b2) //doesn't compile
{
    //do sth.
}

if (b2 == true) //does compile
{
    //do sth.
}

因为b2不是类型
bool
,它是
bool?
,相当于
Nullable

您应该尝试以下方法:

if (b2.HasValue && b2.Value)
{
  // do sth
}

if语句需要解析布尔值

您可以使用该属性

当然,您可能也要检查它是否为null


==true
编译,因为
=
(equals)运算符正在评估一个对象是否与另一个对象等效。这并不一定意味着输出总是正确的(我不是说也不会)但是您应该将
Nullable
视为
Nullable
,并使用适当的属性b2的变量应该可以为null。如果您先检查该变量的值,然后再检查该值是否为true或false。

第二种情况不会编译,因为If语句需要一个布尔表达式,但是
b2
本身不是布尔表达式。它也可以为空

我通常选择你的第三个选项(
b2==true
)。如果它不是
null
,且值为
true
,则将计算为
true


换句话说,
b2==true
相当于
b2!=null&&b2.Value

第三个示例之所以有效,是因为提升了运算符。因此:

对于等式运算符

===

如果操作数类型都是不可为null的值类型且结果类型为bool,则存在运算符的提升形式。提升形式是通过添加单个?每个操作数类型的修饰符。提升运算符认为两个空值相等,一个空值不等于任何非空值。如果两个操作数均非空,则提升运算符将展开操作数并应用基础运算符以生成布尔结果

所以,这就是为什么第三个例子有效——因为所有这些机器都是发明出来的,它适用于所有可为空的类型

您的第二个示例可以正常工作,但它需要编译器对一个可为null的类型执行特殊的工作-
bool?
。一般来说,每次使用可空类型执行隐式转换回原始值类型是不合适的



(以上引自第7.3.7节)

无法将类型
bool?
隐式转换为
bool
。检查
if(b2!=null和b2.Value)
if
导出布尔表达式
bool
是布尔表达式
bool?
不是!但是我也可以用
b2==true
代替
b2.Value==true
@Byyo-我更新了我的答案来解释-(阅读更多关于我更新的内容)为什么
if(b2)
if(b2==true)
@Byyo不一样,因为
b2==true
是一个布尔表达式,
b2
不是。这样想:第一个总是返回
true
false
。第二个可以返回
true
false
null
。if语句不知道如何处理
null
if(b2.Value)