'How to set Object/Combination prop with generic?

I have a problem with generics in Go in combination with prop edit. here is an example:

type Option[T any] func(T)

func AssignOption[T any, O Option[T]](b T, option ...O) {
    if len(option) == 0 {
        return
    }
    for _, f := range option {
        f(b)
    }
}

type Input struct {
    Id   string
}

type Text struct {
    Input
    MaxLength int
}
type Number struct {
    Input
    Min int
}


func WithMin(v int) Option[*Number] {
    return func(p *Number) {
        p.Min = v
    }
}

func WithId(v string) Option[*Input] {
    return func(p *Input) {
        p.Id = v
    }
}

func main() {
    n := Number{Max: 10, Min: 1}
    n2 := Text{}
    AssignOption(&n, WithMin(5), WithId("id20220321")) // WithId error
    AssignOption(&n2, WithId("n2s_id"))
    fmt.Println(n.Id)
    fmt.Println(n2.Id)
}

I want change n2[Text] and n[Number] both prop "Id" with function "WithId", but "WithId" throw an error:
Cannot use 'WithId("id20220321")' (type Option[*Input]) as the type O (Option[*Number])

And then I try use generic:

func WithId[T Number | Text](v string) Option[T] {
    return func(p T) { 
        p.Id = v //error: Unresolved reference 'Id'
    }
}

But now go compiler can't understand what is "p.Id" mean?
So how to resolve it?
I won't write twice "WithId" function.

-------------------------2022.3.23------------------------

Use Interface:


type InputInterface interface {
    SetId(id string)
}

func (p *Input) SetId(id string) {
    p.Id = id
}


type NumberInterface interface {
    InputInterface
}

func WithId[T NumberInterface](v string) Option[T] {
    return func(p T) {
        p.SetId(v)
    }
}

Now I get an error again:Cannot use 'WithId("id_number2")' (type Option[T]) as the type O (Option[NumberInterface])

Help~~



Solution 1:[1]

In your first code block, you are trying to assign multiple types to the generic type.

Even with generics, Go is still type safe. O will be assigned the first type found in the function call.

Option[*Number] and Option[*Input] are different types, so only one can be used at a time.

For the second code block, see this issue.

https://github.com/golang/go/issues/48522#issuecomment-924380147

Property assignments are not supported.

For the third code block, you have type mismatches. This works.

https://go.dev/play/p/mww4C3nyhI9

Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source
Solution 1 wesley