17

厄介なエラーがあります。

type Animal =

    abstract member Name : string

type Dog (name : string) =

    interface Animal with

        member this.Name : string =
            name

let pluto = new Dog("Pluto")
let name = pluto.Name

最後の行、具体的には「Name」は、「フィールド、コンストラクター、またはメンバー'Name'が定義されていません」というコンパイラエラーを生成します。

私が使用した回避策は、書くことです

let name = (pluto :> Animal).Name

ただし、これは非常に煩わしく、多くの視覚的なノイズを生成します。NameがAnimalタイプから派生したメンバーであることをコンパイラーに明示的に通知せずに、Nameを解決できるようにするためにF#でできることはありますか?

4

2 に答える 2

25

F# でインターフェイスを実装すると、C# での明示的なインターフェイスの実装と同等になります。つまり、インターフェイスを介してメソッドを呼び出すことはできますが、クラスを介して直接呼び出すことはできません。

インターフェイスに関する F# のリファレンス記事では、型へのアップキャストを行うメソッドを追加することを提案しています。

type Dog (name : string) =

    member this.Name = (this :> Animal).Name

    interface Animal with
        member this.Name : string = name

または、ダニエルが提案したように、逆の方法で行うことができます。つまり、そのキャストを回避できます。

type Dog (name : string) =

    member this.Name = name

    interface Animal with
        member this.Name : string = this.Name

また、インターフェイス名の .Net 規則では で始まるIため、インターフェイスは と呼ばれる必要がありますIAnimal

于 2013-01-29T23:29:41.410 に答える