RE: simulating dynamic dispatch
(Taking this off to haskell-cafe) It's not unreasonable for it to be ambiguous. The argument 'f' says *forall b*. The cast will cast to a *specified* type. But you aren't specifying the type. If you passed a less polymorphic 'f' it might be ok. Simon | -Original Message- | From: Hal Daume III [mailto:[EMAIL PROTECTED] | Sent: 21 March 2003 22:29 | To: Simon Peyton-Jones | Cc: [EMAIL PROTECTED]; [EMAIL PROTECTED] | | Excellent paper! I have started using some of the techniques already! | | But, back to the real question :). I now no longer think such a thing is | possible. Essentially what I want (given 'cast :: Typeable a, Typeable b | = a - Maybe b' [1]), is to write something like: | | test :: forall a r . Typeable a = | (forall b . (Typeable b, Foo b) = b - r) - | a - Maybe r | test f a = liftM f (cast a) | | but then 'b' is ambiguous. I'm not sure there is any way around | this. Can someone help? | | - Hal | | [1] is there any reason why parens are requires around class | contexts? i've always found this odd... | | -- | Hal Daume III | [EMAIL PROTECTED] | Arrest this man, he talks in maths. | www.isi.edu/~hdaume | | On Fri, 21 Mar 2003, Simon Peyton-Jones wrote: | | You might also find the 'cast' function in Section 3 of Scrap your | boilerplate useful. | http://research.microsoft.com/~simonpj/papers/hmap/ | I'm not certain, but it has the right smell. | Simon | | | -Original Message- | | From: [EMAIL PROTECTED] [mailto:[EMAIL PROTECTED] | | Sent: 21 March 2003 04:19 | | To: [EMAIL PROTECTED]; [EMAIL PROTECTED] | | Subject: Re: simulating dynamic dispatch | | | | | | i'm hoping to be able to simulate a sort of dynamic dispatch based | on | | class instances. | | | | It seems you want to dispatch based not on a type but on the | | constraint of a type. | | | | You code almost worked. Here's the a bit updated and working version. | | | | class Foo a where { foo :: a - Bool } | | class Bar a where { bar :: a - Bool } | | | | data FB = forall a . Foo a = MkFoo a | forall a . Bar a = MkBar a | | | | instance Foo FB where | | foo (MkFoo x) = foo x | | | | instance Bar FB where | | bar (MkBar x) = bar x | | | | -- some instances for the test | | instance Foo Int where | | foo x = x == 0 | | | | instance Bar Char where | | bar x = x == 'a' | | | | | | test x = case x of | | (MkFoo a) - Just $ foo a | | (MkBar a) - Just $ bar a | | -- _ - Nothing | | | | | | -- *Main test $ MkFoo (0::Int) | | -- Just True | | -- *Main test $ MkFoo (10::Int) | | -- Just False | | -- *Main test $ MkBar 'a' | | -- Just True | | -- *Main test $ MkBar 'b' | | -- Just False | | | | ___ | | Haskell mailing list | | [EMAIL PROTECTED] | | http://www.haskell.org/mailman/listinfo/haskell | ___ Haskell-Cafe mailing list [EMAIL PROTECTED] http://www.haskell.org/mailman/listinfo/haskell-cafe
RE: simulating dynamic dispatch
Excellent paper! I have started using some of the techniques already! But, back to the real question :). I now no longer think such a thing is possible. Essentially what I want (given 'cast :: Typeable a, Typeable b = a - Maybe b' [1]), is to write something like: test :: forall a r . Typeable a = (forall b . (Typeable b, Foo b) = b - r) - a - Maybe r test f a = liftM f (cast a) but then 'b' is ambiguous. I'm not sure there is any way around this. Can someone help? - Hal [1] is there any reason why parens are requires around class contexts? i've always found this odd... -- Hal Daume III | [EMAIL PROTECTED] Arrest this man, he talks in maths. | www.isi.edu/~hdaume On Fri, 21 Mar 2003, Simon Peyton-Jones wrote: You might also find the 'cast' function in Section 3 of Scrap your boilerplate useful. http://research.microsoft.com/~simonpj/papers/hmap/ I'm not certain, but it has the right smell. Simon | -Original Message- | From: [EMAIL PROTECTED] [mailto:[EMAIL PROTECTED] | Sent: 21 March 2003 04:19 | To: [EMAIL PROTECTED]; [EMAIL PROTECTED] | Subject: Re: simulating dynamic dispatch | | | i'm hoping to be able to simulate a sort of dynamic dispatch based on | class instances. | | It seems you want to dispatch based not on a type but on the | constraint of a type. | | You code almost worked. Here's the a bit updated and working version. | | class Foo a where { foo :: a - Bool } | class Bar a where { bar :: a - Bool } | | data FB = forall a . Foo a = MkFoo a | forall a . Bar a = MkBar a | | instance Foo FB where | foo (MkFoo x) = foo x | | instance Bar FB where | bar (MkBar x) = bar x | | -- some instances for the test | instance Foo Int where | foo x = x == 0 | | instance Bar Char where | bar x = x == 'a' | | | test x = case x of | (MkFoo a) - Just $ foo a | (MkBar a) - Just $ bar a | --_ - Nothing | | | -- *Main test $ MkFoo (0::Int) | -- Just True | -- *Main test $ MkFoo (10::Int) | -- Just False | -- *Main test $ MkBar 'a' | -- Just True | -- *Main test $ MkBar 'b' | -- Just False | | ___ | Haskell mailing list | [EMAIL PROTECTED] | http://www.haskell.org/mailman/listinfo/haskell ___ Haskell mailing list [EMAIL PROTECTED] http://www.haskell.org/mailman/listinfo/haskell
Re: simulating dynamic dispatch
i'm hoping to be able to simulate a sort of dynamic dispatch based on class instances. It seems you want to dispatch based not on a type but on the constraint of a type. You code almost worked. Here's the a bit updated and working version. class Foo a where { foo :: a - Bool } class Bar a where { bar :: a - Bool } data FB = forall a . Foo a = MkFoo a | forall a . Bar a = MkBar a instance Foo FB where foo (MkFoo x) = foo x instance Bar FB where bar (MkBar x) = bar x -- some instances for the test instance Foo Int where foo x = x == 0 instance Bar Char where bar x = x == 'a' test x = case x of (MkFoo a) - Just $ foo a (MkBar a) - Just $ bar a --_ - Nothing -- *Main test $ MkFoo (0::Int) -- Just True -- *Main test $ MkFoo (10::Int) -- Just False -- *Main test $ MkBar 'a' -- Just True -- *Main test $ MkBar 'b' -- Just False ___ Haskell mailing list [EMAIL PROTECTED] http://www.haskell.org/mailman/listinfo/haskell
Re: simulating dynamic dispatch
-- *Main test $ MkFoo (0::Int) -- Just True -- *Main test $ MkFoo (10::Int) -- Just False -- *Main test $ MkBar 'a' -- Just True -- *Main test $ MkBar 'b' -- Just False ah, yes. i was aware that would work. i forgot to mention the constraint that i don't want the user to have to use the MkFoo/MkBar constructors. if i could use them internally to 'test', that would be great, but that's what i couldn't get to work :). ___ Haskell mailing list [EMAIL PROTECTED] http://www.haskell.org/mailman/listinfo/haskell
Re: simulating dynamic dispatch
On 20-Mar-2003, Hal Daume III [EMAIL PROTECTED] wrote: i'm hoping to be able to simulate a sort of dynamic dispatch based on class instances. basically a function which takes a value and depending on what classes it is an instance of, does something. I call this feature dynamic type class casts. But there are some difficulties in defining the semantics of this. What should it mean in the presence of dynamic loading? If you're allowed to dynamically load new modules that might contain new instance declarations, and you're allowed to check (in a non-IO-monad context) whether a type is an instance of a type class, and you want things to remain referentially transparent, then you've got a problem. i tried something like: class FooBar a where wasFoo :: a - Maybe FB -- will be MkFoo wasBar :: a - Maybe FB -- will be MkBar wasFoo _ = Nothing wasBar _ = Nothing instance Foo a = FooBar a where wasFoo a = Just (MkFoo a) instance Bar a = FooBar a where wasBar a = Just (MkBar a) but this complains about duplicate instance declarations (for obvious reasons). You can use instance declarations for whichever ground types you need, e.g. instance FooBar Int where ... instance FooBar String where ... -- Fergus Henderson [EMAIL PROTECTED] | I have always known that the pursuit The University of Melbourne | of excellence is a lethal habit WWW: http://www.cs.mu.oz.au/~fjh | -- the last words of T. S. Garp. ___ Haskell mailing list [EMAIL PROTECTED] http://www.haskell.org/mailman/listinfo/haskell