How to break out of the loop from inside the switch?

I am writing code that looks like this:

while(true) { switch(msg->state) { case MSGTYPE: // ... break; // ... more stuff ... case DONE: break; // **HERE, I want to break out of the loop itself** } } 

Is there any direct way to do this?

I know that I can use the flag and interrupt the loop by putting a conditional break right after the switch. I just want to know if C ++ has any construction for this already.

+80
c ++ syntax loops switch-statement break
Sep 14 '09 at 6:51
source share
19 answers

Premise

The following code should be considered bad, regardless of language or desired functionality:

 while( true ) { } 

Supporting Arguments

The while( true ) is bad because it:

  • Terminates the implied while loop contract.
    • A while loop declaration must explicitly indicate a single exit condition.
  • Assumes he will be forever.
    • The code inside the loop must be read in order to understand the termination proposal.
    • Cycles that are repeated forever do not allow the user to complete the program from the program.
  • Ineffective.
    • There are several conditions for ending a loop, including a true check.
  • It is prone to errors.
    • It is impossible to determine where to put the code that will be executed for each iteration.
  • Leads to overly complex code.

Go to alternative

The following code looks better:

 while( isValidState() ) { execute(); } bool isValidState() { return msg->state != DONE; } 

Benefits

There is no flag. No goto . No exceptions. Easy to change. Easy to read. Easy to fix. In addition, the code:

  • Isolates knowledge of the cycle workload from the cycle itself.
  • Allows someone to maintain code to easily extend functionality.
  • Allows you to assign multiple completion conditions in one place.
  • Separates a ending sentence from code to execute.
  • Safer for nuclear power plants .; -)

The second point is important. Not knowing how the code works, if someone asked me to make the main loop so that other threads (or processes) have some processor time, two solutions come to mind:

Option number 1

Readily insert a pause:

 while( isValidState() ) { execute(); sleep(); } 

Option number 2

Replace execution:

 void execute() { super->execute(); sleep(); } 

This code is simpler (therefore easier to read) than a loop with a built-in switch . The isValidState method should only determine if the loop should continue. The workhorse of the method should be abstracted to the execute method, which allows subclasses to override the default behavior (a difficult task using the built-in switch and goto ).

Python example

Contrast the following answer (to a Python question) that was posted on StackOverflow:

  • Loop forever.
  • Ask the user to enter their choice.
  • If user input is a β€œrestart”, continue the loop forever.
  • Otherwise, stop the cycle forever.
  • To the end.
The code
 while True: choice = raw_input('What do you want? ') if choice == 'restart': continue else: break print 'Break!' 

Versus:

  • Initialize user selection.
  • Loop, while user choice is the word "reboot".
  • Ask the user to enter their choice.
  • To the end.
The code
 choice = 'restart'; while choice == 'restart': choice = raw_input('What do you want? ') print 'Break!' 

Here, while True leads to misleading and overly complex code.

+51
Sep 14 '09 at 7:14
source share

You can use goto .

 while ( ... ) { switch( ... ) { case ...: goto exit_loop; } } exit_loop: ; 
+132
Sep 14 '09 at 6:53
source share

An alternative solution is to use the continue keyword in combination with break , break .:

 for (;;) { switch(msg->state) { case MSGTYPE // code continue; // continue with loop case DONE: break; } break; } 

Use the continue statement to complete each case label where you want the loop to continue, and use the break statement to complete the case labels that should break the loop.

Of course, this solution only works if there is no additional code after the switch statement.

+44
Sep 14 '09 at 7:41
source share

The best way to do this would be to include this in a function:

 int yourfunc() { while(true) { switch(msg->state) { case MSGTYPE: // ... break; // ... more stuff ... case DONE: return; } } } 

Optional (but "bad methods"): as already mentioned, you can use goto or throw an exception inside the switch.

+19
Sep 14 '09 at 6:56
source share

AFAIK in C ++ there is no "double gap" or similar construct. The closest one will be goto - which, although it has a poor connotation of its name, exists in the language for any reason - if it is used carefully and sparingly, this is a viable option.

+12
Sep 14 '09 at 6:54
source share

You can add your switch to a separate function:

 bool myswitchfunction() { switch(msg->state) { case MSGTYPE: // ... break; // ... more stuff ... case DONE: return false; // **HERE, I want to break out of the loop itself** } return true; } while(myswitchfunction()) ; 
+8
Sep 14 '09 at 7:35
source share

Even if you don't like goto, don't use an exception to exit the loop. The following example shows how ugly it would be:

 try { while ( ... ) { switch( ... ) { case ...: throw 777; // I'm afraid of goto } } } catch ( int ) { } 

I would use goto , as in this answer. In this case, goto will make the code more understandable than any other option. I hope this one is helpful.

But I think using goto is the only option here because of the while(true) . You should consider reorganizing your cycle. I would suggest the following solution:

 bool end_loop = false; while ( !end_loop ) { switch( msg->state ) { case MSGTYPE: // ... break; // ... more stuff ... case DONE: end_loop = true; break; } } 

Or even the following:

 while ( msg->state != DONE ) { switch( msg->state ) { case MSGTYPE: // ... break; // ... more stuff ... } 
+7
Sep 14 '09 at 7:15
source share

In this case, there is no C ++ construct to exit the loop.

Use the flag to break the loop or (if necessary) extract your code into the function and use return .

+5
Sep 14 '09 at 6:59
source share

You could use goto, but I would prefer to set a flag that stops the loop. Then exit the switch.

+2
Sep 14 '09 at 6:54
source share

Why not just fix the condition in your while loop, causing the problem to disappear?

 while(msg->state != DONE) { switch(msg->state) { case MSGTYPE: // ... break; // ... more stuff ... case DONE: // We can't get here, but for completeness we list it. break; // **HERE, I want to break out of the loop itself** } } 
+2
Jul 15 '13 at 15:22
source share

I think:

 while(msg->state != mExit) { switch(msg->state) { case MSGTYPE: // ... break; case DONE: // .. // .. msg->state =mExit; break; } } if (msg->state ==mExit) msg->state =DONE; 
+1
Jan 07 '14 at 8:52
source share

The easiest way to do this is to put a simple IF before you do the SWITCH, and that IF will check your loop exit condition .......... as simple as it can be

0
Nov 12 '09 at 9:06
source share

The break keyword in C ++ only completes the most nested nested iteration or switch . That way, you could not break out of the while (true) directly in the switch ; however, you can use the following code, which I think is a great example for this type of problem:

 for (; msg->state != DONE; msg = next_message()) { switch (msg->state) { case MSGTYPE: //... break; //... } } 

If you need to do something when msg->state is DONE (for example, start the cleanup procedure), then put this code right after the for loop; those. if you have:

 while (true) { switch (msg->state) { case MSGTYPE: //... break; //... case DONE: do_cleanup(); break; } if (msg->state == DONE) break; msg = next_message(); } 

Then use instead:

 for (; msg->state != DONE; msg = next_message()) { switch (msg->state) { case MSGTYPE: //... break; //... } } assert(msg->state == DONE); do_cleanup(); 
0
Jan 04 2018-11-11T00:
source share

It amazes me how simple it is to consider the depth of explanations ... Here is all you need ...

 bool imLoopin = true; while(imLoopin) { switch(msg->state) { case MSGTYPE: // ... break; // ... more stuff ... case DONE: imLoopin = false; break; } } 

Lol !! Indeed! That is all you need! One additional variable!

0
May 04 '11 at 7:57 a.m.
source share
 while(MyCondition) { switch(msg->state) { case MSGTYPE: // ... break; // ... more stuff ... case DONE: MyCondition=false; // just add this code and you will be out of loop. break; // **HERE, you want to break out of the loop itself** } } 
0
Jun 22 2018-11-11T00:
source share

I have the same problem and solved using the flag.

 bool flag = false; while(true) { switch(msg->state) { case MSGTYPE: // ... break; // ... more stuff ... case DONE: flag = true; // **HERE, I want to break out of the loop itself** } if(flag) break; } 
0
Aug 08 '16 at 11:00
source share

No, C ++ has no construct for this, since the keyword "break" is already reserved for exiting the switch block. Alternatively, there may be do..while () with the exit flag.

 do { switch(option){ case 1: ..; break; ... case n: .. ;break; default: flag = false; break; } } while(flag); 
0
Apr 07 '17 at 6:37
source share

If I remember the C ++ syntax well, you can add a shortcut to the break statements, as with goto . So you want to write easily:

 while(true) { switch(msg->state) { case MSGTYPE: // ... break; // ... more stuff ... case DONE: break outofloop; // **HERE, I want to break out of the loop itself** } } outofloop: // rest of your code here 
-2
Sep 14 '09 at 17:13
source share
  while(true) { switch(x) { case 1: { break; } break; case 2: //some code here break; default: //some code here } } 
-3
Jan 30 '12 at 17:45
source share



All Articles