Is there a performance benefit to one way over the other?
Are there other reasons to choose one over the other?
Is there a performance benefit to one way over the other?
Are there other reasons to choose one over the other?
Is there a performance benefit to one way over the other?
No. They both compile to the exact same IL. The cast is syntactic sugar for the Value property. This code:
int? x = null;
Console.WriteLine(x.Value);
Console.WriteLine((int)x);
compiles to these IL instructions, ignoring nop
s: (you can test this yourself using ildasm, ILSpy, DotPeek, etc.)
// int? x = null;
ldloca.s 0
initobj valuetype [mscorlib]System.Nullable`1<int32>
// Console.WriteLine(x.Value);
ldloca.s 0
call instance !!0 [mscorlib]System.Nullable`1<int32>::get_Value()
call void [mscorlib]System.Console::WriteLine(int32)
// Console.WriteLine((int)x);
ldloca.s 0
call instance !!0 [mscorlib]System.Nullable`1<int32>::get_Value()
call void [mscorlib]System.Console::WriteLine(int32)
Are there other reasons to choose one over the other?
I prefer to avoid casts when I can, because there's always the potential for them to get out of sync with the actual type. If I change my variable from int?
to byte?
, then all my casts are wrong -- but if I was using .Value
, I'm free to change the variable as necessary. To me, the hard cast doesn't add anything in terms of readability, but it does cost in terms of maintainability.
Is there a performance benefit to one way over the other?
Performance would be negligible
Are there other reasons to choose one over the other?
Readability?
// most readable
public int GetValue(int? value)
{
return value.GetValueOrDefault();
}
// less readable
public int GetValue(int? value)
{
return value ?? default(int);
}
// least readable
public int GetValue(int? value)
{
return value.HasValue ? value.Value : default(int);
}
//least readable reversed return type/param type
public int? GetValue(int value)
{
return value == 0 ? null : (int?)value;
}
(Old question? Who cares. Contemporary problem.)
First, Joe provides a great answer, and given the current state of C#, I guess I agree with him:
... potential for them to get out of sync with the actual type. If I change my variable from int? to byte?, then all my casts are wrong -- but if I was using .Value, I'm free to change the variable as necessary.
The problem is that you always are committing to a type, because if you use .Value
then you are committing to Nullable<TAny>
and if you're using the cast you're committing to "ICastableTo<TSpecific>
"made up name
That said, Joe's advice is still valid, because the compiler will be much better at catching invalid .Value
usage than potentially semantically invalid casts that may still compile, and you want the compiler to catch as much stuff as it can when changing types.