Javascript: Multiple Switch Statements in a loop - javascript

I have a while loop and my requirement is to pass data to a variable based on first three characters of a string and another data into another variable based on last three characters of a string. So, I used two switch statements in a while loop and it looks like below
while (condition) {
switch (firstThreeChars) {
case 'a':
do this;
break;
case 'b':
do this...;
break;
}
switch (lastThreeChars) {
case 'x':
do this;
break;
case 'y':
do this...;
break;
}
}
I realized that code never reaches second switch because break in first switch-case releases control to while statement. Is there a way I can have multiple switch-case statements in a while loop? Perhaps something alternative to break statement..

That's incorrect; the break keywords terminate the switch statements, not the while. The problem here is that you're comparing your strings to single characters, so you're likely never matching any of the case statements.

Related

js - is it possible to have two elements on the switch condition? [duplicate]

I'm trying to convert an if statement into a switch statement using javascript. This is the working if statement:
if(!error1(num, a_id) && !error2(num, b_id) && !error3(num, c_id) && !error4(num, d_id)) {
a.innerHTML = num;
Any tips on how to put this into a switch statement would be great. Thanks
You can make this a switch, but it's unclear why you would want to. On first glance, this isn't the kind of situation (selecting amongst a set of values and doing something different for each of them) that you use switch for.
Here's how, though I don't recommend it:
switch (false) {
case !error1(num, a_id):
case !error2(num, b_id):
case !error3(num, c_id):
case !error4(num, d_id):
// Do nothing
break;
default:
a.innerHTML = num;
break;
}
This works in JavaScript, but not in most other languages that have switch. The reason it works is that the case labels are evaluated when the execution point reaches them, and they're guaranteed to be evaluated in source code order. So you're switching on the value false, which will first be tested (using strict equality, ===) against the return value of !error1(num, a_id), and then if that doesn't match, against !error2(num, a_id), etc.; if none of them matches, then they all evaluated true, and the code in the default block runs.

Switch with SINGLE case or if else

I am working on a enormous project and WebStorm inspections always offer me to transform switch constructions with single case or case + default, like this
switch (fieldInfo.Type()) {
case this.TYPE_NESTED:
changedFieldInfo.addFieldFromPrototype(proto)
break;
default:
changedFieldInfo._fieldInfo[this.FI_FIELDS] = [];
break;
}
to if else construction like this
if (fieldInfo.Type() === this.TYPE_NESTED) {
changedFieldInfo.addFieldFromPrototype(proto);
} else {
changedFieldInfo._fieldInfo[this.FI_FIELDS] = [];
}
My colleagues say that switch is more readable even if it has only one case clause, especially when checking for enumerations like TYPE in snippets above.
What does js community think about that?
Also assume that we are not going to add second case clause and to go back to a single clause very often, so maintenance issues are minor.
And one more question, is it possible to transform switch with break inside the case clause to if without using extra code, eg
switch (fieldInfo.Type()) {
case this.TYPE_NESTED:
if(smthIsTrue)
break;
changedFieldInfo.addFieldFromPrototype(proto)
break;
default:
changedFieldInfo._fieldInfo[this.FI_FIELDS] = [];
break;
}

Running functions using switch statement performance in javascript

I have a code to generate math problems with random numbers. I am using switch statement to choose which task should be generated.
function genTask(taskid) {
switch (taskid) {
case 1:
// generate some numbers
return numbers;
break;
case 2:
// generate some numbers
return numbers;
break;
// ...
}
}
I think there may be some performance issues when I add 150+ cases. Does this code go trough every case? Wouldnt it be faster if there are separate functions for every task?
function task1() {
// generate some numbers
return numbers;
}
function task2() {
// ...
}
function genTask(taskid) {
switch (taskid) {
case 1:
return task1();
break;
case 2:
return task2();
break;
// ...
}
}
Is there a faster way to do this?
First of all, you need to know where you need to use if/else or switch/case.
When you need to check 2 to 3 conditions then you can use if/elseif/else
When you need to check 5 or above then definitely use switch/case
And based on speed switch/case is faster then if/else
Let's get back to the original point,
In your case, you have 2 choices
Write all code in one switch case.
Make functions in chunk and call-in switch case.
I suggest you go with the second choice because switch case also a faster way of execution compared to other conditional checks, But when you make different functions then you can easily modify it and debug it which more help in development, and performance not compromised in that case.
One more approach is you can use a object lookup
function task1() {
// generate some numbers
return numbers;
}
function task2() {
// some task
}
const taskMap = { 1: task1, 2: task2 };
function genTask(taskid, defaultVal) {
return (taskMap[taskid] && taskMap[taskid]()) || defaultVal;
}
This will be simple object lookup, though in terms of performance it might be slower than switch case but it increases resuability and readability of the code.
In general, I think the performance of "array" is better than "if/else" or "switch". See the reference below. In your specific case, if you comparing if/else to switch, then switch is better.
Using functions will not affect the performance ( I think ), but it is better and preferable as the code will be cleaner and readable.
Reference : https://www.oreilly.com/library/view/high-performance-javascript/9781449382308/ch04.html

Jump case in Switch statement in (javascript) (updated )

I want to ask about switch case statement in javascript.
switch(ch){
case 0:
//do something, if condition match ,so go to case 2 and 3 (no need to go case 1)
//if not match, go to case 1, 2, and 3
break;
case 1:
//..
break;
case 2:
//..
break
case 3:
//...
}
In my code has 4 cases . There is a condition in case 0 that will skip case 1 and go to case 2. How can I do that?
The switch statement is an alternative to long if else statements (See the docs here). In your case, I believe that you should use the regular if statements.
// check if it passes case1
if (condition === case1) {
// check if it passes case1
if (condition === case2) {
// check if it passes case1
if (condition === case3) {
// do something here...
}
}
}
You may also use ternary operator, although it might be a bit hard to read as you add more conditions.
i think if else statement better suit your requirement. if you still want to do it in switch here's example :) :
var sw = function(cs){
switch(cs){
case 1:
console.log("case 1 !!!");
sw(3);
break;
case 2:
console.log("case 2 !!!");
break;
case 3:
console.log("case 3 !!!");
break;
}
};
sw(1);
I believe this's what you are looking for:
function Switcher(choice){
switch(choice){
case 1: console.log(1);;
case 4: console.log(4); break;
case 2: console.log(2); break;
case 3: console.log(3); break;
}
}
and then call Switcher(1) and see the O/P
I was looking at some logic related to switches in JavaScript today, the code I was looking at used a series of if and else statements however there were a bunch of shared logic cases which could be consolidated.
Additionally if and else statements are not exactly equal to switch statements because the runtime may implement them with jump tables making the order of execution faster than if and else.
Because you can only continue iteration patterns in ECMAScript you can hack up a solution which looks like jumping by encapsulating the logic in a fake loop like so:
(function(){
//In some function use this code
var test = 2;
Switch: while(true) switch(test){
case 2: test = 1; continue Switch;
case 1: test = 0; continue Switch;
default:alert(test);return;
};
//End code example
})();
The condition for while(true) can be changed to use another variable for state if you need to.
This gets the code as close to using jump tables as you can in other languages and a similar pattern can implement things like goto or duffs device
See also How can I use goto in Javascript?
Or Porting duff's device from C to JavaScript
Or this GIST https://gist.github.com/shibukawa/315765020c34f4543665

Using an array through a switch() statement in Javascript

I'm trying to develop a simplified poker game through Javascript. I've listed all possible card combinations a given player might have in its hand ordered by its value, like this:
switch(sortedHand)
{
//Pair
case [1,1,4,3,2]: sortedHand.push(1,"Pair"); break;
case [1,1,5,3,2]: sortedHand.push(2,"Pair"); break;
case [1,1,5,4,2]: sortedHand.push(3,"Pair"); break;
case [1,1,5,4,3]: sortedHand.push(4,"Pair"); break;
case [1,1,6,3,2]: sortedHand.push(5,"Pair"); break;
case [1,1,6,4,2]: sortedHand.push(6,"Pair"); break;
case [1,1,6,4,3]: sortedHand.push(7,"Pair"); break;
case [1,1,6,5,2]: sortedHand.push(8,"Pair"); break;
case [1,1,6,5,3]: sortedHand.push(9,"Pair"); break;
case [1,1,6,5,4]: sortedHand.push(10,"Pair"); break;
Even though the "sortedHand" array stores values succesfully (as I've seen through console.log), the switch() statement always returns the default case, and everyone gets an straight flush. I fear this is a matter of the literal approach I've used to declare possible array values to be compared with the whole of "sortedHand", but I don't know any better. Is it even possible to use switch() in such a manner?
You can try switching on a textual representation of the array.
switch(sortedHand.join(' '))
{
//Pair
case '1 1 4 3 2': sortedHand.push(1,"Pair"); break;
case '1 1 5 3 2': sortedHand.push(2,"Pair"); break;
case '1 1 5 4 2': sortedHand.push(3,"Pair"); break;
case '1 1 5 4 3': sortedHand.push(4,"Pair"); break;
// etc.
}
As an alternative to specifying every case directly, perhaps build a function dispatch table using an object and get rid of the switch entirely.
var dispatch = {};
// Build the table however you'd like, for your application
for (var i = 0; i < 10; i++) {
(function(i) {
var hand = ...; // Add your hand logic here
dispatch[hand] = function() { sortedHand.push(i, "Pair"); };
})(i);
}
// Execute your routine
dispatch[sortedHand.join(' ')]();
the switch() statement always returns the default case
That's because the comparison doesn't check the array contents, but the array object itself. Objects are considered equal by their identity, so nothing will be equal to an object instantiated by a literal.
Is it even possible to use switch() in such a manner?
Yes, one can use objects in switch statements, but you would have to use references in the cases. Not applicable to your problem.
In your case, I'd suggest a stringification:
switch(sortedHand.join())
{
//Pair
case "1,1,4,3,2": sortedHand.push(1,"Pair"); break;
case "1,1,5,3,2": sortedHand.push(2,"Pair"); break;
case "1,1,5,4,2": sortedHand.push(3,"Pair"); break;
case "1,1,5,4,3": sortedHand.push(4,"Pair"); break;
case "1,1,6,3,2": sortedHand.push(5,"Pair"); break;
case "1,1,6,4,2": sortedHand.push(6,"Pair"); break;
case "1,1,6,4,3": sortedHand.push(7,"Pair"); break;
case "1,1,6,5,2": sortedHand.push(8,"Pair"); break;
case "1,1,6,5,3": sortedHand.push(9,"Pair"); break;
case "1,1,6,5,4": sortedHand.push(10,"Pair"); break;
but I guess there's an even better, arithmetic solution to detect the patterns you're after. That would be shorter and faster, but I'm not sure what exactly this snippet is supposed to do.
a faster, potentially reusable, and more flexible way of doing it is to use an object instead of case:
var ok= {
'1 1 4 3 2':1,
'1 1 5 3 2':2,
'1 1 5 4 2':3,
'1 1 5 4 3':4
}[ sortedHand.join(' ') ] ;
if(ok){ sortedHand.push( ok ,"Pair"); }
objects work great when one output is hinged on one input. if you need to do five things in each case, then you have to use case, but if you just need X to turn into Y, (a 1:1), Look Up Tables in the shape of Objects are ideal.
i imagine a RegExp can work here, i used them on a connect4 game to identify 4 in a row, but the above logic table should work as well or better than what you describe.
That will not quite work as you have it, but you can use sortedHand.join(',') and compare it with [1,1,1,2,5].join(',') which will compare the two arrays and should be true if their contents were the exact same (Be careful with numbers typed as strings!)
To be fair, though, I can't imagine why you would design your logic like that. Even a simple card game has hundreds of thousands of possible hands. You might do better using underscore.js's collection managing functions as it will be simpler, and just a better practice.
There are 1274 possible combinations of 5 cards in a regular deck. Listing them all out in a switch statement is completely ridiculous. Why not just have a function count any duplicates to check for 2,3,4-of-a-kinds and then check for straights? (Your array doesn't show suit so I'm assuming you are leaving it out).
But if you really want to do it that way, you could use a string. Strings work with switches, and you can even use them like arrays. e.g. "123"[0] == '1'. You can change them back and forth user functions like parseInt.
Since no one suggested this, use a for loop and count the number of cards with exactly the given value. Having such a function you can call 'cardCount = count(sortedHand, cardNumber)'. And of cause looping through all possible card-numbers will give you the hands.
Since a given player can only have 1x2, 2x2, 1x3, 1x3+1x2, 1x4 or straights/streets, you can return an array of all hits being arrays/objects stating the count and the cardNumber involved. So [{2, 5}, {3, 6}] for a full house.

Categories

Resources