7

this should be a quick one for all you f# rockers, but it's got me stuck at the moment.

I've got an F# type which I'm trying to get to implement a c# interface

public interface ICrudService<T> where T: DelEntity, new()
{
    IEnumerable<T> GetAll();
}

here's how it's implemnted in c#:

public IEnumerable<T> GetAll()
{
    return repo.GetAll();
}

repo.GetAll returns an IQueryable, but the c# compiler knows enough to convert to IEnumerable because IQueryable<T> : IEnumerable<T>. but In F# the compiler can't work it and I've tried a few attempt to cast it correctly

type CrudService<'T when 'T :(new : unit -> 'T) and 'T :> DelEntity>(repo : IRepo<'T>) = 
    interface ICrudService<'T> with
         member this.GetAll () = 
            repo.GetAll<'T>

this is giving me a type mismatch error

ildjarn
  • 62,044
  • 9
  • 127
  • 211
Jonny Cundall
  • 2,552
  • 1
  • 21
  • 33

2 Answers2

7

You need to cast to IEnumerable<'T>:

type CrudService<'T when 'T :(new : unit -> 'T) and 'T :> DelEntity>(repo : IRepo<'T>) = 
        interface ICrudService<'T> with
             member this.GetAll () = 
                repo.GetAll() :> IEnumerable<'T>
Lee
  • 142,018
  • 20
  • 234
  • 287
  • 1
    That did it. I had tried the cast to IEnumerable, but what I was missing was the brackets after the function call on GetAll. – Jonny Cundall May 31 '14 at 23:08
1

What if you used Seq.cast<'T? It sounds like it just needs to be casted to the correct Type. Since IEnumerables are implemented differently in F# than they are in C#.

let seqCast : seq<int> = Seq.cast repo.GetAll<'T>
Johnathon Sullinger
  • 7,097
  • 5
  • 37
  • 102