unlike C#'s extension methods, F#'s type extension methods just like the methods on the type. Combining the power from Generic Invoke (GI) function, we can expand current system much easier. The following is the code:
- the feed function defined at first line is the GI function, it takes any time with a member Feed with signature unit->unit.
- the original type does not have Feed function. The feed function is from type extension.
// the catType and dogType is from third party and can't change it.
type CatType =
| CatA of string
| CatB of string
| CatC of string * int
type DogType =
| DogA of string
| DogB of string
| DogC of string * DogType
// code to extension
let inline feed (x : ^T) = (^T : (member Feed : unit -> unit) (x))
type Animal =
| Cat of CatType
| Dog of DogType
// type extension to add a new method: Feed
type DogType with
member this.Feed() = printfn "feed dog"
type CatType with
member this.Feed() = printfn "feed cat"
type Animal with
member this.Feed() =
match this with
| Dog(m) -> feed m
| Cat(m) -> feed m
let dogs = [ DogA("a"); DogB("a1") ] |> List.map Animal.Dog
let cats = [ CatA("b"); CatB("b1") ] |> List.map Animal.Cat
let zoo = dogs @ cats
zoo |> Seq.iter feed
From the previous post, we have the ability to unify two type into a single list structure, which provide the foundation to process them in a single run.