多态
多态是一个比较好理解的概念,直接看测试代码 1,感受一下
package polymorphism
import (
"fmt"
"testing"
)
type Code string
type Programmer interface {
WriteHelloWorld() Code
}
type GoProgrammer struct {
}
func (p *GoProgrammer) WriteHelloWorld() Code {
return "fmt.Println(\"Hello World!\")"
}
type JavaProgrammer struct {
}
func (p *JavaProgrammer) WriteHelloWorld() Code {
return "System.out.println(\"Hello World!\")"
}
// %T 输出传入参数的类型
func writeFirstProgram(p Programmer) {
fmt.Printf("%T %v\n", p, p.WriteHelloWorld())
}
func TestPolymorphism(t *testing.T) {
goProg := new(GoProgrammer)
javaProg := new(JavaProgrammer)
writeFirstProgram(goProg) // *polymorphism.GoProgrammer fmt.Println("Hello World!")
writeFirstProgram(javaProg) // *polymorphism.JavaProgrammer System.out.println("Hello World!")
}
空接口和断言
空接口可以表示任何类型
通过断言来讲空接口转换为指定类型
v, ok := p.(int) // ok=true 时为转换成功
测试实例 2
package empty_interface
import (
"fmt"
"testing"
)
func DoSomeThing(p interface{}) {
//if i, ok := p.(int); ok {
// fmt.Println("Integer ", i)
// return
//}
//if i, ok := p.(string); ok {
// fmt.Println("String ", i)
// return
//}
//fmt.Println("Unknown Type")
switch v := p.(type) {
case int:
fmt.Println("Integer ", v)
case string:
fmt.Println("String ", v)
default:
fmt.Println("Unknown Type")
}
}
func TestEmptyInterfaceAssertion(t *testing.T) {
DoSomeThing(10) // Integer 10
DoSomeThing("10") // String 10
}
Go 接口最佳实践
倾向于使用小的接口定义,很多接口只包含一个方法
type Reader interface { Read(p []byte) (n int, err error) } type Write interface { Write(p []byte) (n int, err error) }
较大的接口定义,可以由多个小接口定义组合而成
type ReadWriter interface { Reader Writer }
只依赖于必要功能的最小接口
func StoreData(reader Reader) error { ... }