hazelmouse
hazelmouse

Reputation: 381

What is the purpose of boolean switch statements in JavaScript?

I just encountered a boolean switch statement in someone else's JavaScript code. It looked a little bit like this:

switch (a || b) {
  case true:
    // do some stuff
  break;
  default:
    // do other stuff
  break;
}

I haven't been programming for very long, but I certainly have never seen anything like this before. It seems kind of stupid, but I would like to give the programmer the benefit of the doubt. Is there any functional difference between the above code and the following:

if (a || b) {
  // do some stuff
}
else {
  // do other stuff
}

And if there is, what is it?

Upvotes: 8

Views: 7090

Answers (5)

annakata
annakata

Reputation: 75862

To be clear this case looks abusive, but since Javascript isn't strongly typed in principle it can be valuable where you can't control the input:

switch (foo)
{
    case true:
        // whatever
        break;
    case false:
        // whatever
        break;
    default:
        // FOO IS NOT A BOOLEAN, DO SOMETHING ELSE!
        break;
}

As well as Andrew's mixed case. This is a bit safer than a simple if/else, and more concise than some kind of boolean checking and then an if/else.

Upvotes: 2

Andrew Whitaker
Andrew Whitaker

Reputation: 126072

Updated after Andy's comment and answer There's no difference (in your example), but in your example, the if block is more readable and makes more sense in that case (in my opinion).

switching on a statement that evaluates to a boolean seems wrong just because there will always only be two cases (true and false), and for this reason I'd recommend the if block instead.

switch makes more sense when you're evaluating a variable that could have many values:

switch(fruitType) {
    case 'Apple':
    // Apple Code
    break;
    case 'Orange':
    // Orange Code
    break;
    // etc...
    default: // other fruit
    break;
}

Hope that helps!

Upvotes: 1

Andy E
Andy E

Reputation: 344675

Yes, there's a difference. Taking your example into account,

var a = 0,
    b = 1;

Now let's look at the switch statement:

switch (a || b) {

When this switch statement is run, the expression a || b is evaluated. || is a short-circuit operator, it will return the left operand's value if it's "truthy", else it will return the right operand's value. In this case, a = 0, so b will be returned (1). Now look at the case statement:

case true:

When evaluating case statements, no type coercion is performed on either value and strict equality is assumed. In our example, this is the same as writing 1 === true, so the code following the case statement is never run. So let's take a look at the if statement:

if (a || b) {

For an if statement, the conditional expression a || b is evaluated and then the result is converted to a boolean. Internally, this looks like ToBoolean(a || b). Since a || b evaluates to 1 and coercion of 1 to a boolean is true, the condition passes and the block executes.

A better equivalent would be:

if ((a || b) === true) {
    // do some stuff
}
else {
    // do other stuff
}

As already pointed out, in situations where there are many cases and types could vary, a switch statement could be useful. Such a situation would be rare, however.

Upvotes: 8

mpdonadio
mpdonadio

Reputation: 2941

Your example doesn't show it, but I think that this may make for more concise code if you want to use a fallthrough (ie, no break) in the first case, depending on the situation.

It also may be a decent construct if you are implementing something in a way that anticipates potential changes and want to have minimal rework (eg, want to keep the actions the same while just redoing the selection logic).

Upvotes: 0

David Hellsing
David Hellsing

Reputation: 108500

In your example, there is no difference. But depending on how a and b is defined, you could add more switch statements later on, f.ex:

var a = false, b = null;
switch (a || b) {
  case true:
    // do some stuff
  break;
  case null:
    // do some stuff
  break;
  default:
    // do other stuff
  break;
}

Other than that, it's mostly a matter of coding preference.

Upvotes: 0

Related Questions