我了解了一点,并且在一定程度上也了解了界面(比如我如何在 ruby 中进行 ducktyping) 但是阅读接口(interface)定义https://github.com/golang/go/wiki/CodeReviewComments
我不知道要传达什么。
第一:我没看懂评论。
Go interfaces generally belong in the package that uses values of the interface type, not the package that implements those values.
第二:我不明白这个
Do not define interfaces on the implementor side of an API "for mocking"; instead, design the API so that it can be tested using the public API of the real implementation.
第三:我不明白这个例子
Do not define interfaces before they are used: without a realistic example of usage, it is too difficult to see whether an interface is even necessary, let alone what methods it ought to contain.
package consumer // consumer.go
type Thinger interface { Thing() bool }
func Foo(t Thinger) string { ..... }
package consumer // consumer_test.go
type fakeThinger struct{ … }
func (t fakeThinger) Thing() bool { … }
if Foo(fakeThinger{…}) == "x" { ... }
// DO NOT DO IT!!!
package producer
type Thinger interface { Thing() bool }
type defaultThinger struct{ … }
func (t defaultThinger) Thing() bool { … }
func NewThinger() Thinger { return defaultThinger{ … } }
package producer
type Thinger struct{ … }
func (t Thinger) Thing() bool { … }
func NewThinger() Thinger { return Thinger{ … } }
谁能用通俗易懂的语言解释以上三件事。
最佳答案
暂时忘记与其他语言的类比。将接口(interface)想象成契约(Contract) - 使用它的功能的一组要求。
假设我定义了一个函数 MakeNoise,它需要知道传入的声音,但不关心它。下面的代码全部放在一起,但想象一下这在两个单独的包中——一个用于具体类型,一个用于 MakeNoise。
MakeNoise 函数可以采用特定类型,但这在一定程度上限制了它,可能会使测试更加困难等,因此通常您可能希望它而不是定义它需要该类型做什么 - 在这种情况下它只需要一些带有要调用的 Sound() 方法,除此之外它不关心。
现在在 Cat/Dog 方面,您可能不关心 MakeNoise,甚至还不知道它,您的动物应该单独定义并且不关心它们符合的任何接口(interface)——这些接口(interface)甚至可能还没有被编写.
所以 Wiki 只是说,编写 MakeNoise 的人应该关心它需要什么并将其放在界面中,但是编写 Cat/Dog 的人不应该关心,界面应该与 MakeNoise 一起使用,而不是与 Cat/Dog 一起使用。这意味着以后有人可能会在另一个包中编写 Giraffe,它仍然可以与 MakeNoise 一起使用。
接口(interface)是一个要求,而不是一个 promise 。
https://play.golang.org/p/4r1wiXokKMb
// Here are some types which share one function.
// They might have other functions too
package main
type Cat struct {}
func (d Cat) Sound() string {
return "miao"
}
type Dog struct {}
func (d Dog) Sound() string {
return "woof"
}
func main() {
cat := Cat{}
dog := Dog{}
MakeNoise(cat)
MakeNoise(dog)
}
// Sounder is the requirement for MakeNoise, so it lives with it.
// perhaps in a package together which knows nothing of cats and dogs.
type Sounder interface {
Sound() string
}
// MakeNoise prints the sound of the thing
// it only cares the thing makes a Sound
func MakeNoise(thing Sounder) {
println(thing.Sound())
}
关于go - 在 go wiki 中解释 go 接口(interface)定义,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/57822244/