package main import "fmt" // 定义基础接口 type Reader interface { Read() string } // 定义扩展接口(方法集包含Reader) type ReadWriter interface { Reader // 嵌入接口,继承Read()方法 Write(string) } // 实现ReadWriter接口(隐式实现Reader) type File struct { content string } func (f *File) Read() string { return f.content } func (f *File) Write(s string) { f.content = s } // 接口作为函数参数 func readData(r Reader) { fmt.Println("读取数据:", r.Read()) } func main() { // 隐式实现与接口赋值 var f *File = &File{content: "test data"} var r Reader = f // File实现Reader,可赋值 var rw ReadWriter = f // File实现ReadWriter,可赋值 fmt.Printf("Reader Read: %s\n", r.Read()) // 输出test data rw.Write("测试数据") fmt.Printf("ReadWriter Read: %s\n", rw.Read()) // 输出测试数据 // 类型断言(判断接口存储的具体类型) if file, ok := r.(*File); ok { file.Write("new data") fmt.Printf("After Write: %s\n", r.Read()) // 输出new data } // 接口作为函数参数 readData(f) // File实现了Reader接口,可以传递 // 空接口使用 var any interface{} any = 100 fmt.Printf("any type: %T, value: %v\n", any, any) // 输出int, 100 any = "hello" fmt.Printf("any type: %T, value: %v\n", any, any) // 输出string, hello // 空接口与nil的陷阱 var p *int = nil var i interface{} = p fmt.Printf("p == nil? %t, i == nil? %t\n", p == nil, i == nil) // 输出true, false // 说明: // 当一个接口变量被赋值时,它会存储两个信息: // 动态类型 (dynamic type) // 动态值 (dynamic value) // p 是一个指向 int 的指针,其值为 nil // 当将 p 赋值给接口变量 i 时: // i 的动态类型是 *int // i 的动态值是 nil(来自 p 的值) // 但是 i 本身不是 nil 接口,而是一个包含 (*int, nil) 的接口 // i (interface{}): // ├── type: *int // └── value: nil (p的值) // // p (*int): // └── value: nil var emptyInterface interface{} // 这个才是 == nil 的 fmt.Println("emptyInterface == nil?", emptyInterface == nil) }