I have a vexing error.
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
The last line, specifically "Name" generates a compiler error saying that "the field, constructor or member 'Name' is not defined".
The workaround I've used is to write
let name = (pluto :> Animal).Name
However this is very annoying and creates a lot of visual noise. Is there something one can do in F# to just be able to resolve Name without telling the compiler explicitly that Name is a derived member from the Animal type?
In F#, when you implement an interface, it's an equivalent of explicit interface implementation in C#. That is, you can call the method through the interface, but not directly through the class.
F# reference article about interfaces suggests adding a method that does the upcasting to the type:
type Dog (name : string) =
member this.Name = (this :> Animal).Name
interface Animal with
member this.Name : string = name
Or, as suggested by Daniel, you can do it the other way around, which means you can avoid that cast:
type Dog (name : string) =
member this.Name = name
interface Animal with
member this.Name : string = this.Name
Also, the .Net convention for interface names is to start them with I, so your interface should be called IAnimal.
Another option is to use an abstract class instead of an interface:
[<AbstractClass>]
type Animal () =
abstract Name : string
type Dog (name) =
inherit Animal()
override dog.Name = name
let pluto = Dog("Pluto")
let name = pluto.Name
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With