switch case failure

Y

YitzHandel

The following is an extract from my program, which I seperated out and
compiled as its own program.

The problem is that as soon as a case tests true, all the cases below
it execute as well. So if the user inputs, 4, the statements from
cases 4-9 will execute.

(I replaced function calls with cout for testing.)

I am using Win2k, Open Watcom IDE v 1.3.

This has tested as happening in several places in the program.

(p.s. - it compiles as is, it also compliles fine with all the
commented out libraries - same error either way)




//#include <stdio.h>
#include <stdlib.h>
#include <iostream.h> // instead of using namespace std
//#include <string.hpp>
//#include <fstream.h>
//#include <istream>
//#include "Fcopy.h"
//#include <ctime>
//#include <math.h>


int main ()
{
int menu_select_int =-1;

do
{
system("CLS");
cout <<"**********************MENU***********************\n";
cout << " Create Or Edit Input File..........1\n";
cout << " Calc. no. of stages................2\n";
cout << " Data plot..........................3\n";
cout << " RR vs. No. Of stages...............4\n";
cout << " McCabe Thiele plot.................5\n";
cout << " Printout the input file............6\n";
cout << " Printout of the tray compositions..7\n";
cout << " Printout of the vle data...........8\n";
cout << " Quit...............................9\n";
cout << "*************************************************\n\n";
cout << "MENU: ";
cin >> menu_select_int;

switch (menu_select_int)
{

case 1:
cout << "\ngoing to input data function\n";
cout << "case 1";
cin.ignore();

case 2:
cout << "\ngoing to CNOS function\n";
cout << "case 2";
cin.ignore();

case 3:
cout << "\ngoing to DP function\n";
cout << "case 3";
cin.ignore();

case 4:
cout << "\ngoing to RR vs function\n";
cout << "case 4";
cin.ignore();

case 5:
cout << "\ngoing to McTh function\n";
cout << "case 5";
cin.ignore();

case 6:
cout << "\ngoing to PIF function\n";
cout << "case 6";
cin.ignore();

case 7:
cout << "\ngoing to printout function\n";
cout << "case 7";
cin.ignore();

case 8:
cout << "\ngoing to PO VLE function\n";
cout << "case 8";
cin.ignore();

case 9:
cout << "\ngoing to AYS - end function\n";
cout << "case 9";
cin.ignore();


} //end switch case
} while (menu_select_int != 9);

cin.ignore();
return(0);

}
 
D

David Resnick

YitzHandel said:
The following is an extract from my program, which I seperated out and
compiled as its own program.

The problem is that as soon as a case tests true, all the cases below
it execute as well. So if the user inputs, 4, the statements from
cases 4-9 will execute.

(I replaced function calls with cout for testing.)

I am using Win2k, Open Watcom IDE v 1.3.

This has tested as happening in several places in the program.

(p.s. - it compiles as is, it also compliles fine with all the
commented out libraries - same error either way)




//#include <stdio.h>
#include <stdlib.h>
#include <iostream.h> // instead of using namespace std
//#include <string.hpp>
//#include <fstream.h>
//#include <istream>
//#include "Fcopy.h"
//#include <ctime>
//#include <math.h>


