面试题:Go 语言中 string(65) 输出的为什么不是 65?

栗子
栗子
发布时间:2026-08-25| 56人浏览过
原创

前言

很多人第一次看到 string(65),都会下意识认为输出应该是 65。但这正是这道 Go 面试题容易“坑”人的地方:它考的不是数字转字符串的日常经验,而是 Go 对字符和字符串转换的明确语义。顺着这个例子看下去,你可以分清 string(int)、rune 和数字字符串之间的区别,也能判断什么时候该用 strconv.Itoa 或 fmt.Sprintf。

很多人第一次看到 fmt.Println(string(65)),都会下意识认为输出应该是 65。但这正是这道 Go 面试题容易“坑”人的地方:它考的不是数字转字符串的日常经验,而是 Go 对字符和字符串转换的明确语义。顺着这个例子看下去,你可以分清 string(int)、rune 和数字字符串之间的区别,也能判断什么时候该用 strconv.Itoa 或 fmt.Sprintf。

这段代码到底输出什么

先看题目本身:

package main

import "fmt"

func main() {
    fmt.Println(string(65))
}

这段代码的输出不是 65,也不会报编译错误,而是:

A

原因在于,Go 里的 string() 在接收整数值做转换时,并不是把这个整数转成十进制文本,而是把它解释成一个 Unicode 代码点,再生成对应字符的字符串。

数值 65 对应的大写字母 A,因此 string(65) 的结果就是只包含一个字符的字符串 "A"。

为什么会是 A,而不是 65

这背后对应的是 Go 的一条很重要的类型转换规则:string(整数) 表示按字符编码构造字符串,不是按十进制数字形式格式化输出。

换句话说,65 在这里扮演的不是“一个待打印的数字”,而是“一个字符位置编号”。Go 会拿这个值去查对应的 Unicode code point,然后返回那个字符。

由于 65 同时也是 ASCII 中 A 的编码,所以这里最终得到的是 A。这也是为什么不少刚接触 Go 的开发者会误判:他们把“类型转换”和“格式化成数字字符串”混成了一件事,但在 Go 中,这两件事是分开的。

如果想得到字符串 65,正确写法是什么

如果你的目标确实是把整数 65 变成字符串 "65",那就应该使用专门的数字格式化方法,而不是直接写 string(65)。

用卡片对比 Go 中 string(65) 与 strconv.Itoa(65) 的不同结果
两种转换,结果完全不同把“字符转换”和“数字转字符串”拆开看,最容易避免误用。

方式一:使用 strconv.Itoa

package main

import (
    "fmt"
    "strconv"
)

func main() {
    fmt.Println(strconv.Itoa(65)) // 输出:"65"
}

这是最直接、也最常见的整数转字符串方式。

方式二:使用 fmt.Sprintf

package main

import "fmt"

func main() {
    fmt.Println(fmt.Sprintf("%d", 65)) // 输出:"65"
}

当你已经在使用格式化输出,或者需要拼接更复杂的文本时,fmt.Sprintf 也很合适。

说明 Go 中 rune、int32、字符字面量和字符串字面量关系的编辑配图
从 rune 到字符串的关系图理解 rune 和字符串的边界后,为什么会输出 A 就不再抽象。

简单区分的话:

  • string(65):按字符编码取对应字符
  • strconv.Itoa(65):转成十进制数字字符串
  • fmt.Sprintf("%d", 65):按格式化规则生成数字字符串

这种混用为什么容易出 bug

这个问题看起来只是一个小知识点,但在真实代码里很容易埋坑。比如处理用户 ID、订单编号、状态码、业务编码时,如果本来需要的是字符串形式的数字,却误用了 string(),程序依然能编译通过,但结果会悄悄变成一个字符,问题往往要到数据落库、日志排查或接口联调时才暴露出来。

Go 工具链也注意到了这一类误用。用 go vet 检查代码时,如果发现你把整数直接转成字符串,通常会给出类似提示:

conversion from int to string yields a string of one rune, 
not a string of digits (did you mean fmt.Sprint(x)?)

这段提示的重点很明确:从 int 到 string,得到的是“一个 rune 对应的字符串”,不是“数字的字符串表示”。如果你的本意是得到数字文本,应该考虑 fmt.Sprint(x)、strconv.Itoa 等方法。

因此,这类问题最值得警惕的地方不在于它会不会报错,而在于它很可能“不报错但结果不对”。

再往里看:rune、字符和字符串是什么关系

要彻底理解这个现象,需要把 Go 里的字符和字符串区分开。

在 Go 中,rune 是 int32 的别名,用来表示一个 Unicode 代码点;而字符串则是字节序列。也就是说,字符本质上是一个数值,字符串则是一段编码后的内容。

例如下面这段代码:

a := 'A'
fmt.Printf("%T, %dn", a, a) // 输出:int32, 65

这里的 'A' 不是字符串,而是字符字面量。它对应的值是 65,类型表现为 int32,也就是 rune 的底层形式。

而 "A" 才是真正的字符串字面量。于是你就能看懂前面的行为了:

  • 'A' 代表字符,其数值是 65
  • string(65) 是把代码点 65 转成字符串
  • 结果自然就是 "A"

这也是 Go 在字符处理上保持一致性的地方:整数、rune、字符串各自有明确语义,转换规则并不含糊。

记住这一条就不容易再答错

这道题的关键不在“记住答案是 A”,而在于记住背后的规则:

  1. string(整数) 会把整数当作 Unicode 代码点,得到对应字符
  2. strconv.Itoa(整数) 才是把整数转成十进制字符串
  3. 涉及 ID、编码、数字文本时,要特别留意自己需要的是字符还是数字字符串

所以,string(65) 输出 A,并不是 Go “特殊处理”了这个数字,而是它一直都在遵守统一的转换语义。面试里答对这道题不难,真正重要的是在写业务代码时别把这两类转换混在一起。

相关标签:

免责声明:本文内容仅供参考,不代表本站观点。转载或引用请注明出处。

Python 相关产品和应用

全部下载
Selenium

Selenium

4.51.0 · Windows

用于浏览器自动化和 Web 测试的 Python 工具。

scikit-learn

scikit-learn

1.9.1 · Windows

常用 Python 机器学习算法与模型评估工具库。

Black

Black

26.10.1 · Windows

强调一致性的 Python 自动代码格式化工具。

Ruff

Ruff

0.17.1 · macOS

由 Rust 编写的高速 Python 代码检查和格式化工具。

pytest

pytest

9.1.1 · Windows

简洁而强大的 Python 自动化测试框架。

FastAPI

FastAPI

0.146.0 · Windows

高性能 Python API 框架,支持类型提示和自动接口文档。

Flask

Flask

3.1.3 · Windows

轻量灵活的 Python Web 应用框架。

Django

Django

6.1.2 · Windows

成熟的 Python Web 框架,适合构建内容站点和业务系统。

Spyder

Spyder

6.1.7 · Windows

面向科学计算与数据分析的 Python 集成开发环境。

SciPy

SciPy

1.18.1 · Windows

面向科学、工程和技术计算的 Python 算法库。