Author Topic: IF vs CASE  (Read 4308 times)

Offline John

  • Forum Support / SB Dev
  • Posts: 1758
    • ScriptBasic Open Source Project
IF vs CASE
« on: February 22, 2012, 02:21:15 PM »
Quote
I have not done any timing tests but currently Bcx translates this:

James,

ScriptBasic doesn't have a SELECT/CASE structure but it's IF/THEN/ELSEIF/ELSE/ENDIF allows unlimited nesting so I'm fine without it.

John

Marcus

  • Guest
IF vs CASE
« Reply #1 on: February 23, 2012, 02:52:58 AM »
Naalaa doesn't have select/switch either. They have no impact on speed unless you restrict the selectors to be constants and implement jump table like thingies (in the vm case). They do make code more readable though :)

James, as you translate your select/case to if statements, I assume bcx supports non-constant cases?
« Last Edit: February 23, 2012, 02:58:28 AM by Marcus »

jcfuller

  • Guest
IF vs CASE
« Reply #2 on: February 23, 2012, 09:32:44 AM »
John,
  I think SELECT/CASE for multiples is easier to code and understand.


Marcus,
  I guess this is what you are asking?

James


Code: [Select]
$ONEXIT "GCTDC.BAT $FILE$ -m32"

SET IA[] As int
    0,1,2,3,4,5,6,7,8,9
END SET

SET B$[]
    "apples",
    "oranges",
    "pears",
    "cabbage",
    "peas",
    "beans"
END SET

Dim A$
Dim N As int
A$ = "peas"

SELECT CASE A$
    CASE B$[0],B$[1],B$[2]
        Print "Fruit"
    CASE B$[3],B$[4],B$[5]
        Print "veggie"    
End Select
N=6
SELECT CASE N
    CASE 1 TO 5
        Print "Greater Than zero and less than 6"
    CASE IA[8]
        Print "Is it eight?"
    CASE IA[6] TO IA[7]
        Print " 6-7"
    CASE ELSE
        Print "A problem"            
End Select
Pause

translates to
Code: [Select]
..snip....

static int     N;
static char    A[cSizeOfDefaultString];
static int IA[]=
  {
 0,1,2,3,4,5,6,7,8,9
};

static char   B[][cSizeOfDefaultString]=
  {
 "apples",
 "oranges",
 "pears",
 "cabbage",
 "peas",
 "beans"
};


int main(int argc, char *argv[])
{
strcpy(A,"peas");
if(str_cmp(A,B[0])==0 ||  str_cmp(A,B[1])==0 ||  str_cmp(A,B[2])==0)
  {
    printf("%s\n","Fruit");
    goto L1000;
  }
if(str_cmp(A,B[3])==0 ||  str_cmp(A,B[4])==0 ||  str_cmp(A,B[5])==0)
  {
    printf("%s\n","veggie");
  }
L1000:; // SelectState[PusherSelectState].CaseFlag 2
N= 6;
if(N>=1&&N<=5 )
  {
    printf("%s\n","Greater Than zero and less than 6");
    goto L1001;
  }
if(N==IA[8])
  {
    printf("%s\n","Is it eight?");
    goto L1001;
  }
if(N>=IA[6]&&N<=IA[7])
  {
    printf("%s\n"," 6-7");
  }
else // case else
  {
    printf("%s\n","A problem");
  }
L1001:; // SelectState[PusherSelectState].CaseFlag 3
Pause();
  return 0;   /* End of main program */
}


Marcus

  • Guest
IF vs CASE
« Reply #3 on: February 25, 2012, 02:48:20 AM »
Yes, that's much more flexible than c's switch/case. Maybe I'll add this to naalaa :)

Offline John

  • Forum Support / SB Dev
  • Posts: 1758
    • ScriptBasic Open Source Project
IF vs CASE
« Reply #4 on: February 25, 2012, 09:49:58 AM »
Quote from: jcfuller
I think SELECT/CASE for multiples is easier to code and understand.

BCX SELECT/CASE

Code: [Select]
SELECT CASE N
    CASE 1 TO 5
        Print "Greater Than zero and less than 6"
    CASE IA[8]
        Print "Is it eight?"
    CASE IA[6] TO IA[7]
        Print " 6-7"
    CASE ELSE
        Print "A problem"            
End Select

