常量不允许溢出

题目:

题一:

1
2
3
4
5
6
7
8
package main

func main() {
var a int8 = -1
var b int8 = -128 / a

println(b)
}

题二:

1
2
3
4
5
6
7
8
package main

func main() {
const a int8 = -1
var b int8 = -128 / a

println(b)
}

它们分别输出什么?

答案:

​ 其实这是一道计算机基础题。

题一

​ 因为 var b int8 = -128 / a 不是常量表达式,因此 untyped 常量 -128 隐式转换为 int8 类型(即和 a 的类型一致),所以 -128 / a 的结果是 int8 类型,值是 128,超出了 int8 的范围。因为结果不是常量,允许溢出,128 的二进制表示是 10000000,正好是 -128 的补码。所以,第一题的结果是 -128。

题二

​ 对于 var b int8 = -128 / a,因为 a 是 int8 类型常量,所以 -128 / a 是常量表达式,在编译器计算,结果必然也是常量。因为 a 的类型是 int8,因此 -128 也会隐式转为 int8 类型,128 这个结果超过了 int8 的范围,但常量不允许溢出,因此编译报错。


常量不允许溢出
http://example.com/2023/09/20/Go每日一题/常量不允许溢出/
作者
Feng Tao
发布于
2023年9月20日
更新于
2023年9月23日
许可协议