本篇基于 Go 1.25.1 版本,带你彻底理解 Go 字符串的 UTF-8 编码、rune 类型、中文/Unicode 处理,再也不乱码✅
一、核心先记住(超重要)
- 1. Go 字符串默认 = 只读字节流(UTF-8 编码)
- 2. 一个中文 ≠ 1 个字节(中文占 3 字节)
- 3. rune = Go 里的 Unicode 字符(int32 别名)
- 4. 遍历字符串必须转 []rune,否则中文会乱码
二、关键概念对照表(收藏)
| 概念 | 含义 | 大小 | 作用 |
|---|---|---|---|
| byte | 字节 | 8位 | 处理原始二进制、ASCII |
| rune | Unicode 字符 | 32位 | 处理中文、 emoji、任意语言文字 |
| string | 只读 UTF-8 字节序列 | - | 存储文本 |
| UTF-8 | 变长编码 | 1~4字节 | Go 字符串默认编码 |
三、字符串本质
Go 字符串 本质是 []byte,但内容默认采用 UTF-8 编码 存储。
s := "Go 学习"
// 存储形式:G o 空 学(3字节) 习(3字节)四、rune 类型是什么?
rune = int32 的别名
专门表示 一个 Unicode 字符
中文、英文、emoji、日文都能用它表示。
var r rune = '学'五、最常见坑:遍历字符串
错误方式(按 byte 遍历 → 中文乱码)
s := "Go学习"
for i := 0; i < len(s); i++ {
fmt.Printf("%c ", s[i]) // 中文乱码!
}正确方式(for range 自动按 rune 遍历)
s := "Go学习"
for _, r := range s {
fmt.Printf("%c ", r) // G o 学 习 ✅
}最强方式(转 []rune)
rs := []rune(s)六、完整可运行 Demo(全覆盖、直接跑)
main.go 零语法错误,包含 Unicode、UTF-8、rune 全套演示👇
package main
import (
"fmt"
"unicode/utf8"
)
func main() {
str := "Go 学习 🚀"
fmt.Println("===== 1. 字符串长度(字节数) =====")
fmt.Println("len(str) =", len(str)) // 字节长度
fmt.Println("\n===== 2. 字符个数(rune 数) =====")
fmt.Println("字符数 =", utf8.RuneCountInString(str))
fmt.Println("\n===== 3. 正确遍历(for range) =====")
for idx, r := range str {
fmt.Printf("索引:%d, 字符:%c\n", idx, r)
}
fmt.Println("\n===== 4. 转 []rune =====")
runes := []rune(str)
fmt.Printf("rune 切片长度:%d\n", len(runes))
for i, r := range runes {
fmt.Printf("第%d个字符:%c\n", i, r)
}
fmt.Println("\n✅ Unicode / UTF-8 / rune 演示完成!")
}运行命令
go run main.go运行结果
===== 1. 字符串长度(字节数) =====
len(str) = 14
===== 2. 字符个数(rune 数) =====
字符数 = 7
===== 3. 正确遍历(for range) =====
索引:0, 字符:G
索引:1, 字符:o
索引:2, 字符:
索引:3, 字符:学
索引:6, 字符:习
索引:9, 字符:
索引:10, 字符:🚀
===== 4. 转 []rune =====
rune 切片长度:7
第0个字符:G
第1个字符:o
第2个字符:
第3个字符:学
第4个字符:习
第5个字符:
第6个字符:🚀
✅ Unicode / UTF-8 / rune 演示完成!七、高频实用工具
- 1. 获取字符数(非字节)
utf8.RuneCountInString(s) - 2. 字符串转 rune 切片
rs := []rune(s) - 3. 判断是否 UTF-8
utf8.ValidString(s)
八、新手避坑指南
- 1. ❌ len(中文串) ≠ 字符个数
- 2. ❌ 按索引遍历字符串会把中文拆成字节(乱码)
- 3. ✅ 处理中文/Unicode 一定用 rune
- 4. ✅ 遍历字符串用 for range 或 []rune
- 5. ✅ Go 字符串天然 UTF-8,无需手动转码
📌 总结
- 1. Go 字符串 = 只读 UTF-8 字节数组
- 2. rune = int32 = 一个 Unicode 字符
- 3. len() 求字节数,utf8.RuneCount 求字符数
- 4. 遍历中文必须用 for range 或 []rune
- 5. 中文占 3 字节,emoji 占 4 字节
一篇搞定 Go 字符串 Unicode / UTF-8 / rune,国际化文本随便处理✨
MiaoAll