我有一个接口Model,它是由 struct 实现的Person。' @+ T. [/ H- B! j6 G* e
为了获得模型实例,我有以下帮助函数:) U9 K- S) R$ `) H1 M- i; n* \, a
func newModel(c string) Model switch c case "person": return newPerson() return nil}func newPerson() *Person return &erson{}} , E2 h c) _$ R% _6 B9 a" A |
func newModels(c string) []Model switch c case "person": return newPersons() return nil}func newPersons() *[]Person var models []Person return &models}0 Z; A6 I0 Z8 T
去抱怨: cannot use newPersons() (type []Person) as type []Model in return argument* j" N# I7 R3 q$ A' p
我的目标是返回请求的任何模型切片(无论是[]Person、[]FutureModel、[]Terminator2000、 w/e)。我错过了什么,如何正确实施这样的解决方案? 0 T$ P4 k' r" g. n 6 x+ c1 j7 G6 W1 x4 T, r 解决方案: : |& H# V+ b$ N
简短的答案是你是对的。结构切片不等于结构实现接口切片。 & e, q8 M0 R0 c) x6 t8 b8 I* ?A[]Person和 a[]Model内存布局不同。这是因为它们的切片类型有不同的内存布局。AModel它是一个接口值,这意味着它在内存中的大小是两个字。一个词表示类型信息,另一个词表示数据。APerson它的大小取决于它包含的字段。a 转换[]Person为 a []Model,您需要遍历数组并转换每个元素的类型。; G/ d8 D# f5 j
因为这个转换是一个 O(n) 操作并且会导致一个新的切片被创建,Go 拒绝隐式这样做。您可以使用以下代码显式执行此操作。 - y) N1 m9 j) O- d. G4 S; W
models := make([]Model,len(persons))for i,v := range persons models = Model(v)}return models ; V) N! m& w7 z3 D