Using continue in a switch statement
Solution 1
It's fine, the continue
statement relates to the enclosing loop, and your code should be equivalent to (avoiding such jump statements):
while (something = get_something()) {
if (something == A || something == B)
do_something();
}
But if you expect break
to exit the loop, as your comment suggest (it always tries again with another something, until it evaluates to false), you'll need a different structure.
For example:
do {
something = get_something();
} while (!(something == A || something == B));
do_something();
Solution 2
Yes, continue will be ignored by the switch statement and will go to the condition of the loop to be tested. I'd like to share this extract from The C Programming Language reference by Ritchie:
The
continue
statement is related tobreak
, but less often used; it causes the next iteration of the enclosingfor
,while
, ordo
loop to begin. In thewhile
anddo
, this means that the test part is executed immediately; in thefor
, control passes to the increment step.The continue statement applies only to loops, not to a
switch
statement. Acontinue
inside aswitch
inside a loop causes the next loop iteration.
I'm not sure about that for C++.
Solution 3
Yes, it's OK - it's just like using it in an if
statement. Of course, you can't use a break
to break out of a loop from inside a switch.
Solution 4
It's syntactically correct and stylistically okay.
Good style requires every case:
statement should end with one of the following:
break;
continue;
return (x);
exit (x);
throw (x);
//fallthrough
Additionally, following case (x):
immediately with
case (y):
default:
is permissible - bundling several cases that have exactly the same effect.
Anything else is suspected to be a mistake, just like if(a=4){...}
Of course you need enclosing loop (while
, for
, do...while
) for continue
to work. It won't loop back to case()
alone. But a construct like:
while(record = getNewRecord())
{
switch(record.type)
{
case RECORD_TYPE_...;
...
break;
default: //unknown type
continue; //skip processing this record altogether.
}
//...more processing...
}
...is okay.
Solution 5
While technically valid, all these jumps obscure control flow -- especially the continue
statement.
I would use such a trick as a last resort, not first one.
How about
while (something = get_something())
{
switch (something)
{
case A:
case B:
do_something();
}
}
It's shorter and perform its stuff in a more clear way.
Related videos on Youtube
Matt Joiner
About Me I like parsimonious code, with simple interfaces and excellent documentation. I'm not interested in enterprise, boiler-plate, or cookie-cutter nonsense. I oppose cruft and obfuscation. My favourite languages are Go, Python and C. I wish I was better at Haskell. Google+ GitHub Bitbucket Google code My favourite posts http://stackoverflow.com/questions/3609469/what-are-the-thread-limitations-when-working-on-linux-compared-to-processes-for/3705919#3705919 http://stackoverflow.com/questions/4352425/what-should-i-learn-first-before-heading-to-c/4352469#4352469 http://stackoverflow.com/questions/6167809/how-much-bad-can-be-done-using-register-variables-in-c/6168852#6168852 http://stackoverflow.com/questions/4141307/c-and-c-source-code-profiling-tools/4141345#4141345 http://stackoverflow.com/questions/3463207/how-big-can-a-malloc-be-in-c/3486163#3486163 http://stackoverflow.com/questions/4095637/memory-use-of-stl-data-structures-windows-vs-linux/4183178#4183178
Updated on July 08, 2022Comments
-
Matt Joiner almost 2 years
I want to jump from the middle of a
switch
statement, to the loop statement in the following code:while (something = get_something()) { switch (something) { case A: case B: break; default: // get another something and try again continue; } // do something for a handled something do_something(); }
Is this a valid way to use
continue
? Arecontinue
statements ignored byswitch
statements? Do C and C++ differ on their behaviour here?-
antik over 14 yearsYour idea is fine but the loop above will never execute
do_something()
. -
Alexander Poluektov over 14 yearsEven if control reaches case A or case B?
-
Antony Woods over 14 yearsI was going to say, antik is wrong about that. In the case of A or B then do_something() will execute. With default it will bail.
-
Matt Joiner over 14 years@acron, that's the intended behaviour
-
Antony Woods over 14 yearsYeah, I know :) Was correcting antik's comment.
-
phoeagon over 10 yearsI think this looks far more suspicious & confusing and therefore more harmful than a
goto
. -
Yan Zhou over 7 yearsI don't see any problem with your code. Perhaps check if the input does get to the
default
branch? Maybe you can provide a more complete example that can reproduce your problem.
-
-
Matt Joiner over 14 yearsBut
if
has no effect on the behaviour ofcontinue
orbreak
. How do you mean it's alike? -
Matt Joiner over 14 yearssorry for the confusion Alexander, the code is for demonstration only, i have good reason (i believe) for the actual structure in my code.
-
visitor over 14 years@Matt: That would probably mean an even more obfuscated structure... :)
-
Admin over 14 years@Matt I mean it will continue the loop in both cases.
-
Matt Joiner over 14 years@Neil, okay, confusion averted.
-
Tim Schaeffer over 14 yearsI think it is still confusing.
-
chacham15 over 10 years'equivalent' only in the semantic sense. the code the compiler generates is very different. with a switch statement, the compiler can generate a jump table which avoids multiple comparisons and thus is much faster than comparing against each element 1 by 1.
-
Vality over 9 yearssorry for necroposting, but I would add that a call to
exit
would also usually be a fine thing to end a switch case with. -
avakar over 9 years@chacham15, why couldn't the compiler generate the same code for both?
-
chacham15 over 9 years@avakar switch statements generate jump tables whereas the other representation is a series of logical evaluations. google jump table for more information.
-
avakar over 9 years@chacham15, what prevents the compiler from generating a jump table for the two if statements or a series of logical evaluations for the switch?
-
chacham15 over 9 years@avakar switch statements require the cases to be constant values, because that is not the case with if statements, it cannot make the same optimization (note: i am speaking in the general case, it is possible given certain requirements (e.g. const values only, only certain logical operators, etc.) to make the optimization, but it is highly compiler dependent and YMMV).
-
Rick almost 7 yearsThe
switch
statement is inside awhile
loop, socontinue
is perfectly valid. -
Mouradif over 6 yearsyou can use
break
to break out of a loop from inside a switch just like you can break out of an outer loop from inside an inner loop like this :break 2;
orbreak 3;
to go up another level etcetera... -
arjunyg about 6 years@KiJéy I can't find any reference for this, and in many years of C programming I have never seen any compiler that supports this... Where on earth did you find this?
-
Mouradif about 6 yearsWow sorry, I saw this in PHP, thought it was an old practice, turns out it's just PHP...
-
SlySven over 5 yearsWell, I am going to got all Dr. Frankenstein here and also point out that
default:
does not have to be the last/bottom entry - as this question points out... -
SF. over 5 years@SlySven: Lexically, it doesn't, but if you don't have a good reason not to make it last, do make it last. It's often confusing if used at other places.
-
Geoffrey over 4 yearsThis is NOT a PHP question.
-
Ruslan almost 4 years@SF. well, I can easily imagine the cases when it would make more sense to make
default:
case the first instead of the last. Like "do this, unless you get the following unusual values, which should be handled as follows".