if..else if..else.. 的简化版本:
switch (a) {case 2:// 执行一些代码break;case 42:// 执行另外一些代码break;default:// 执行缺省代码}
switch有一些陷阱:
首先,a 和 case 表达式的匹配算法与 ===相同。通常 case 语句中的 switch 都是简单值,所以这并没有问题。然而,有时可能会需要通过强制类型转换来进行相等比较(即 ==),这时就 需要做一些特殊处理:
var a = "42";switch (true) {case a == 10:console.log( "10 or '10'" );break;case a == 42:console.log( "42 or '42'" );break;default:// 永远执行不到这里console.log("default")}// 42 or '42'
除简单值以外,case 中还可以出现各种表达式,它会将表达式的结果值和 true 进行比较。 因为 a == 42 的结果为 true,所以条件成立。
尽管可以使用 ==,但 switch 中 true 和 true 之间仍然是严格相等比较。即如果 case 表达式的结果为真值,但不是严格意义上的 true,则条件不成立。所以,在这里使用 || 和 && 等逻辑运算符就很容易掉进坑里:
var a = "hello world";var b = 10;switch (true) {case (a || b == 10):console.log( "a || b" );// 永远执行不到这里break;default:console.log( "Oops" );}// Oops
因为(a || b == 10)的结果是"hello world"而非true,所以严格相等比较不成立。此时可以通过强制表达式返回 true 或 false,如 case !!(a || b == 10):
最后,default 是可选的,并非必不可少(虽然惯例如此)。break 相关规则对 default 仍然适用:
var a = 10;switch (a) {case 1:case 2:// 永远执行不到这里default:console.log( "default" );case 3:console.log( "3" );break;case 4:console.log( "4" );}// default// 3
上述代码:首先遍历并找到所有匹配的 case,如果没有匹配则执行default中的代码。因为其中没有break,所以继续执行已经遍历过的case 3代码块,直到 break 为止。一般不这样写,如果确实需要这样,建议做好注释。
