目录
- 前言
- [if-else 分支结构](#if-else 分支结构)
- [for 循环结构](#for 循环结构)
- [for range 键值循环](#for range 键值循环)
- [switch case 多分支结构](#switch case 多分支结构)
- [Continue、Break 与 Goto](#Continue、Break 与 Goto)
- 总结

前言
流程控制是每种编程语言控制逻辑走向 和执行次序 的重要部分,可以说是一门语言的"经脉"。Go 语言中最常用的流程控制有 if
和 for
,而 switch
和 goto
主要是为了简化代码、降低重复代码而生的结构,属于扩展类的流程控制。
if-else 分支结构
基本语法
if-else
是最基础的条件判断语句,用于根据条件执行不同的代码分支。其基本结构如下:
go
if 条件表达式 {
// 条件为 true 时执行
} else if 条件表达式 {
// 第一个条件为 false,此条件为 true 时执行
} else {
// 所有条件都为 false 时执行
}
语法特点
Go 语言的 if
语句有以下几个重要特点:
- 可以省略条件表达式的小括号,这使代码更简洁
- 花括号
{}
不可省略,即使只有一行代码 - 左花括号
{
必须与if
在同一行,不能换行
示例代码
基础条件判断
go
age := 18
if age >= 18 {
fmt.Println("已成年")
} else {
fmt.Println("未成年")
}
if 的特殊用法 - 在条件表达式前声明变量
在某些特殊场景下,可以将变量的声明放置在条件表达式前。
go
// 变量 score 的作用域仅限于 if-else 块内
if score := 85; score >= 90 {
fmt.Println("优秀")
} else if score >= 60 {
fmt.Println("及格")
} else {
fmt.Println("不及格")
}
// 这里无法访问 score 变量
这种写法的优势是可以限制变量的作用域,避免变量污染外部作用域。
多条件判断
go
username := "admin"
password := "123456"
if username == "admin" && password == "123456" {
fmt.Println("登录成功")
} else if username != "admin" {
fmt.Println("用户名错误")
} else {
fmt.Println("密码错误")
}
for 循环结构
Go 语言中的所有循环类型均可以使用 for
关键字来完成,这是 Go 与其他语言的一个显著区别 - Go 中没有 while 和 do-while 语句。
基本语法
for 循环有多种形式:
go
// 完整形式
for 初始语句; 条件表达式; 结束语句 {
// 循环体
}
// 类似 while 的形式
for 条件表达式 {
// 循环体
}
// 无限循环
for {
// 循环体
}
示例代码
标准 for 循环
go
// 打印 1 到 10
for i := 1; i <= 10; i++ {
fmt.Println(i)
}
类似 while 的用法
go
i := 1
for i <= 10 {
fmt.Println(i)
i++
}
无限循环配合 break
go
count := 0
for {
count++
fmt.Println("循环次数:", count)
if count >= 5 {
break // 跳出循环
}
}
for 循环嵌套
go
// 打印九九乘法表
for i := 1; i <= 9; i++ {
for j := 1; j <= i; j++ {
fmt.Printf("%d×%d=%d\t", j, i, i*j)
}
fmt.Println()
}
for range 键值循环
for range
是 Go 语言特有的迭代结构,可用于遍历数组、切片、字符串、map 和 channel。
遍历切片
go
nums := []int{10, 20, 30, 40, 50}
// 同时获取索引和值
for index, value := range nums {
fmt.Printf("索引: %d, 值: %d\n", index, value)
}
// 只要值,忽略索引
for _, value := range nums {
fmt.Println(value)
}
// 只要索引
for index := range nums {
fmt.Println(index)
}
遍历字符串
go
str := "Hello,世界"
// range 遍历字符串时,value 是 rune 类型(Unicode 码点)
for index, char := range str {
fmt.Printf("索引: %d, 字符: %c\n", index, char)
}
遍历 map
go
userMap := map[string]int{
"Alice": 25,
"Bob": 30,
"Carol": 28,
}
for key, value := range userMap {
fmt.Printf("%s: %d岁\n", key, value)
}
switch case 多分支结构
switch
语句用于基于不同条件执行不同动作,是一种更优雅的多分支选择结构,可以替代冗长的 if-else
链。
基本语法
go
switch 变量 {
case 值1:
// 执行代码块1
case 值2:
// 执行代码块2
default:
// 所有 case 都不匹配时执行
}
示例代码
基础用法
go
day := 3
switch day {
case 1:
fmt.Println("星期一")
case 2:
fmt.Println("星期二")
case 3:
fmt.Println("星期三")
case 4:
fmt.Println("星期四")
case 5:
fmt.Println("星期五")
case 6, 7: // 一个 case 可以有多个值
fmt.Println("周末")
default:
fmt.Println("无效的日期")
}
一个分支多个值
go
score := 'B'
switch score {
case 'A', 'a':
fmt.Println("优秀")
case 'B', 'b':
fmt.Println("良好")
case 'C', 'c':
fmt.Println("及格")
default:
fmt.Println("不及格")
}
省略 switch 后的变量 - 分支使用表达式
go
age := 25
switch {
case age < 18:
fmt.Println("未成年")
case age >= 18 && age < 60:
fmt.Println("成年人")
case age >= 60:
fmt.Println("老年人")
}
这种方式类似于 if-else
链,但更加清晰。
switch 初始化语句
go
switch num := 10; {
case num > 0:
fmt.Println("正数")
case num < 0:
fmt.Println("负数")
default:
fmt.Println("零")
}
fallthrough 穿透
Go 的 switch
默认每个 case
执行完后会自动跳出(不需要 break) ,如果需要继续执行下一个 case
,需要使用 fallthrough
关键字。
go
num := 1
switch num {
case 1:
fmt.Println("case 1")
fallthrough // 强制穿透到下一个 case
case 2:
fmt.Println("case 2")
fallthrough
case 3:
fmt.Println("case 3")
default:
fmt.Println("default")
}
// 输出:
// case 1
// case 2
// case 3
注意事项:
- Go 的
switch
默认不穿透,执行完匹配的case
后自动结束 fallthrough
会无条件执行下一个case
,不判断条件fallthrough
不能用在switch
的最后一个case
中- 虽然不需要
break
,但建议标注出明晰整体逻辑
Continue、Break 与 Goto
continue 继续下一次循环
continue
语句用于跳过当前循环的剩余代码,直接开始下一次循环迭代。continue
只能在 for
循环中使用。
示例代码
跳过偶数:
go
for i := 1; i <= 10; i++ {
if i%2 == 0 {
continue // 跳过偶数,不打印
}
fmt.Println(i)
}
// 输出: 1 3 5 7 9
continue 配合标签用于嵌套循环:
go
OuterLoop:
for i := 1; i <= 3; i++ {
for j := 1; j <= 3; j++ {
if j == 2 {
continue OuterLoop // 跳过外层循环的当前迭代
}
fmt.Printf("i=%d, j=%d\n", i, j)
}
}
break 跳出循环
break
语句用于立即终止循环或 switch
语句的执行,程序会跳转到循环或 switch
之后的代码。
示例代码
跳出单层循环:
go
for i := 1; i <= 10; i++ {
if i == 5 {
break // 当 i 等于 5 时跳出循环
}
fmt.Println(i)
}
// 输出: 1 2 3 4
在 switch 中使用 break
go
score := 85
switch {
case score >= 90:
fmt.Println("优秀")
case score >= 60:
fmt.Println("及格")
if score < 70 {
fmt.Println("需要继续努力")
break // 提前退出 switch
}
fmt.Println("表现不错")
default:
fmt.Println("不及格")
}
break 结合标签跳出多层循环
在嵌套循环中,普通的 break
只能跳出当前层循环。如果需要跳出外层循环,可以使用标签。
go
OuterLoop:
for i := 1; i <= 3; i++ {
for j := 1; j <= 3; j++ {
fmt.Printf("i=%d, j=%d\n", i, j)
if i == 2 && j == 2 {
break OuterLoop // 直接跳出外层循环
}
}
}
fmt.Println("循环结束")
// 输出:
// i=1, j=1
// i=1, j=2
// i=1, j=3
// i=2, j=1
// i=2, j=2
// 循环结束
goto 无条件跳转
goto
语句可以无条件地跳转到程序中指定的标签位置。虽然 goto
可以简化某些场景的代码,但过度使用会使程序逻辑混乱,降低可读性。因此应谨慎使用。
基本语法
go
goto 标签名
标签名:
// 从这里继续执行
示例代码
简单跳转:
go
fmt.Println("开始")
goto End
fmt.Println("这行不会执行")
End:
fmt.Println("跳转到这里")
fmt.Println("程序结束")
// 输出:
// 开始
// 跳转到这里
// 程序结束
跳出多层循环:
go
for i := 0; i < 5; i++ {
for j := 0; j < 5; j++ {
if i*j > 6 {
goto BreakAll // 跳出所有循环
}
fmt.Printf("i=%d, j=%d, i*j=%d\n", i, j, i*j)
}
}
BreakAll:
fmt.Println("已跳出所有循环")
错误处理场景:
go
func processFile() error {
file, err := openFile()
if err != nil {
goto CleanUp
}
data, err := readFile(file)
if err != nil {
goto CleanUp
}
err = processData(data)
if err != nil {
goto CleanUp
}
return nil
CleanUp:
closeFile(file)
return err
}
使用注意事项
goto
不能跳转到其他函数内部goto
不能跳过变量声明语句- 应优先考虑使用其他控制结构(如
break
、continue
)代替goto
- 合理的使用场景:统一的错误处理、跳出深层嵌套循环
总结
Go 语言的流程控制简洁而强大:
- if-else: 条件分支的基础,支持在条件中声明变量
- for : 唯一的循环关键字,涵盖所有循环场景,包括传统循环、类 while 循环和
for range
迭代 - switch:优雅的多分支选择,默认不穿透,支持多值匹配和表达式判断
- break/continue:控制循环执行流程,支持标签跳转
- goto:无条件跳转,应谨慎使用
掌握这些流程控制语句,能够帮助你编写出结构清晰、逻辑严谨的 Go 程序。在实际开发中,建议优先使用 if
、for
和 switch
,只在必要时才使用 goto
,以保持代码的可读性和可维护性。
2025.10.15 西直门