switch语句会先对一个表达式求值,然后运行第一个与该值匹配的case。相比冗长的if ... else if链,它往往是更简洁的选择。
operatingSystem := "windows"
switch operatingSystem {
case "windows":
// do something if the operating system is windows
case "linux":
// do something if the operating system is linux
case "macos":
// do something if the operating system is macos
default:
// do something if the operating system is none of the above
}
可以用逗号把多个值合并到同一个case里。只要表达式的值等于其中任意一个,这个case就匹配:
switch operatingSystem {
case "windows", "linux":
// do something if the operating system is windows or linux
case "macos":
// do something if the operating system is macos
default:
// do something if the operating system is none of the above
}
switch后面的表达式也可以完全省略。此时每个case里都是一个布尔表达式,第一个求值为true的case会被执行。
age := 21
switch {
case age > 20 && age < 30:
// do something if age is between 20 and 30
case age == 10:
// do something if age is equal to 10
default:
// do something else for every other case
}
和if一样,switch也可以在表达式前面加上一条简短的初始化语句。在那里声明的变量,作用域只限于这个switch代码块:
switch v := getValue(); {
case v < 0:
// do something if v is less than 0
case v == 0:
// do something if v is 0
default:
// do something else for every other case
}
// v will not be accessible here
fallthrough会让下一个case的主体执行,不管它的表达式是否匹配。它必须是该case主体里的最后一条语句,而且后面必须还有一个case可以执行。
在地道的 Go 代码里,fallthrough并不常见,因为它会让相邻的case互相依赖。这样一来,也就更难单独理解每个case,整个 switch 也更难读。如果几个case应该有相同的行为,用逗号把它们分组会更清楚。如果各个case因为其他原因共享逻辑,可以考虑把共享的逻辑提取成一个辅助函数。
s := "hello"
switch s {
case "hello":
fmt.Println("hello")
fallthrough
case "world":
fmt.Println("world") // also runs, even though s != "world"
}
// Output:
// hello
// world
想了解更多,可以看看 Go by Example: Switch 或 Go 语言规范。