メインコンテンツにスキップ
モジュール 6 · レッスン 1 / 5コース内の 26/50~12 min
モジュールのレッスン (1/5)

インターフェイス: 動作の定義

Go の インターフェイス は、メソッド シグネチャのセットです。値 これらのメソッドが すべて ある場合、インターフェイスを実装します。いいえ implements、extends なし、明示的な登録なし。それは モデルは、「構造的型付け」または「静的ダック型付け」と呼ばれることがよくあります。 コンパイラはコンパイル時に適合性をチェックしますが、それに基づいて 宣言ではなく形状です。

インターフェースの宣言

Go
type Greeter interface {
    Greet() string
}

規則: 単一メソッド インターフェイスの場合は、-er で終わる名前 (Reader、Writer、Stringer、Closer)。小さなインターフェース (1 ~ 2 のメソッド) は 慣用的です: 標準ライブラリには 一緒に構成される小さなインターフェイス (io.ReadWriter、 io.ReadCloser, …)。

暗黙的な実装

Go
type Person struct{ Name string }

func (p Person) Greet() string {
    return "ciao " + p.Name
}

// Person satisfies Greeter because it has the required method.
var s Greeter = Person{Name: "Ada"}
fmt.Println(s.Greet())

キーワードはありません。型にメソッドがある場合は、次のように割り当てることができます。 そのインターフェイス タイプの変数。それでおしまい。

インターフェイスを介したポリモーフィズム

Go
type Robot struct{ ID string }
func (r Robot) Greet() string { return "bip " + r.ID }

func greet(s Greeter) {
    fmt.Println(s.Greet())
}

greet(Person{Name: "Ada"})
greet(Robot{ID: "R2"})

greet は、Greeter を満たす任意の型を受け入れます。これがGoのやり方です ポリモーフィズムの実行: 階層はなく、機能のみです。

空のインターフェース

Go
var x interface{} = 42
var y any = "ciao"   // any is the built-in alias of interface{}

interface{} (または Go 1.18 以降では any) はメソッドを必要としないため、 値はそれを満たします。一般的なコンテナに便利ですが、抽出する場合に便利です。 タイプ アサーション または タイプ スイッチ が必要な具体的な値 (次のレッスン)。

メソッド セット: 値とポインター レシーバー (プレビュー)

モジュール 5 を思い出してください:

  • 値レシーバーを持つメソッドは、T と *T の両方のメソッド セットに含まれます。
  • ポインター レシーバー を持つメソッドは、*T のメソッド セットにのみ含まれます。

実際的な結果:

Go
type Counter struct{ N int }
func (c *Counter) Inc() { c.N++ }

type Incrementer interface { Inc() }

var i Incrementer = &Counter{}   // OK: *Counter has Inc()
// var j Incrementer = Counter{} // ERROR: Counter (value) does NOT

メソッドにポインタ レシーバがある場合、ポインタをメソッドに割り当てる必要があります。 インターフェース変数。

試してみてください

運動#go.m6.l1.e1
試行回数: 0読み込み中…

単一のメソッド Greet() 文字列を使用してインターフェイス Greeter を定義します。

エディターを読み込み中…
ヒントを表示

構文: `type Name Interface { Method(args) return }`。

3 回の試行後に解決策が利用可能になります

運動#go.m6.l1.e2
試行回数: 0読み込み中…

フィールド ID 文字列を持つ新しいタイプのロボットに Greeter を実装します。メソッドは「bip」+IDを返します。

エディターを読み込み中…
ヒントを表示

「実装」はありません。正しいシグネチャを持つメソッドを定義するだけです。

3 回の試行後に解決策が利用可能になります

Quiz#go.m6.l1.e3
準備完了

タイプ P が Greeter インターフェイスを実装していることをどのように宣言しますか?

Go
type P struct{}
// ?
回答の選択肢

要約

  • インターフェイス = メソッド シグネチャのセット。いいえ、implements。
  • 暗黙的実装: 適切なシグネチャを持つメソッドを用意するだけです。
  • 慣用的: 小規模 インターフェイス (1 ~ 2 メソッド)、-er の名前。
  • interface{} / any: 任意の値を受け入れますが、型安全性は失われます。
  • メソッドセット: ポインターレシーバー → *T のみがインターフェースを満たす。
  • Go ポリモーフィズム: インターフェース型パラメーター、階層なし。