Golang Range语句详解
我在学习Golang的range语句时遇到了一些困惑:
- range语句在遍历不同数据结构(数组、切片、map、字符串、channel)时具体有什么区别?
- range返回的第二个值(索引/键)在什么情况下可以忽略?
- 使用range遍历map时顺序是随机的吗?如何保证固定顺序遍历?
- 在遍历过程中修改被遍历的数据结构会有什么影响?特别是对slice和map的操作。
- range遍历字符串时是按字节还是按rune处理的?如何处理多字节字符?
- range在性能上有什么需要注意的地方?和传统的for循环相比如何? 希望有经验的开发者能帮忙解答这些疑问。
2 回复
Golang的range用于迭代数组、切片、字符串、map和通道。
- 数组/切片:返回索引和值
- 字符串:返回字符索引和Unicode值
- map:返回键和值
- 通道:迭代接收值直到关闭
注意:range返回的是副本,修改需通过索引或指针。
更多关于Golang Range语句详解的实战系列教程也可以访问 https://www.itying.com/category-94-b0.html
Golang 中的 range 语句用于遍历数组、切片、字符串、映射(map)或通道(channel)中的元素。它提供了一种简洁的方式来迭代这些集合类型,并返回索引(或键)和值。
基本语法
for index, value := range collection {
// 使用 index 和 value
}
- 对于数组、切片和字符串,
index是当前元素的索引(从 0 开始),value是元素的值。 - 对于映射,
index被替换为键(key),value是对应的值。 - 对于通道,只返回一个值(元素值),没有索引。
使用示例
1. 遍历数组或切片
nums := []int{10, 20, 30}
for i, num := range nums {
fmt.Printf("索引: %d, 值: %d\n", i, num)
}
输出:
索引: 0, 值: 10
索引: 1, 值: 20
索引: 2, 值: 30
2. 遍历字符串
遍历字符串时,range 返回每个 Unicode 字符的起始字节索引和 rune 值:
str := "Go语言"
for i, ch := range str {
fmt.Printf("索引: %d, 字符: %c\n", i, ch)
}
输出:
索引: 0, 字符: G
索引: 1, 字符: o
索引: 2, 字符: 语
索引: 5, 字符: 言
3. 遍历映射
m := map[string]int{"a": 1, "b": 2}
for key, value := range m {
fmt.Printf("键: %s, 值: %d\n", key, value)
}
注意:映射的迭代顺序是不确定的。
4. 遍历通道
range 会从通道持续接收值,直到通道被关闭:
ch := make(chan int, 2)
ch <- 1
ch <- 2
close(ch)
for v := range ch {
fmt.Println(v)
}
输出:
1
2
省略索引或值
如果不需要索引或值,可以使用下划线 _ 忽略:
// 只取值
for _, num := range nums {
fmt.Println(num)
}
// 只取索引
for i := range nums {
fmt.Println(i)
}
注意事项
- 遍历映射时顺序随机。
- 字符串遍历按 rune 进行,非字节。
- 通道遍历需确保最终关闭,否则会导致死锁。
- 修改遍历中的集合可能导致意外行为(如映射)。
range 是 Go 中处理集合迭代的高效且简洁的方式。

