我尝试检查Golang何时将本地值返回为nil,然后我使用此代码。
package main
import (
"fmt"
)
type S struct{}
func InitEfacePointer() interface{} {
var s *S
println(s)
return s
}
func main() {
s := InitEfacePointer()
fmt.Println(s)
//println(s)
}
输出是 为0x0
但是当我只使用println输出值时。
package main
type S struct{}
func InitEfacePointer() interface{} {
var s *S
println(s)
return s
}
func main() {
s := InitEfacePointer()
println(s)
}
输出更改为 为0x0 (0x93d40,0x0)
有人能解释一下这种行为的机制吗?谢谢!
答案 0 :(得分:3)
你不应该使用builtin println,它明确指出:
println内置函数将其参数格式化为 特定于实现的方式并将结果写入标准错误。 始终在参数之间添加空格,并附加换行符。 Println对于引导和调试很有用;它不是 保证保持语言。
spec也提到:
当前的实现提供了几个有用的内置函数 在自举期间。记录这些功能是为了完整性 但不保证保持语言。他们没有返回 结果
实施限制:不需要打印和打印 接受任意参数类型,但打印boolean,numeric和 必须支持字符串类型。
就是这样。 print
和println
是有用的调试工具,但不应该依赖于:
那就是说,我猜你的情况是打印内部接口字段:指向类型的指针和值。
答案 1 :(得分:1)
首先,fmt.Println
和内置println
是完全不同的问题:它们在实现和目的上都是不同的。 fmt.Println
使用反射处理许多复杂的情况,println
只处理一些基本情况,仅用于“引导或调试”(如规范所述)。
在这种特定情况下,您正在打印从interface{}
返回的InitEfacePointer()
。 fmt.Println
使用reflect查看接口并获取基础数据:指向字符串的nil指针,然后将其打印出来:0x0
。另一方面,内置println
采用接口和编译器的魔力(或不是),它识别它是一个接口。作为this post,golang接口实际上是两个指针,一个指向存储类型的信息,另一个指向底层数据。因此内置println
进入界面细节,0x93d40
是“类型信息”,0x0
是底层数据。 (第一个0x0
来自函数调用)。
此外,测试返回的接口是否为nil
似乎是一个常见的错误。请在此处阅读:https://golang.org/doc/faq#nil_error