For some reason, M1()
causes a compiler error, while M2()
, which does the same thing, causes no error. Any idea why?
Using false ==
should be the same as using the not operator, !
.
Use of unassigned local variable 'i'
class Program {
static void Main(string[] args) {
int x = 8;
M1(x);
M2(x);
} // Main()
public static void M1(Object obj) {
if (false == (obj is int i)) // Causes ERROR on WriteLine
return;
System.Console.WriteLine(i); // Use of unassigned local variable 'i'
}
public static void M2(Object obj) {
if (!(obj is int i)) // OKAY
return;
System.Console.WriteLine(i);
}
} // class Program
The issue here is with the way the compiler handles "definitely assigned when true". !
inverts that; == false
doesn't. So for the code:
if (!(obj is int i))
return;
System.Console.WriteLine(i);
The compiler can infer that if obj is int i
is false, the !
inverts that, thus return
will occur if it's not an int
. Therefore i
can be allowed to "leak" into subsequent code safely.
However, the same rules do not apply to == false
. Whilst semantically identical to a human reader of the code, the compiler treats !
and == false
as very different things. So for:
if (false == (obj is int i))
the compiler baulks and takes the view it cannot know the assignment state of i
, thus the error.
For a discussion on this, please see Incorrect "Use of unassigned local variable" for (x is T y) == false
.
The moral of the story: avoid comparing to false
and use !
when using C# patterns.
EDIT
It should be noted that == false
is not a special case here. Any use of ==
removes the ability of the compiler to determine "definitely assigned when true". For example, the following code compiles:
object x = 1;
if (!(x is bool y))
return 0;
var z = y;
But add a == true
and it no longer does:
object x = 1;
if (!(x is bool y == true))
return 0;
var z = y; // error: use of an unassigned variable
EDIT2
Incidently, for anyone who uses if (expression == false)
because they find if (!expression)
difficult to read, you may be interested to know that the syntax, if !(expression)
is being considered for C# 8.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With