Go 中公共接口的意义是什么?

dmz*_*rsk -2 go

https://github.com/golang/go/wiki/CodeReviewComments#interfaces说:

Go 接口通常属于使用接口类型值的包,而不是实现这些值的包

那么,大多数接口不能是私有的吗?

package mypackage

type thinger interface {
  Thing() bool
}

func Smth(t thinger) bool {...}
Run Code Online (Sandbox Code Playgroud)
package otherpackage

type MyThing struct{}
func (t MyThing) Thing() bool {return true}

myVar := MyThing{}
mypackage.Smth(myVar)
Run Code Online (Sandbox Code Playgroud)

公共接口有什么意义?例如io.Reader,成为公共接口有什么好处?

Jim*_*imB 6

接口也是一种契约。以io.Reader例如; 它具有所有实现都必须遵守的特定行为,并将其用作参数或返回类型记录您期望的行为以及方法签名。反之亦然,对于具有重叠方法集的类型,如果您碰巧有相同的方法但不坚持特定的接口,则可以使用不同的接口名称来区分两者(这可能不是一个代码库中的良好模式,但经常遇到可能需要区分的外部接口)。

当您使用 定义某种方法或函数时io.Reader,您可以依赖所有记录的行为,io.Reader而不必每次都在您自己的代码中记录它。

Go 类型不是变体,因此您不能声明满足另一个具有私有接口的函数签名。如果有一个函数func ReadFrom(r internal),你不能用你自己的函数签名来满足这个函数签名func ReadFrom(r myInternal)。标准库中有很多这样的例子,如果接口是私有的,你就无法实现;例如

最后,众所周知的接口也有助于简单地阅读和理解代码。io.Reader是一个已知的界面,并且在源代码中很容易识别。遇到 时myReader,不查阅文档,您不知道预期的行为是什么,甚至不知道方法集是什么。

  • @dmzkrsk:go 库的设计依赖于共享接口。我想到的第一个例子是,如果不使用,就无法实现 [`http.Handler`](https://pkg.go.dev/net/http?tab=doc#Handler) (或 `HandlerFunc`) `http.ResponseWriter`。这是一个非常有用的属性,除了“因为你可以”之外,无需任何理由就可以扔掉。 (3认同)
  • @dmzkrsk:您无法在自己的函数签名中使用它,例如“func ReadFrom(r io.Reader, x myType)”。 (2认同)