Possible Duplicate:
Type extension errors
I would like to add an extension method in F# to System.Collections.Generic.Dictionary. The trouble is that I cannot seem to get the type constraints right. I was hoping something like the following would work:
type Dictionary<'k, 'd when 'k : equality> with
static member ofList (xs:list<'k * 'd>) : Dictionary<'k, 'd> =
let res = new Dictionary<'k, 'd> ()
for (k, d) in xs do
res.Add (k, d)
res
However, the compiler complains that my declaration differs from that of Dictionary. It does not produce that particular error when I leave out the equality constraint. But then it warns that it’s missing. Many thanks for any hints, preferably other that “turn the warning level down” 🙂
EDIT
Many thanks to KVB for providing the answer I wanted.
type Dictionary<'k, 'd> with
static member ofList (xs:list<'k * 'd>) : Dictionary<'k, 'd> =
let res = new Dictionary<'k, 'd> (EqualityComparer<'k>.Default)
for (k, d) in xs do
res.Add (k, d)
res
EDIT: Here is an example to better explain my reply to RJ. It shows that type arguments are optional when instantiating a type provided the compiler can infer them. It compiles without warnings or errors.
type System.Collections.Generic.Dictionary<'k, 'd> with
static member test (dict:System.Collections.Generic.Dictionary<'k, 'd>) : bool =
dict.Values |> List.ofSeq |> List.isEmpty
let test (x:System.Collections.Generic.Dictionary<'k, 'd>) =
System.Collections.Generic.Dictionary.test x
If you need
ofSeqfunctions for various collections, you might consider an approach similar to C# collection initializers. That is, make it work for any collection with anAddmethod. This also sidesteps your present problem.Interestingly, you can even limit it to collection types with a specific constructor overload. For example, if you wanted to use structural equality you could do: