
In imperative languages one can test the type of a variable and downcast if necessary. Here's an example in Pseudojava: T v := ... ; if (v instanceof T') T' v' := (T')v Is it possible to do something like this in Haskell? Eric.

On Sat, Apr 28, 2007 at 02:06:21PM +0100, Eric wrote:
In imperative languages one can test the type of a variable and downcast if necessary. Here's an example in Pseudojava:
T v := ... ; if (v instanceof T') T' v' := (T')v
Is it possible to do something like this in Haskell?
Possible, yes. Usually a good idea - no. Look at the Data.Typeable and Data.Dynamic modules in the standard hierarchal libraries. Stefan

On Sat, 28 Apr 2007 14:06:21 +0100
Eric
In imperative languages one can test the type of a variable and downcast if necessary. Here's an example in Pseudojava:
T v := ... ; if (v instanceof T') T' v' := (T')v
In object-oriented languages you can achieve the same effect by defining a method on each type which has different behaviour depending on the type. In Haskell you can achieve much the same effect by defining methods in typeclasses and then defining instances for types. It's quite analogous. This is the recommended way of doing it in Haskell. -- Robin

Robin Green wrote:
In object-oriented languages you can achieve the same effect by defining a method on each type which has different behaviour depending on the type.
In Haskell you can achieve much the same effect by defining methods in typeclasses and then defining instances for types. It's quite analogous. This is the recommended way of doing it in Haskell.
I thought about that. But consider the following scenario. We have a Dispatcher and a Handler. The Dispatcher sends messages to Handlers. There are two ways we could implement this in an OOP language (0) Have each type of message be a method on a Handler type class. The problem here is that to dispatch new message types we would have to recompile the Dispatcher. (1) Have Handlers implement a method handle(m: Msg). To add new types of message, we declare message types which extend Msg. The Handler then uses runtime type testing to decide how to deal with each message. The advantage of this design is that we can add new Handler and new Msg types without recompiling the Dispatcher. Type classes allow us to adopt approach (0) in Haskell, but don't seem to allow approach (1).... E.

Hello Eric, Saturday, April 28, 2007, 5:33:02 PM, you wrote:
Type classes allow us to adopt approach (0) in Haskell, but don't seem to allow approach (1)....
may be multi-parameter type class is what you need here, may be just closure. anyway, OOP may be simulated in Haskell via hierarchy of existentials but such emulation is too expensive (in terms of easiness of programming) i highly recommend you to read http://haskell.org/haskellwiki/OOP_vs_type_classes and papers mentioned at the end there in order to grok relations between FP, OOP, type classes and existentials. unfortunately, dynamics are not yet mentioned there, read 'An Extensible Dynamically-Typed Hierarchy of Exceptions' by Simon Marlow -- Best regards, Bulat mailto:Bulat.Ziganshin@gmail.com

Hi Eric
I thought about that. But consider the following scenario. We have a Dispatcher and a Handler. The Dispatcher sends messages to Handlers. There are two ways we could implement this in an OOP language
"Consider how to implement OO features in Haskell"... Lets not, rather instead lets try to come up with a much cleaner and more Haskell-like by design. You can do imperative programming and OO programming in Haskell, in the same way you can do functional programming in ASM - possible but not a great idea. Thinking in Haskell requires you to peel away all the layers of OO, right back to the original thoughts about what you want to happen. Rather than sending a message from the dispatcher to the handler, and have a general purpose handler, why not instead register functions as callbacks? registerOnClick :: (Coordinates -> IO ()) -> IO () registerOnClose :: (Bool -> IO()) -> IO () Now you have absolutely no restriction on what information a "message" contains. (Note: you haven't given enough information to know if this suits your problem, but dynamic typing isn't the best answer, whatever the question!) Thanks Neil

Eric wrote:
(1) Have Handlers implement a method handle(m: Msg). To add new types of message, we declare message types which extend Msg. The Handler then uses runtime type testing to decide how to deal with each message. The advantage of this design is that we can add new Handler and new Msg types without recompiling the Dispatcher.
Note however that the type of the handle method is a lie (your handlers don't actually accept arbitrary messages). I guess, you actually want a polymorphic "Dispatcher", which will actually turn out to be a function. Of course, you give insufficient information to actually solve your problem.
Type classes allow us to adopt approach (0) in Haskell, but don't seem to allow approach (1)....
I consider that a good thing. -Udo
participants (6)
-
Bulat Ziganshin
-
Eric
-
Neil Mitchell
-
Robin Green
-
Stefan O'Rear
-
Udo Stenzel