为什么没有类型不匹配错误?
我将用户输入的数字定义为var input float64
,我输入一个整数,我希望得到一个错误,但我得到err = <nil>
。我错过了什么?为什么没有类型不匹配错误?
package main
import (
"fmt"
)
func main() {
var input float64
fmt.Print("Enter a number:")
n, err := fmt.Scanf("%f\n", &input)
fmt.Printf("err = %v\n", err)
if err != nil {
fmt.Printf("%v is not a float - exiting with error\n", input, err)
return
}
fmt.Printf("n is %v:", n)
}
这是输出:
C:\Go\src\play\exercise>go run exercise2.go
Enter a number to take its square root: 1
err = <nil>
n is 1:
在GO编程语言规范
具体规则适用于数字 类型之间(非恒定)的转换。数值类型
对于非恒定数值的转换之间
换算,以下规则 适用:
- 当整数类型之间的转换,如果该值是一个带符号的 整数,它将符号扩展为隐式无限精度; 否则为零扩展。然后将其截尾以适应 结果类型的大小。例如,如果v:= uint16(0x10F0),则 uint32(int8(v))== 0xFFFFFFF0。转换始终会生成有效的 值;没有溢出的迹象。
- 将浮点数转换为整数时,会丢弃部分 (截断为零)。
- 将整数或浮点数转换为浮点型 或将复数转换为另一个复杂类型 时,结果值四舍五入为由目标类型 指定的精度。例如,类型为 float32的变量x的值可以使用超出IEEE-754 32位数字的附加精度来存储,但是float32(x)表示 将x的值舍入为32位精度的结果。同样,x + 0.1可能会使用多于32位精度的 ,但float32(x + 0.1)不会。
在涉及浮点或复杂 值,如果结果类型不能代表转换 成功的值,但结果值是依赖于实现的所有非恒定的转换。
在Go中,您可以从整数类型转换为浮点类型。因此,没有理由不宽容。
在计算中,稳健性原则,是一个普遍的设计指导 软件:
在你做什么保守的,在你从别人 接受什么样的自由主义(通常改写为“在你发送的内容中保守,在你接受的内容中是自由主义的” )。
原则也被称为Postel的法律,互联网先驱 乔恩·波斯特尔,谁在传输 控制协议的早期规范写道之后:1
TCP实现应该遵循稳健性的一般原则:是保守在你做什么,在你自己接受别人的东西时是自由的。接收输入
换句话说,代码发送命令或数据的其它机器(或 在同一台机器上的其他程序)应该完全符合 规格,但代码应该接受 不符合的输入,只要因为意思很清楚。
并且只是为了完整性,来自golang规范:http://golang.org/ref/spec#Floating-point_literals – pkuderov
这实际上并没有回答这个问题 – ispilledthejava
SCANF扫描文本读取标准输入,存储连续空间分隔值成连续的参数如由格式决定。 它返回成功扫描的项目数。
Scanf返回它读取的东西的数量。在这种情况下n == 1,因为...您输入了一个标记后跟一个换行符。据推测,你想要input
的价值,而不是n
。
你知道1是一个完全有效的浮点数吗? – fuz
不,我不知道。我认为浮点数需要用小数写出。按照我的想法,'1.0'不应该给出错误,而应该是'1'。例如,在Mark Summerfield关于Go的书中,“浮点数用小数点写成......” – Zeynel
我认为@FUZxxl试图说的是“1”可以完美地表示为浮点数,即'1.0'。 '%f'格式应该读取包含小数点的浮点数。这可能是一个方便的事情,因为如果所有的需求都是“1”,人们可能不想输入“1.0”,但是我会对包含实际证据的更完整的答案感兴趣;) – fresskoma