I am no F# wiz but I believe only classes (and thus object expressions) can subscribe to interfaces. Type exp is simply an algebraic data type, not a class. A solution would depend much on what you exactly mean by your code, which is not clear to me.

Cheers,

Jorge.

By on 3/7/2007 6:10 AM ()

No, it works with algebraic data types. I've used several times, and my example works when there's not the type parameter (and the recursion).

This code was minimalist. I have a quite big AST that implements the IFormattable interface (for pretty-printing). It's working fine, but I'd like to add a type parameter to make it more generic. When I added the type parameter (with the type constraint), I got the message "The type exp is not compatible with the type IFormattable".

So my current solution is to duplicate type definitions, but it's not pretty.

Laurent.

By on 3/7/2007 7:08 AM ()

Hi LLB,

This is indeed a bug. We will of course fix it for the next release.

Kind regards

Don

By on 3/9/2007 7:13 PM ()

Hi,

Thank you Don.
I have another problem with the interface. I might be the same bug, but I prefer to be sure. I can't call recursively GetLayout (error: "member 'GetLayout' is not defined"). As a workaround, I defined a get_layout function, but it's not elegant. Minimalist example:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
let get_layout (env: #IEnvironment) (e: #IFormattable) = e.GetLayout(env)


type foo = Item of int * foo | Empty

with

   interface IFormattable with

      member x.GetLayout(env) =

          match x with

//           | Item (_,a) -> a.GetLayout(env) // not allowed

            | Item (_,a) -> get_layout env a   // ok

            | Empty -> emptyL

    end

end

Laurent.

By on 3/10/2007 3:04 PM ()

The issue here is that the "this" value i.e. "a" has type "foo". Methods associated with intefaces are not immediately accessible from a value of type "foo" - you have to cast to the interface type first. Try the following

1
2
3
4
5
6
7
8
9
10
 
type foo = Item of int * foo | Empty
with
  interface IFormattable with
   member x.GetLayout(env) =
     match x with
     | Item (_,a) -> (a :> IFormattable).GetLayout(env) 
     | Empty -> emptyL
  end
end

Don

By on 3/10/2007 4:05 PM ()

OK, thank you.
I hoped the compiler could know it's a IFormattable. Actually, I will keep my solution, because it's shorter (I would need to add a lot of casts).

Laurent.

By on 3/10/2007 6:21 PM ()

Hi Laurent,

Just to let you know that this bug has been fixed and the fix will be in the 1.9.1 release of F#, due out "real soon now".

Thanks

don

By on 3/15/2007 10:55 AM ()
IntelliFactory Offices Copyright (c) 2011-2012 IntelliFactory. All rights reserved.
Home | Products | Consulting | Trainings | Blogs | Jobs | Contact Us | Terms of Use | Privacy Policy | Cookie Policy
Built with WebSharper