はじめに
先日、Go 1.24で追加予定のgeneric alias typesの記事がGoの公式Blogに投稿されました。
https://go.dev/blog/alias-names
type definition
新しい型を定義する。
type Foo int
intとは別の全く新しい型として定義しているので、int型をFoo型に代入することはできない。
func main() {
var a Foo
var b int = 1
a = b
fmt.Printf("%d", a)
}
型エイリアス
go1.9で追加された機能。
type Foo = int
あくまでFooはint型のエイリアスなので、int型と同じ。新しい型を定義しているわけではない。ゆえに、Fooにint型を代入することができる。
type Foo = int
func main() {
var a Foo
var b int = 1
a = b
fmt.Printf("%d", a)
}
例えば以下のようなパッケージがあるとする。
package oldpkg
type User struct {
ID int
Name string
}
このパッケージを新しいパッケージに移動したい場合 以下のようにする
package newpkg
import "path/to/oldpkg"
type User = oldpkg.User
newpkg.User と oldpkg.User は同じ型になる。
Generic Type Aliases
Go1.18でジェネリクスが導入されたが、エイリアスでジェネリクスを使用することはできなかった。Generic Type Aliases によって以下のようなジェネリクスを含むエイリアスがサポートされる。
type Alias[P1 C1, P2 C2] = someType
次に、Fooがgeneric型の場合を考える。
package oldpkg
type Foo[T any] struct {
ID T
Name string
}
これを同じように新しい型として移行できる。
package newpkg
import "path/to/oldpkg"
type User[T any] = oldpkg.User[T]
パッケージ間でジェネリック型を移動するときに完全な型の互換性を維持できます。
終わりに
この機能は、Go 1.23 では、GOEXPERIMENT=aliastypeparams
フラグを指定することで使用することができる。Go 1.24からはデフォルトで使用可能となる予定である。