MST

星途 面试题库

面试题:Go语言接口设计中常见的一种反模式及改进方法

在Go语言接口设计里,有一种常见反模式是接口过于宽泛,导致实现者负担过重。请举例说明这种反模式,并阐述如何对其进行改进,以遵循最佳实践。
16.2万 热度难度
编程语言Go

知识考点

AI 面试

面试题答案

一键面试

举例说明反模式

假设我们有一个电商系统,设计了一个非常宽泛的 Product 接口,它涵盖了各种不同类型产品(如书籍、电子产品、食品等)的所有可能操作:

type Product interface {
    GetName() string
    GetPrice() float64
    GetAuthor() string // 只适用于书籍
    GetBrand() string // 适用于电子产品等
    GetExpiryDate() time.Time // 适用于食品
    // 更多各种类型产品可能的方法
}

对于书籍产品实现者,需要实现 GetBrandGetExpiryDate 等与书籍无关的方法;食品产品实现者需要实现 GetAuthor 等无关方法,这就导致实现者负担过重。

改进方式

  1. 拆分为更细粒度的接口
    • 对于书籍,可以定义 Book 接口:
    type Book interface {
        GetName() string
        GetPrice() float64
        GetAuthor() string
    }
    
    • 对于电子产品,定义 ElectronicProduct 接口:
    type ElectronicProduct interface {
        GetName() string
        GetPrice() float64
        GetBrand() string
    }
    
    • 对于食品,定义 Food 接口:
    type Food interface {
        GetName() string
        GetPrice() float64
        GetExpiryDate() time.Time
    }
    
  2. 遵循接口隔离原则:让不同类型的产品实现各自对应的细粒度接口,而不是一个大而全的接口。这样每个实现者只需要关注自己真正需要实现的方法,降低了负担,也符合接口设计的最佳实践。例如:
type MyBook struct {
    name   string
    price  float64
    author string
}

func (b MyBook) GetName() string {
    return b.name
}

func (b MyBook) GetPrice() float64 {
    return b.price
}

func (b MyBook) GetAuthor() string {
    return b.author
}

这里 MyBook 结构体只实现 Book 接口的方法,而不需要处理其他无关方法。