Possible Duplicate:
Variable declaration in c# switch statement
What is the purpose of the extra braces in Switch case?
Today I was writing a small piece of code and, at debugging time, VS slapped me and told me I made a big mistake with my local variables names: “A local variable named ‘i’ is already defined in this scope”.
MyEnum enumerator = MyEnum.B;
switch (enumerator)
{
case MyEnum.A:
Int32 i = 0;
// DoStuffsA();
break;
case MyEnum.B:
Double i = 0D;
// DoStuffsB();
break;
}
So I said “Ok VS, let me fix it in a moment, I want to scope my cases first as I like them more!”. So I made my cosmetic change… but suddenly VS stopped whining about that error:
MyEnum enumerator = MyEnum.B;
switch (enumerator)
{
case MyEnum.A:
{
Int32 i = 0;
// DoStuffsA();
break;
}
case MyEnum.B:
{
Double i = 0D;
// DoStuffsB();
break;
}
}
Ok… I’m aware of the meaning of “scope” and I know I produced two different scopes like so. The problem is that I don’t know how switch statements are translated into IL code and I always thought that all the case statements were placed into the switch scope no matter if curly braces were used or not. So… the following oddity can be compiled, right?
MyEnum enumerator = MyEnum.B;
switch (enumerator)
{
case MyEnum.A:
String s = "Hello!";
Console.WriteLine(s);
break;
case MyEnum.B:
s = "Goodbye!";
Console.WriteLine(s);
break;
}
But not the following one:
MyEnum enumerator = MyEnum.B;
switch (enumerator)
{
case MyEnum.A:
{
String s = "hello";
Console.WriteLine(s);
break;
}
case MyEnum.B:
{
s = "goodbye";
Console.WriteLine(s);
break;
}
}
Can some explain me better the behavior of the compiler in this situation?
Many thanks!
Firstly, the translation to IL is somewhat irrelevant. IL doesn’t have the same concepts of scope at all. This is all about the C# language specification.
It’s pretty simple, really: the scope of a local variable is the block in which it’s declared, and you can’t declare one local variable when another local variable of the same name is in scope.
In your first snippet of code, the scope of
iis the whole switch statement. Your second declaration tries to declare anotherivariable within the same scope, thus it fails.In your second snippet of code, the scope of each
ivariable is just the block created by the curly braces – they’re in entirely separate scopes, no nesting, so it’s fine.In your third snippet of code, the variable
sis in scope for the second case, as its scope is the entire switch statement – so it’s fine to use it.In your fourth snippet of code, the variable
sis only in the scope of the block in which it’s declared (inside case A) so it’s not in scope in case B.I would strongly recommend against using code like your third snippet of code though. It will confuse many people. If you really want a variable which is in scope for multiple cases, I’d declare it before the switch statement.