Unintentional fall-through in D's switch statements
by Leandro Lucarella on 2009-11-20 23:34 (updated on 2009-11-20 23:34)- with 2 comment(s)
Removing switch fall-through from D's switch statement is something discussed since the early beginnings of D, there are discussions about it since 2001 and to the date [*]. If you don't know what I'm talking about, see this example:
switch (x) {
case A:
i = x;
// fall-through
case B:
j = 2;
break;
case C:
i = x + 1;
break;
}
If you read carefully the case B case A code, it doesn't include a break statement, so if x == A not only i = x will be executed, the code in case B will be executed too. This is perfectly valid code, introduced by C, but it tends to be very error prone and if you forget a break statement, the introduced bug can be very hard to track.
Fall-through if fairly rare, and it would make perfect sense to make it explicit. Several suggestions were made in this time to make fall-through explicit, but nothing materialized yet. Here are the most frequently suggested solutions:
Add a new syntax for non-fall-through switch statements, for example:
switch (x) { case A { i = x; } case B { j = 2; } case C { i = x + 1; }Don't fall-through by default, use an explicit statement to ask for fall-through, for example:
switch (x) { case A: i = x; goto case; case B: j = 2; break; case C: i = x + 1; break; }Others suggested continue switch or fallthrough, but I think some of this suggestions were made before goto case was implemented.
A few minutes ago, Chad Joan has filled a bug with this issue, but with a patch attached 8-). He opted for an intermediate solution, more in the lines of new switch syntax. He defines 2 case statements: case X: and case X!: (note the !). The former doesn't allow implicit fall-through and the latter does. This is the example in the bug report:
switch (i)
{
case 1!: // Intent to use fall through behavior.
x = 3;
case 2!: // It's OK to decide to not actually fall through.
x = 4;
break;
case 3,4,5:
x = 5;
break;
case 6: // Error: You either forgot a break; or need to use !: instead of :
case 7: // Fine, ends with goto case.
goto case 1;
case 8:
break;
x = 6; // Error: break; must be the last statement for case 8.
}
While I really think the best solution is to just make a goto case required if you want to fall-through [†], it's great to have a patch for a solution. Thanks Chad! =)
| [†] | I find it more readable and with better locality, to know if something fall-through or not I just have to read the code sequentially without remembering which kind of case I'm in. And I think cases without any statements should be allowed too, I wonder how this works with case range statements. |
Gato Pajero
by Leandro Lucarella on 2009-11-20 16:07 (updated on 2009-11-20 16:07)- with 0 comment(s)

Sacada en el Museo de Ciencias Naturales de la Facultad de Ciencias Naturales y Museo de la Universidad Nacional de La Plata.
Más allá del chiste, muy lindo museo para ir a visitar...