給定一個通用結構:
type R2[IDTYPE comparable] struct {
ID IDTYPE
IsActive bool
}
實作介面:
type Storable interface {
Store(ctx context.Context) error
}
我希望以下定義有效:
func (r R2[int]) Store(ctx context.Context) error {
r.ID = 123 // not allowed
// ...
return nil
}
但是,方法定義是不允許的。錯誤是:
'123' (type untyped int) cannot be represented by the type IDTYPE (int)
在 Go 中還不能進行這種通用欄位分配嗎?
附錄:在去操場上,錯誤是:
cannot use 123 (untyped int constant) as int value in assignment
并且轉換為int(123)不起作用。這種情況下的錯誤是:
cannot use comparable(123) (untyped int constant 123) as int value in assignment
uj5u.com熱心網友回復:
實體化必須發生在型別級別,而不是方法級別,并且方法不能引入新的型別引數,請參閱如何在 Go 中創建泛型方法?(方法必須沒有型別引數)
這意味著當您想使用 時R2,您必須為型別引數選擇型別引數,并且方法無法更改這些,您“卡住”了您在R2實體化時選擇的型別。
另請注意,由于 is 的約束IDTYPE,例如comparable可能是string,整數123不能ID在所有情況下都分配給欄位,因為它的型別可能是string。
如果您想要/必須為 ID 處理多個具體型別,泛型不是正確的選擇。可以使用介面代替:
type R2 struct {
ID any
IsActive bool
}
另請注意,如果您希望修改接收器(例如結構的欄位),則接收器必須是指標。
如果您希望限制存盤在IDto中的值comparable,請使用(通用)函式。
以下是您的操作方法:
type R2 struct {
ID any
IsActive bool
}
func (r *R2) Store(ctx context.Context) error {
setID(r, 123)
return nil
}
func setID[ID comparable](r *R2, id ID) {
r.ID = id
}
測驗它:
r := &R2{}
var s Storable = r
s.Store(context.TODO())
fmt.Println(r)
哪些輸出(在Go Playground上嘗試):
&{123 false}
這提供了靈活性(您可以ID使用 為欄位設定任何可比較的值setID()),并提供編譯時安全性:嘗試設定不可比較的值將導致編譯時錯誤,例如:
setID(r, []int{1}) // Error: []int does not implement comparable
轉載請註明出處,本文鏈接:https://www.uj5u.com/gongcheng/506765.html
下一篇:如何傳遞genericType?
