如何在go中返回泛型类型

问题描述 投票:0回答:1

我是个新手,仍处于学习阶段,找不到任何与我的问题匹配的答案,所以请不要投票。 我有这个通用接口,可以通过两个类型参数实例化,使用实现该接口的类型创建新映射绝对没有问题。我还可以插入和索引键,但在尝试使用通用函数从地图返回值时遇到问题。请帮我修复下面提到的

GetGenericIfaceVal
功能。编译器抱怨它无法返回类型 c,因为它是一个
IncompatibleAssign

package main

import (
  "strings"
)

type GenericIface[rType ~map[string]T, T interface{}] interface {
  GetSubTypes() rType
}

type t1 struct  {
  subTypes r1
}

type r1 map[string]r1

type t2 struct {
  subTypes r2
}

type r2 map[string]t2


var mapFirst = make(map[string]GenericIface[r1, r1])
var mapSecond = make(map[string]GenericIface[r2, t2])

//cannot use mapFirst[cType] (map index expression of type GenericIface[r1, r1]) as c value in return statement compiler (IncompatibleAssign) [29, 12]
func GetGenericIfaceVal[c GenericIface[M, T],M ~map[string]T, T interface{}](cType string) c {
  if strings.HasPrefix(cType, "$") {
    return mapFirst[cType]
  }
  return mapSecond[cType]
}

func (t *t1) GetSubTypes() r1 {
  return t.subTypes
}

func (t *t2) GetSubTypes() r2 {
  return t.subTypes
}

go generics interface
1个回答
0
投票

使用泛型时事情会变得很棘手,尤其是在 Go 中。我们需要仔细处理复杂的类型约束在您的情况下,问题似乎与类型约束和函数的返回值有关。您可以按照以下方法处理:

package main

import (
    "fmt"
    "strings"
)


type GenericIface[M ~map[string]T, T any] interface {
    GetSubTypes() M
}


type t1 struct {
    subTypes r1
}

type r1 map[string]r1

type t2 struct {
    subTypes r2
}

type r2 map[string]t2


var mapFirst = make(map[string]GenericIface[r1, r1])
var mapSecond = make(map[string]GenericIface[r2, t2])

GenericIface[r2, t2] based on the input type.
func GetGenericIfaceVal[M ~map[string]T, T any](cType string) GenericIface[M, T] {
    if strings.HasPrefix(cType, "$") {
        return mapFirst[cType].(GenericIface[M, T])
    }
    return mapSecond[cType].(GenericIface[M, T])
}

interface.
func (t *t1) GetSubTypes() r1 {
    return t.subTypes
}

func (t *t2) GetSubTypes() r2 {
    return t.subTypes
}

func main() {

    mapFirst["$example"] = &t1{subTypes: make(r1)}
    mapSecond["example"] = &t2{subTypes: make(r2)}


    val1 := GetGenericIfaceVal[r1, r1]("$example")
    fmt.Printf("val1: %T\n", val1)


    val2 := GetGenericIfaceVal[r2, t2]("example")
    fmt.Printf("val2: %T\n", val2)
}
© www.soinside.com 2019 - 2024. All rights reserved.