简体   繁体   English

根据ReSharper,C#是具有可空类型的运算符,始终为false

[英]C# is operator with nullable types always false according to ReSharper

I'm attempting to convert an object to a bool type and want to convert bool and Nullable<bool> types. 我正在尝试将object转换为bool类型,并想要转换boolNullable<bool>类型。 I also want to make sure I make the appropriate casts where possible. 我还想确保在可能的情况下进行适当的投射。 So I have the following code: 所以我有以下代码:

if (value is bool)
{
    boolValue = (bool) value;
}
else if (value is bool? && ((bool?)value).HasValue)
{
    boolValue = ((bool?) value).Value;
}
else
{
    throw new ArgumentException("Value must be a boolean type");
}

ReSharper 2016 informs me that value is bool? ReSharper 2016告诉我, value is bool? will always evaluate to false in this stack of if statements. 在此if语句堆栈中将始终为false。 Why is that? 这是为什么? That would imply that Nullable<bool> doesn't inherit from object (impossible) or that value is bool will capture a bool? 这意味着Nullable<bool>不会从object继承(不可能),或者value is bool会捕获bool? .

It's also possible that ReSharper 2016 has a bug; ReSharper 2016也可能有错误; I see that the implementation of System.Windows.Controls.BooleanToVisibilityConverter.Convert is pretty much identical. 我看到System.Windows.Controls.BooleanToVisibilityConverter.Convert的实现几乎相同。 I doubt that WPF core would have such a mistake in it, leading me to believe it's an issue with ReSharper. 我怀疑WPF内核中是否会有这样的错误,使我相信ReSharper的问题。

When a value type is stored as object it is boxed . 当值类型存储为object装箱 Boxing of Nullable<T> gets special treatment : Nullable<T>拳击获得特殊待遇

Objects based on nullable types are only boxed if the object is non-null. 仅当对象为非空时,才将基于可为空类型的对象装箱。 If HasValue is false, the object reference is assigned to null instead of boxing ... Boxing a non-null nullable value type boxes the value type itself , not the System.Nullable that wraps the value type. 如果HasValue为false,则将对象引用分配给null而不是装箱 ...将非null的可空值类型装箱将值类型本身装箱 ,而不是包装值类型的System.Nullable。

And, per the documentation for is : 而且,按照文档is

An is expression evaluates to true if the provided expression is non-null , and the provided object can be cast to the provided type without causing an exception to be thrown. 如果提供的表达式为非null ,则is表达式的计算结果为true,并且可以将提供的对象强制转换为提供的类型而不会引发异常。

So, using both of these you can deduce (see fiddle ) that in the null case: 因此,使用这两种方法,您可以推断出(请参见fiddle )在空情况下的情况:

bool? x = null;
object obj = x;   // assigns obj = null
obj is bool?      // false, obj is null
obj is bool       // false, obj is null

And in the non-null case: 在非null的情况下:

bool? x = true;
object obj =  x;  // obj is boxed bool (true)
obj is bool?      // true, obj unboxes to bool?
obj is bool       // true, obj unboxes to bool

So ReSharper is correct: your first branch will evaluate as true if value is true or false (whether the object was assigned from a bool or bool? is not relevant or even known). 因此ReSharper是正确的:如果valuetruefalse (对象是从bool还是bool?分配的,则不相关甚至未知),则您的第一个分支的评估结果为true The second branch will always be false in this case. 在这种情况下,第二个分支将始终为false

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM