Go genericやっと着きました!
Go言語にはGenerickは存在しません.
なぜこの問題がないのかについては、ネット検索でも数十ページ以上の論争的なテーマが出ており、それを嫌う人と同じように必要だという人も多い.
実は私の周りにはもっと多くの人が必要だと言っているようです.
しかし昨年から、Go 2にジェニーリックを導入するとでたらめに言っていました.
昨年末、突然1.18版からジュネーブの導入が決定した.
もちろん、今回1.18に導入されたジュネーブはまだ完全ではないようだ.
最も必要だと思いますが、現在はない機能は、方法の中で新しいジュネーブを宣言することです.
これは意図的だそうです.
しかし個人的にはこの機能が必要だと思い、いつか追加されるのでこう書いています.
Go言語では,今回導入したJenny Rickが言語的に大きく変化しているので,すぐに研究する必要がある.
GoがEnericを必要とする理由
なぜこの問題がないのかについては、ネット検索でも数十ページ以上の論争的なテーマが出ており、それを嫌う人と同じように必要だという人も多い.
実は私の周りにはもっと多くの人が必要だと言っているようです.
しかし昨年から、Go 2にジェニーリックを導入するとでたらめに言っていました.
昨年末、突然1.18版からジュネーブの導入が決定した.
もちろん、今回1.18に導入されたジュネーブはまだ完全ではないようだ.
最も必要だと思いますが、現在はない機能は、方法の中で新しいジュネーブを宣言することです.
これは意図的だそうです.
しかし個人的にはこの機能が必要だと思い、いつか追加されるのでこう書いています.
Go言語では,今回導入したJenny Rickが言語的に大きく変化しているので,すぐに研究する必要がある.
GoがEnericを必要とする理由
Genericは本当にローエンドの新しい機能ですか?
まず、公式のGo 1.18以前にはジェニーリックは存在しなかった.
でも….本当ですか.
ずいぶん前にJAVAでJENARICがなかったときにどうやってリストを実現したか覚えていますか?
当時javaのList
類は多分こんな感じでした.class List{
void add(int index, Object element)
boolean contains(Object o)
Object get(int index)
int size()
}
古いファイルで、保存したファイルをダウンロードする必要があります.このgo言語に対する提案書によるとで代わります.List
では、どのタイプの人もList
に加入できるように、すべての等級の両親がObject
を使用していることがわかります.
GoであればObject
の代わりにinterface{}
を使うべきです.
この点を考慮してGoのappend
関数を考えてみましょう.
Goソースコードによれば、append
関数はこのように定義される.// https://go.googlesource.com/go/+/refs/tags/go1.17.8/src/builtin/builtin.go#103
// Type is here for the purposes of documentation only. It is a stand-in
// for any Go type, but represents the same type for any given function
// invocation.
type Type int
// https://go.googlesource.com/go/+/refs/tags/go1.17.8/src/builtin/builtin.go#134
func append(slice []Type, elems ...Type) []Type
ここでType
の注釈を考察すると、こうなる.
represents the same type for any given function invocation
パラメータに指定された値のタイプに応じて、戻りタイプが変わります...これは私たちの名前は何ですか?
Go言語がGenerickを全くサポートしていない場合、append
関数はこの形式であるべきです.func append(slice []interface{}, elems ...interface{}) []interface{}
そしてこの状態であれば、appendをするたびに強制的にこのタイプを推定します.var a = make([]byte, 10)
a = append(a, 1, 2, 3, 4, 5).([]byte)
上のコードを見るだけで吐き気がしますが、本当に上のような要素がなければ、Go-enericはかなり不便です.
それだけではない.make
の最初のパラメータをもう一度よく見てみましょう.
「タイプ」を並べたのではないでしょうか.
パラメータ受信タイプとして...もしそれがジェニーンリックでなければ何ですか?make
も本物のジュネーブをサポートしていない場合は、C言語のようにコードを書くべきです.var a = make(10 * 1).([]byte)
つまり、私が言いたいのは、
実際,GoにはJENICのような構文が既に存在しており,この構文は特定の構築関数にのみ適用される.
今回増えたジェニーリックは「普及化」しただけだ.
この角度から見ると、正式に導入されて嬉しいです.私にとって、文法の一貫性も役に立ちます.
もちろん、make、appendなどはgeneric形式に変換されていません.
Go 2が本当に現れるまでは、構築された関数は絶対にGoチームでは触れないと思います.
なぜジェニーンリックが必要なの?テンプレートコード
Go言語で最も腹立たしい部分はsort
に違いない.
Go言語でsortを実装するには、次の手順に従います.type StudentMean struct {
name string
mean float32
}
type ArrayStudentMean []StudentMean
func (a ArrayStudentMean) Len() int { return len(a) }
func (a ArrayStudentMean) Swap(i, j int) { a[i], a[j] = a[j], a[i] }
func (a ArrayStudentMean) Less(i, j int) bool { return a[i].mean < a[j].mean }
上記のコードでは、StudentMean
の配列をソートする場合、StudentMean[]
をArrayStudentMean
タイプに変換し、sort.Sort
関数を使用してソートを実行する必要があります.
大した問題ではないように見えるかもしれません.
実は大した問題ではないかもしれません.
もし、何十もの構造体がソートする必要がないなら.
上記の例では、StudentMean
型の並べ替え可能なテンプレートを4行並べ替えた.
では、100個の構造体が簡単な算術でソートする必要がある場合、テンプレートは何行必要ですか?
答えは400行で、考えてみれば恐ろしい.
上のコードから見ると、実際に本当に重要な部分は.Less
メソッドしかありませんが、残りのLen、Swapは本当に簡単な繰り返しです.
ジェニーンリックがいれば簡単に消すことができる常用球です.
現在、sort
パッケージはまだGenericを使用していないため、依然として不便であるが、間もなくアップグレードされる見通しだ.
今回Goは面白い機能が入っていて、しばらく楽しく勉強できました.
個人的にはもったいないと思いますが、Go言語も近いうちに強力なGenericサポートを提供することを夢見て、Genericが生み出したGo言語を導入する特徴的な面を中心に文章を書きます.
リファレンス
このリンク
Reference
この問題について(Go genericやっと着きました!), 我々は、より多くの情報をここで見つけました
https://velog.io/@egoavara/Go-generic-드디어-도착
テキストは自由に共有またはコピーできます。ただし、このドキュメントのURLは参考URLとして残しておいてください。
Collection and Share based on the CC Protocol
class List{
void add(int index, Object element)
boolean contains(Object o)
Object get(int index)
int size()
}
// https://go.googlesource.com/go/+/refs/tags/go1.17.8/src/builtin/builtin.go#103
// Type is here for the purposes of documentation only. It is a stand-in
// for any Go type, but represents the same type for any given function
// invocation.
type Type int
// https://go.googlesource.com/go/+/refs/tags/go1.17.8/src/builtin/builtin.go#134
func append(slice []Type, elems ...Type) []Type
func append(slice []interface{}, elems ...interface{}) []interface{}
var a = make([]byte, 10)
a = append(a, 1, 2, 3, 4, 5).([]byte)
var a = make(10 * 1).([]byte)
type StudentMean struct {
name string
mean float32
}
type ArrayStudentMean []StudentMean
func (a ArrayStudentMean) Len() int { return len(a) }
func (a ArrayStudentMean) Swap(i, j int) { a[i], a[j] = a[j], a[i] }
func (a ArrayStudentMean) Less(i, j int) bool { return a[i].mean < a[j].mean }
このリンク
Reference
この問題について(Go genericやっと着きました!), 我々は、より多くの情報をここで見つけました https://velog.io/@egoavara/Go-generic-드디어-도착テキストは自由に共有またはコピーできます。ただし、このドキュメントのURLは参考URLとして残しておいてください。
Collection and Share based on the CC Protocol