Golang で型の安全性を確保し、潜在的なパニックを回避しながら、インターフェースのスライスに具体的な型のインスタンスを効率的に埋め込むにはどうすればよいでしょうか?

Patricia Arquette
リリース: 2024-10-26 03:59:02
オリジナル
213 人が閲覧しました

How can I efficiently fill a slice of interfaces with instances of a concrete type in Golang, while ensuring type safety and avoiding potential panics?

インターフェイスと具象型のスライスのジェネリック Fill 関数

Golang では、ジェネリックを使用してジェネリック関数を定義できます。インターフェイスのスライスと具象型を扱うときの一般的なタスクは、スライスのすべての要素を具象型で初期化することです。次の関数を考えてみましょう。この関数は、型 X へのポインターのスライスを X の新しいインスタンスで埋めることを目的としています。

<code class="go">func Fill[X any](slice []*X){
   for i := range slice {
      slice[i] = new(X)
   }
}</code>
ログイン後にコピー

この関数は、どの型のスライスでも期待どおりに機能します。ただし、この動作をインターフェイスのスライスに拡張し、要素 (Y) の具体的な型を指定しようとすると、課題が発生します。

<code class="go">func Fill[X, Y any](slice []X){
   for i := range slice {
      slice[i] = new(Y) // not work!
   }
}</code>
ログイン後にコピー

X と Y の両方を any に制約する場合、インターフェイスと実装者の関係失われます。コンパイラは X と Y を別個の型として扱い、関数本体内で X と Y 間の代入を防止します。

これを解決するには、明示的なアサーションを使用できます。

<code class="go">func Fill[X, Y any](slice []X) {
    for i := range slice {
        slice[i] = any(*new(Y)).(X)
    }
}</code>
ログイン後にコピー

ただし、このアプローチは可能性があります。 sync.Mutex (ポインタ型) が sync.Locker を実装している場合のように、Y が X を実装していない場合はパニックになります。さらに、ポインター型のゼロ値は nil であるため、このメソッドは、同様に nil 値でスライスを初期化する make([]X, n) を使用する場合に比べて大幅な改善はありません。

より効果的な解決策は、2 番目の型パラメーターの代わりにコンストラクター関数を利用することです。

<code class="go">func Fill[X any](slice []X, f func() X) {
    for i := range slice {
        slice[i] = f()
    }
}</code>
ログイン後にコピー

この関数は、X のインスタンスを返す関数である追加パラメーター f を受け取ります。これにより、柔軟性が高まります。また、インターフェイスの具体的なタイプの入力をサポートします。たとえば、sync.Mutex 要素を使用して sync.Locker のスライスを初期化するには、次のコードを使用できます。

<code class="go">xs := make([]sync.Locker, 10)
Fill(xs, func() sync.Locker { return &sync.Mutex{} })</code>
ログイン後にコピー

このアプローチを利用すると、インターフェイスのスライスを具体的なインスタンスで効率的に埋めることができます。 type を使用して、便利でタイプセーフなソリューションを提供します。

以上がGolang で型の安全性を確保し、潜在的なパニックを回避しながら、インターフェースのスライスに具体的な型のインスタンスを効率的に埋め込むにはどうすればよいでしょうか?の詳細内容です。詳細については、PHP 中国語 Web サイトの他の関連記事を参照してください。

ソース:php.cn
このウェブサイトの声明
この記事の内容はネチズンが自主的に寄稿したものであり、著作権は原著者に帰属します。このサイトは、それに相当する法的責任を負いません。盗作または侵害の疑いのあるコンテンツを見つけた場合は、admin@php.cn までご連絡ください。
著者別の最新記事
人気のチュートリアル
詳細>
最新のダウンロード
詳細>
ウェブエフェクト
公式サイト
サイト素材
フロントエンドテンプレート
私たちについて 免責事項 Sitemap
PHP中国語ウェブサイト:福祉オンライン PHP トレーニング,PHP 学習者の迅速な成長を支援します!