## 静态成员(static member)
这个模式只用在很稀少的场景,你需要某个struct类型的所有的实例需要共享同一个值。 我最近偶然发现的一个例子是出于调试目的:一个接口`I`实现了`Kind() string`函数,用来在日志系统中打印类型。
这太容易实现了,而且也不会弄乱包命名空间:
~~~
type myImpl struct{}
func (*myImpl) Kind() string {
return "Best implementation"
}
~~~
注意`Kind()`需要一个指针类型的receiver,但是它并没有为这个receiver命名,所以很清晰的表明我们并不使用类型实例。
## 错误组(Errgroup)
有时候你想创建多个goroutine,让它们并行地工作,当遇到某种错误或者你不像再输出了,你可能想取消整个goroutine。
为了取得这个效果你可以使用 sync.Waitgroup 和 context.Context 是可行的,但是这得需要很多冗余代码,我建议使用[errgroup.Errgroup](https://godoc.org/golang.org/x/sync/errgroup)。
例子:
~~~
import "golang.org/x/sync/errgroup"
......
eg, ctx := errgroup.WithContext(context.TODO())
for _, w := range work {
w := w
eg.Go(func() error {
// Do something with w and
// listen for ctx cancellation
})
}
// If any of the goroutines returns an error ctx will be
// canceled and err will be non-nil.
if err := eg.Wait(); err != nil {
return err
}
~~~