代码之家  ›  专栏  ›  技术社区  ›  blackgreen

如何将类型参数约束到嵌入另一个结构的结构?

  •  0
  • blackgreen  · 技术社区  · 3 年前

    我试图在Go中定义一个通用函数,它接受具有某些字段的值,例如, ID int 。我尝试了几种方法,但似乎都不起作用。下面是我尝试的一个例子。

    package main
    
    import (
        "fmt"
    )
    
    func Print[T IDer](s T) {
        fmt.Print(s.ID)
    }
    
    func main() {
        Print(Person{3, "Test"})
    }
    
    type IDer interface {
        ~struct{ ID int }
    }
    
    type Person struct {
        ID   int
        Name string
    }
    
    type Store struct {
        ID     int
        Domain string
    }
    
    

    这里是游乐场链接: https://gotipplay.golang.org/p/2I4RsUCwagF

    在上面的例子中,我想保证传递给 Print 函数有一个属性 ID int ,也可以在函数中访问。有没有任何方法可以在Go中实现这一点,而无需在接口中定义方法(例如。, GetID() int )?

    0 回复  |  直到 1 年前
        1
  •  0
  •   Vinicius Fortuna    1 年前

    有没有什么方法可以实现这一点,那就是Go,而无需在接口中定义方法(例如,GetID()int)?

    不,您必须在接口中定义方法。

    Go 1.18中的泛型实现不支持结构类型,尽管最初的类型参数提案建议它支持结构类型。有关访问联合中的公共字段,请参阅 this explanation .

    尽管如此,我认为值得指出一个很容易从你的例子中产生的误解:近似的含义 ~T (波浪号类型)的意思是“底层类型为T的一组类型。

    现在,当你写:

    ~struct{ ID int }
    

    这意味着其基础类型为的类型 确切地 struct{ ID int } 。无论如何,这不包括具有字段的结构 ID int 其他的东西。例如的基本类型 type Foo struct { ID int; Name string } struct { ID int; Name string } ,而不是 结构{ID int} ,所以无论如何都不能满足约束。

    当前时间参数实现没有指定部分结构类型的语法。我记得 proposal 要在接口约束中添加字段术语(以及类型术语和方法),请执行以下操作:

    type IDer interface {
        ID int
    }
    

    这将使您能够在不破坏波浪号含义的情况下进行尝试 ~ 。但这不会包含在Go 1.18中。