Torbjörn Gyllebring
Torbjörn Gyllebring

Reputation: 18218

Type inference & new in F#

Using F# 2.0 and FSI I have the following:

let foo = List(xs)//works
let bar = new List(xs) //need type parameter 'The type System.Collectsion.Generic<_> expects 1 type argument 0 was given

now of course I can do:

let baz = new List<TypeOItemsInXs>(xs)//why?

Now is there something I reasonably can do? Why do I have to choose between working type inference or warnings free code (if 'List' is disposable you get a warning that you should use 'new' to be explicit about it).

Any workaround? Is this a bug or something?

Upvotes: 7

Views: 796

Answers (2)

Robert
Robert

Reputation: 6437

Yin Zhu answer is correct, I'd like to add one detail. In F# you can call .NET constructors with or without the new keyword. If new is omitted there's no need to add the generic parameter, but if you use new then you must add a generic parameter, even if you let type inference do the work using a wildcard _.

Thus, you can say:

> ResizeArray([1; 2; 3;]);;
val it : System.Collections.Generic.List<int> = seq [1; 2; 3]

or

> new ResizeArray<_>([1; 2; 3;]);;
val it : ResizeArray<int> = seq [1; 2; 3]

but not:

> new ResizeArray([1; 2; 3;]);;

  new ResizeArray([1; 2; 3;]);;
  ----^^^^^^^^^^^

C:\Temp\stdin(5,5): error FS0033: The type 'Microsoft.FSharp.Collections.ResizeArray<_>' expects 1 type argument(s) but is given 0

Upvotes: 8

Yin Zhu
Yin Zhu

Reputation: 17119

You can still use type inference with a wildcard _:

open System.Collections.Generic
let xs = [1;2;3]

let bar = new List<_>(xs)

BTW, to distinguish F# list and .NET List<T> container, F# has renamed the .NET List<T> to ResizeArray<T>, which is in Microsoft.FSharp.Collections and this namespace is opened by default:

let bar2 = new ResizeArray<_>(xs)

Upvotes: 13

Related Questions