ScriptBasic IF Structure

Code: [Select]
IF N > 0 AND N < 6 THEN
  PRINT "Greater Than zero and less than 6\n"
ELSEIF N = IA[8] THEN
  PRINT "Is it eight?\n"
ELSEIF N >= IA[6] AND N <= IA[7] THEN
  PRINT " 6-7\n"
ELSE
  PRINT "A problem\n"            
ENDIF

I don't see the improved readability with SELECT/CASE.
 


« Last Edit: February 25, 2012, 09:52:49 AM by JRS »

Marcus

  • Guest
IF vs CASE
« Reply #5 on: February 25, 2012, 01:19:48 PM »
I like the select/case struct in basic (bcx), it does look more clear. But if I added it to naalaa it would be in combination with jump tables (at a vm level), and then the struct would be as limited as in c. It would give some extra speed.

And when implementing a vm the c switch/case is much faster than if/else if. The only thing faster is direct branching, and my point is that we can use that if the c compilers supports pointers to labels.
« Last Edit: February 25, 2012, 01:23:00 PM by Marcus »

Offline John

  • Forum Support / SB Dev
  • Posts: 1758
    • ScriptBasic Open Source Project
IF vs CASE
« Reply #6 on: February 25, 2012, 07:20:39 PM »
Quote from: Marcus
I like the select/case struct in basic (bcx), it does look more clear.

It really doesn't matter how many helper functions a translator based language has because it's just text and what ends up as C code is what counts. I don't think Peter Verhas could justify adding a duplicate flow structure with a slightly different syntax and keep the interpreter under 500 KB.

That said, the IF structure is more flexible by dynamically changing the CASE compare value(s) and satisfying multiple ELSEIF branches where SELECT sets CASE in the beginning and becomes a constant.

As James has shown, BCX translates it's SELECT/CASE to IF/ELSE C structures. Would BCX create less code if IF was used in the first place?
  
« Last Edit: February 27, 2012, 12:53:07 AM by JRS »

Offline drogon

  • BASIC Developer
  • Posts: 4
    • Drogon Projects
Re: IF vs CASE
« Reply #7 on: September 02, 2013, 04:44:58 AM »
Adding my 2 pennith here...

I included switch/case support into RTB more to see what it would look like than anything else ... It is marginally faster than multiplly nested if/else if/endif type statements though, but I do wonder if it's actually more wordy than that...

An example is:

Code: [Select]
    key = INKEY
    SWITCH (key)
      CASE KeyUp
        xSpeed = 0
        ySpeed = snakeDia
      ENDCASE
      CASE KeyDown
        xSpeed = 0
        ySpeed =  - snakeDia
      ENDCASE
      CASE KeyLeft
        xSpeed =  - snakeDia
        ySpeed = 0
      ENDCASE
      CASE KeyRight
        xSpeed = snakeDia
        ySpeed = 0
      ENDCASE
    ...
    ENDSWITCH

I allow for multiple values on CASE statments separated by commas and there is a DEFAULT case too. What I don't allow is "dropping through" from one case statement to the next, although I could add it in...

It works by evaluating the expression in the SWITCH statement (once), then just performing comparisions (string or numeric) against each CASE value. I don't have provision for ranges, so the example above which looked like:

Code: [Select]
  CASE 1 TO 5

would look like:

Code: [Select]
  CASE 1,2,3,4,5

So it's an interesting construct - possible aiding the "structured programming" approach, or improving readability - with the improvement in program execution time vs. a few more lines of typing...

-Gordon

Offline John

  • Forum Support / SB Dev
  • Posts: 1758
    • ScriptBasic Open Source Project
Re: IF vs CASE
« Reply #8 on: September 02, 2013, 10:14:07 PM »
When I have to convert a SELECT/CASE block to an IF structure this how your example would look in SB.

Code: [Select]
CASE = key
  IF CASE = KeyUp THEN
        xSpeed = 0
        ySpeed = snakeDia
  ELSEIF CASE = KeyDown THEN
        xSpeed = 0
        ySpeed =  - snakeDia
  ELSEIF CASE = KeyLeft THEN
        xSpeed =  - snakeDia
        ySpeed = 0
  ELSEIF CASE = KeyRight THEN
        xSpeed = snakeDia
        ySpeed = 0
  ELSE
       ' Default CASE
  ENDIF