Section 6.8.1 of C11 or C99, or section 3.6.1 of C89 all seem to indicate that default
and case x
(where x
is some constant-expression) are examples of labeled statements, along-side identifier:
-style labels that are suitable for use with goto
.
I'm aware that I could simply place an identifier:
-style label directly following the default:
or case x:
labels. That's not what this question is about. I'm more curious as to whether there is any actual rationale behind prohibiting this kind of behaviour.
If it were possible to declare default:
labels outside of a switch
selection structure, then I would understand, as there would be some conflict between where the goto
inside of the switch
selection structure is intended to aim. However, section 6.4.1 of C11 or C99 or 3.1.1 of C89 prohibits the use of default
as anything other than a keyword, and 6.8.1 restricts its use further to switch
structures only (or generic
structures in C11, which are irrelevant here).
I would also understand if multiple (possibly nested) switch
structures, each with default:
(or case x:
) labels introduced ambiguity, however the scope of those labels seems to be restricted to within their inner-most surrounding switch
structures, and referring to any identifier outside of its scope is clearly an error requiring a diagnostic at compile-time.
Has this been discussed in any standard documents (e.g. the rationale)? Is there any kind of explanation for this behaviour other than "it is because it is" or "because the spec says so"? If so, what is that explanation?
A label is a valid C# identifier followed by colon. In this case, case and default statements of a Switch are labels thus they can be targets of a goto. However, the goto statement must be executed from within the switch. that is we cannot use the goto to jump into switch statement .
The position of default doesn't matter, it is still executed if no match found. // The default block is placed above other cases.
Yes, it does.
A 'switch' statement should have 'default' as the last label. Adding a 'default' label at the end of every 'switch' statement makes the code clearer and guarantees that any possible case where none of the labels matches the value of the control variable will be handled.
(I don't see how goto
to a case
would work syntactically.)
As you say, case
and default
labels only have the scope of the corresponding switch
statement and can only be jumped to from outside. On the other hand
labels in C have function scope and can be jumped to from anywhere in the function.
So we are talking of labels with a quite different properties, they are probably treated quite different, internally. It seems relatively complicated to reconcile these properties and would make implementing this more complicated. All of a sudden you would have to have to decide when implementing goto
which case
or default
is the correct one, whereas now you just have to put the address of the file scope identifier, there.
All of this said, this is just a guess about the original intentions for this distinction. But I am sure that argumentation along these lines would quickly kill any attempt to introduce such a feature now.
counter example
fun() {
switch (b) {
case x:
doSomething();
break;
}
switch(b2) {
case x:
doMore();
break;
}
goto x; // which one?
}
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