int main ()
{
int menu_select_int =-1;

do
{
system("CLS");
cout <<"**********************MENU***********************\n";
cout << " Create Or Edit Input File..........1\n";
cout << " Calc. no. of stages................2\n";
cout << " Data plot..........................3\n";
cout << " RR vs. No. Of stages...............4\n";
cout << " McCabe Thiele plot.................5\n";
cout << " Printout the input file............6\n";
cout << " Printout of the tray compositions..7\n";
cout << " Printout of the vle data...........8\n";
cout << " Quit...............................9\n";
cout << "*************************************************\n\n";
cout << "MENU: ";
cin >> menu_select_int;

switch (menu_select_int)
{

case 1:
cout << "\ngoing to input data function\n";
cout << "case 1";
cin.ignore();

Add a "break" statement after every case you don't want
to fall through to the next case...

-David
 
M

mlimber

YitzHandel said:
The following is an extract from my program, which I seperated out and
compiled as its own program.

The problem is that as soon as a case tests true, all the cases below
it execute as well. So if the user inputs, 4, the statements from
cases 4-9 will execute.
[snip]

You need to insert break statements after each case "body". By default
(unfortunately), switch statements fall through. Here's an example:

switch( some_int )
{
case 1:
cout << "Case 1" << endl;
break;
case 2:
cout << "Case 2" << endl;
break;
default:
cout << "Default case" << endl;
}

Cheers! --M
 
I

Ian

YitzHandel said:
The following is an extract from my program, which I seperated out and
compiled as its own program.

The problem is that as soon as a case tests true, all the cases below
it execute as well. So if the user inputs, 4, the statements from
cases 4-9 will execute.
Your forgot the "break;" after each case!

Ian
 
D

Default User

mlimber wrote:

You need to insert break statements after each case "body". By default
(unfortunately), switch statements fall through. Here's an example:



It's not "unfortunate". It would be a real pain if it didn't work that
way. That's the only way C (and so C++) can do multiple cases resolving
to the same action. If fall-through weren't there, you couldn't have
this:


switch (n)
{
case 1:
case 2:
case 3:
// do thing A
break;
case 4:
// do thing B
break;
default:
// do thing C
}



Brian
 
W

Wilton Helm

Whether it is unfortunate or not is a matter of opinion. It probably does
allow some programming techniques which are prone to bugs or aren't as
structured. On the other hand a lot of C programmers take advantage of it
for things like this excerpt from a parser:

switch(c) {

case '0' :
case '1' :
case '2' :
case '3' :
case '4' :
case '5' :
case '6' :
case '7' :
case '8' :
case '9' :
accum = 10 * accum + (c - '0');
break;

case 'S' : // Store value

// other alpha command cases

Or the situation where two cases are identical except for a line or two at
the beginning so one can fall through into the other:

case FIRST:
// some initial code
// NOTE: Falls through

case SECOND:
/// code shared between cases

In which case the wise programmer will ALWAYS place the note there pointing
out the lack of a break statement--otherwise somebody will get bit.

Wilton
 
J

Jon Slaughter

Default User said:
mlimber wrote:





It's not "unfortunate". It would be a real pain if it didn't work that
way. That's the only way C (and so C++) can do multiple cases resolving
to the same action. If fall-through weren't there, you couldn't have
this:


switch (n)
{
case 1:
case 2:
case 3:
// do thing A
break;
case 4:
// do thing B
break;
default:
// do thing C
}



Brian

um, or you could just have an "unbreak" statement that is less error prone
and still do the exact same thing?
 
J

Josce

You need to insert break statements after each case "body". By default
It's not "unfortunate". It would be a real pain if it didn't work that
way. That's the only way C (and so C++) can do multiple cases resolving
to the same action. If fall-through weren't there, you couldn't have
this:

switch (n)
{
case 1:
case 2:
case 3:
// do thing A
break;
case 4:
// do thing B
break;
default:
// do thing C
}

Talking about switch statements in general:
I would have liked the possibility to write 1..5 meaning 1,2,3,4 or 5 like:

switch (n)
{
case 1..3:
// do thing A
break;
case 4:
// do thing B
break;
default:
// do thing C
}

Josce
 
P

Peter C. Chapin

It's not "unfortunate". It would be a real pain if it didn't work that
way. That's the only way C (and so C++) can do multiple cases resolving
to the same action. If fall-through weren't there, you couldn't have
this:

One could argue that a better language design would be to allow for syntax
such as

switch (n)
{
case 1..3:
// do thing A

case 8 or 9:
// do some other thing

default:
// etc
}

Peter
 
S

Steve Fábián

Peter C. Chapin et al.:
....
One could argue that a better language design would be to allow for syntax
such as

switch (n)
{
case 1..3:
// do thing A

case 8 or 9:
// do some other thing

default:
// etc
}

There have also been proposals for "select all":

select all (n) {
case 1..3 or 5 or 9;
// do A
case 2 or 5..7 or 0;
// do B
case 1 or 6 or 9;
// do C
}

where n=1 would do first A then C, n=2 would do A,B, n=6 would do B,C, etc.
"switch" would be "select first" instead.

This would permit an enhanced version of what Wilton liked - some cases
could skip not just early, but instead any stage. It's almost an
implementation of state transition tables.

BTW, why is a multiway selection less structured than its special case, the
two-way selection? Real life problems are hardly ever structured!
 
J

JimS

One could argue that a better language design would be to allow for syntax
such as

switch (n)
{
case 1..3:
// do thing A

case 8 or 9:
// do some other thing

default:
// etc
}

Peter

Doesn't GCC support case ranges eg (1..3) as an extension already?

JimS
 
D

Default User

Josce wrote:

Talking about switch statements in general:
I would have liked the possibility to write 1..5 meaning 1,2,3,4 or 5 like:

switch (n)
{
case 1..3:
// do thing A
break;
case 4:
// do thing B
break;
default:
// do thing C
}


I would tend to agree. My guess would be that they didn't want to change
the same construct too much from the original C version. But that's just a
guess, you'd have to ask the committee.




Brian
 
C

Cesar Rabak

Default User escreveu:
Josce wrote:





I would tend to agree. My guess would be that they didn't want to change
the same construct too much from the original C version. But that's just
a guess, you'd have to ask the committee.
My guess is that for this minimum comfort we get a can of worms in the
parser design. . .
 
S

Steve Fábián

switch (n)
My guess is that for this minimum comfort we get a can of worms in the
parser design. . .

It is a "minimum comfort" if the range is 1..3, but not if it is 1005..11004
(you'd not like to list them as individual cases,would you). Yes, I know you
can do it with an "if" instead, but if/elseif/elseif/elseif... is far less
clear to the person validating the code.

Personally, I'd like to see the "select first/select all" I mentioned before
(with the ranges).
 
J

JimS

It is a "minimum comfort" if the range is 1..3, but not if it is 1005..11004
(you'd not like to list them as individual cases,would you). Yes, I know you
can do it with an "if" instead, but if/elseif/elseif/elseif... is far less
clear to the person validating the code.

Personally, I'd like to see the "select first/select all" I mentioned before
(with the ranges).

The problem is that you can't use 1..3 or 1...3 because then the way C
parsers work it will look like 1. which is a floating point number.
In GCC's case-range extension it has to look like 1 ... 3

You can always use a combination of switch/if/else, or if it all gets
a bit too hairy, use a jump table.

JimS
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,769
Messages
2,569,578
Members
45,052
Latest member
LucyCarper

Latest Threads

Top