Re: [Haskell-cafe] Splitting data and function declarations over multiple files

2009-10-01 Thread Job Vranish
Along the projection/co-algebra lines (I actually didn't know that's what
they were called until today :)  yay for learning new things!)

How about something like this:

-- Define prototypes for your class of actions here
data Actor = Actor {pos::Vector2 Float, move::Vector2 Float - Actor}

-- simple class that selects your actions based on type
class ActorClass a where
  mkActor :: a - Actor

-- object types
data Ball = Ball ...  -- stuff
data Paddle = Paddle ... -- stuff
data Wall = Wall ... -- suff

-- Functions for working with objects
getBallPosition (Ball ...) = ...
getPaddlePosition (Paddle ...) = ...

moveBall (Ball ...) = ...
movePaddle (Ball ...) = ...

-- selection actions for Ball
instance Actor Ball where
  mkActor this = let
pos' = getBallPosition this
move' v = moveBall this
in Actor pos' move'

-- selection actions for Paddle
instance Actor Paddle where
  mkActor this = let
pos' = getPaddlePosition this
move' v = movePaddle this
in Actor pos' move'


Base off a technique I ran across here:
http://www.mail-archive.com/hask...@haskell.org/msg04513.html

Also, a useful wikipage for doing OO things in haskell:
http://www.haskell.org/haskellwiki/OOP_vs_type_classes

- Job


On Thu, Oct 1, 2009 at 4:45 AM, Peter Verswyvelen bugf...@gmail.com wrote:

 I'm not sure if I understand what you mean with this co-algebraic approach,
 but I guess you mean that functions - like move - don't work directly on any
 datatype; you need to provide other functions that give access to the data.
 But that's basically what type classes do no? And that's also related to my
 earlier post of strong duck typing in Haskell.
 At least also in C#, that's the way I usually write code that works on any
 type, just make an interface or pass in a delegate.  I also know that my OO
 background keeps pushing me in the wrong direction when it comes to Haskell
 ;-)

 The collision handling approach is always interesting :)  In OO this is
 usually solved using multi-methods or visitors:
 http://en.wikipedia.org/wiki/Multiple_dispatch. What I usually did in old
 games of mine to handle collisions is not look at the type, but at the
 collision specific features of a type (which are again functions that
 extract information from the object), and that is most likely again the
 co-algebraic approach?

 On Wed, Sep 30, 2009 at 9:15 PM, Luke Palmer lrpal...@gmail.com wrote:

 On Wed, Sep 30, 2009 at 9:54 AM, Peter Verswyvelen bugf...@gmail.com
 wrote:
  I guess this is related to the expression problem.
  Suppose I have a datatype
  data Actor = Ball ... | Paddle ... | Wall ...
  and a function
  move (Ball ...) =
  move (Paddle ...) =
  move (Wall ...) =
  in Haskell one must put Actor and move into a single file.
  This is rather cumbersome if you work with multiple people or want to
 keep
  the files small and readable.
  Surely it is possible to use type classes, existentials, etc to split
 the
  data type into multiple ones, but that's already advanced stuff in a
 sense.

 You can do it without type classes and existentials.  The
 functionality you want is already supported by Haskell, you just have
 to let go of your syntactical expectations.  The trick is that you
 should rewrite your data type not as an algebra (a set of
 constructors), but as a coalgebra (a set of projections).

 Let's say your two open functions are:

 move :: Actor - Actor
 isAlive :: Actor - Bool

 This gives rise to the definition of an Actor type:

 data Actor = Actor { move :: Actor, isAlive :: Bool }

 And then the alternatives of your open data type are just values of type
 Actor:

 ball :: Vector - Vector - Actor
 ball pos vel = Actor {
move = ball (pos + vel) vel,
isAlive = True
  }

 etc.

 This trick works well until you get to the encoding of functions that
 pattern match on multiple Actors at the same time.  As far as I can
 tell, that cannot be encoded in this style in any reasonable way.
 Such functions must be rephrased in a coalgebraic style; i.e. instead
 of asking about constructors, using projection functions it knows are
 available.

 So for example instead of implementing collide by asking about
 pairs, add functions which report a shape function and a normal, or
 whatever your collide algorithm needs from shapes.

 You would probably end up having to do this anyway even with your
 proposed extension, because watch:

 partial data Actor = Ball ...

 collide (Ball ...) (Ball ...) = ...
 collide (Ball ...) x = ...

 We don't know about any other constructors, so the second line has to
 contain a pattern-free x.  So you would have to use projection
 functions to get any information about it, exactly as you would when
 you're writing in the coalgebraic style.

 So, Yes!  Haskell can do that!

 Luke



 ___
 Haskell-Cafe mailing list
 Haskell-Cafe@haskell.org
 http://www.haskell.org/mailman/listinfo/haskell-cafe


___

Re: [Haskell-cafe] Splitting data and function declarations over multiple files

2009-10-01 Thread Job Vranish
Opps, errors, it should be more like:

moveBall (Vector2 x y) (Ball ...) = ...
movePaddle (Vector2 x y) (Paddle ...) = ...

-- selection actions for Ball
instance Actor Ball where
  mkActor this = let
pos' = getBallPosition this
move' v = mkActor $ moveBall v this
in Actor pos' move'

-- selection actions for Paddle
instance Actor Paddle where
  mkActor this = let
pos' = getPaddlePosition this
move' v = mkActor $ movePaddle v this
in Actor pos' move'


Hmm, I bet some generics, or template haskell could clean up the extra
boilerplate associated with this technique.

- Job


On Thu, Oct 1, 2009 at 11:35 AM, Job Vranish jvran...@gmail.com wrote:

 Along the projection/co-algebra lines (I actually didn't know that's what
 they were called until today :)  yay for learning new things!)

 How about something like this:

 -- Define prototypes for your class of actions here
 data Actor = Actor {pos::Vector2 Float, move::Vector2 Float - Actor}

 -- simple class that selects your actions based on type
 class ActorClass a where
   mkActor :: a - Actor

 -- object types
 data Ball = Ball ...  -- stuff
 data Paddle = Paddle ... -- stuff
 data Wall = Wall ... -- suff

 -- Functions for working with objects
 getBallPosition (Ball ...) = ...
 getPaddlePosition (Paddle ...) = ...

 moveBall (Ball ...) = ...
 movePaddle (Ball ...) = ...

 -- selection actions for Ball
 instance Actor Ball where
   mkActor this = let
 pos' = getBallPosition this
 move' v = moveBall this
 in Actor pos' move'

 -- selection actions for Paddle
 instance Actor Paddle where
   mkActor this = let
 pos' = getPaddlePosition this
 move' v = movePaddle this
 in Actor pos' move'


 Base off a technique I ran across here:
 http://www.mail-archive.com/hask...@haskell.org/msg04513.html

 Also, a useful wikipage for doing OO things in haskell:
 http://www.haskell.org/haskellwiki/OOP_vs_type_classes

 - Job


 On Thu, Oct 1, 2009 at 4:45 AM, Peter Verswyvelen bugf...@gmail.comwrote:

 I'm not sure if I understand what you mean with this co-algebraic
 approach, but I guess you mean that functions - like move - don't work
 directly on any datatype; you need to provide other functions that give
 access to the data. But that's basically what type classes do no? And that's
 also related to my earlier post of strong duck typing in Haskell.
 At least also in C#, that's the way I usually write code that works on any
 type, just make an interface or pass in a delegate.  I also know that my OO
 background keeps pushing me in the wrong direction when it comes to Haskell
 ;-)

 The collision handling approach is always interesting :)  In OO this is
 usually solved using multi-methods or visitors:
 http://en.wikipedia.org/wiki/Multiple_dispatch. What I usually did in old
 games of mine to handle collisions is not look at the type, but at the
 collision specific features of a type (which are again functions that
 extract information from the object), and that is most likely again the
 co-algebraic approach?

 On Wed, Sep 30, 2009 at 9:15 PM, Luke Palmer lrpal...@gmail.com wrote:

 On Wed, Sep 30, 2009 at 9:54 AM, Peter Verswyvelen bugf...@gmail.com
 wrote:
  I guess this is related to the expression problem.
  Suppose I have a datatype
  data Actor = Ball ... | Paddle ... | Wall ...
  and a function
  move (Ball ...) =
  move (Paddle ...) =
  move (Wall ...) =
  in Haskell one must put Actor and move into a single file.
  This is rather cumbersome if you work with multiple people or want to
 keep
  the files small and readable.
  Surely it is possible to use type classes, existentials, etc to split
 the
  data type into multiple ones, but that's already advanced stuff in a
 sense.

 You can do it without type classes and existentials.  The
 functionality you want is already supported by Haskell, you just have
 to let go of your syntactical expectations.  The trick is that you
 should rewrite your data type not as an algebra (a set of
 constructors), but as a coalgebra (a set of projections).

 Let's say your two open functions are:

 move :: Actor - Actor
 isAlive :: Actor - Bool

 This gives rise to the definition of an Actor type:

 data Actor = Actor { move :: Actor, isAlive :: Bool }

 And then the alternatives of your open data type are just values of type
 Actor:

 ball :: Vector - Vector - Actor
 ball pos vel = Actor {
move = ball (pos + vel) vel,
isAlive = True
  }

 etc.

 This trick works well until you get to the encoding of functions that
 pattern match on multiple Actors at the same time.  As far as I can
 tell, that cannot be encoded in this style in any reasonable way.
 Such functions must be rephrased in a coalgebraic style; i.e. instead
 of asking about constructors, using projection functions it knows are
 available.

 So for example instead of implementing collide by asking about
 pairs, add functions which report a shape function and a normal, or
 whatever your collide algorithm needs from 

Re: [Haskell-cafe] Splitting data and function declarations over multiple files

2009-10-01 Thread Peter Verswyvelen
I'm not sure if I understand what you mean with this co-algebraic approach,
but I guess you mean that functions - like move - don't work directly on any
datatype; you need to provide other functions that give access to the data.
But that's basically what type classes do no? And that's also related to my
earlier post of strong duck typing in Haskell.
At least also in C#, that's the way I usually write code that works on any
type, just make an interface or pass in a delegate.  I also know that my OO
background keeps pushing me in the wrong direction when it comes to Haskell
;-)

The collision handling approach is always interesting :)  In OO this is
usually solved using multi-methods or visitors:
http://en.wikipedia.org/wiki/Multiple_dispatch. What I usually did in old
games of mine to handle collisions is not look at the type, but at the
collision specific features of a type (which are again functions that
extract information from the object), and that is most likely again the
co-algebraic approach?

On Wed, Sep 30, 2009 at 9:15 PM, Luke Palmer lrpal...@gmail.com wrote:

 On Wed, Sep 30, 2009 at 9:54 AM, Peter Verswyvelen bugf...@gmail.com
 wrote:
  I guess this is related to the expression problem.
  Suppose I have a datatype
  data Actor = Ball ... | Paddle ... | Wall ...
  and a function
  move (Ball ...) =
  move (Paddle ...) =
  move (Wall ...) =
  in Haskell one must put Actor and move into a single file.
  This is rather cumbersome if you work with multiple people or want to
 keep
  the files small and readable.
  Surely it is possible to use type classes, existentials, etc to split the
  data type into multiple ones, but that's already advanced stuff in a
 sense.

 You can do it without type classes and existentials.  The
 functionality you want is already supported by Haskell, you just have
 to let go of your syntactical expectations.  The trick is that you
 should rewrite your data type not as an algebra (a set of
 constructors), but as a coalgebra (a set of projections).

 Let's say your two open functions are:

 move :: Actor - Actor
 isAlive :: Actor - Bool

 This gives rise to the definition of an Actor type:

 data Actor = Actor { move :: Actor, isAlive :: Bool }

 And then the alternatives of your open data type are just values of type
 Actor:

 ball :: Vector - Vector - Actor
 ball pos vel = Actor {
move = ball (pos + vel) vel,
isAlive = True
  }

 etc.

 This trick works well until you get to the encoding of functions that
 pattern match on multiple Actors at the same time.  As far as I can
 tell, that cannot be encoded in this style in any reasonable way.
 Such functions must be rephrased in a coalgebraic style; i.e. instead
 of asking about constructors, using projection functions it knows are
 available.

 So for example instead of implementing collide by asking about
 pairs, add functions which report a shape function and a normal, or
 whatever your collide algorithm needs from shapes.

 You would probably end up having to do this anyway even with your
 proposed extension, because watch:

 partial data Actor = Ball ...

 collide (Ball ...) (Ball ...) = ...
 collide (Ball ...) x = ...

 We don't know about any other constructors, so the second line has to
 contain a pattern-free x.  So you would have to use projection
 functions to get any information about it, exactly as you would when
 you're writing in the coalgebraic style.

 So, Yes!  Haskell can do that!

 Luke

___
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


[Haskell-cafe] Splitting data and function declarations over multiple files

2009-09-30 Thread Peter Verswyvelen
I guess this is related to the expression problem.
Suppose I have a datatype

*data Actor = Ball ... | Paddle ... | Wall ...*

and a function

*move (Ball ...) = *
*move (Paddle ...) = *
*move (Wall ...) = *

in Haskell one must put *Actor* and *move* into a single file.

This is rather cumbersome if you work with multiple people or want to keep
the files small and readable.

Surely it is possible to use type classes, existentials, etc to split the
data type into multiple ones, but that's already advanced stuff in a sense.

But wouldn't it be possible to allow these to be put into multiple files,
and let the compiler merge them back into one? A bit like C#'s partial
keyword:

in file Ball.hs:
*partial data Actor = Ball ...*
*move (Ball ...) =*

in Paddle.hs
*partial data Actor = Paddle ...*
*move (Paddle ...) =*

The compiler would then merge all partial data types and functions into one.

As far as no overlap exists in the pattern matches in move, so that the
order of the pattern matches does not matter at all, the partial trick
should be possible no?

Cheers,
Peter
___
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


Re: [Haskell-cafe] Splitting data and function declarations over multiple files

2009-09-30 Thread Niklas Broberg
Hi Peter,

sounds to me you want to have a look at Open Data Types and Open
Functions by Andres Löh and Ralf Hinze:

http://people.cs.uu.nl/andres/OpenDatatypes.pdf

Cheers,

/Niklas

On Wed, Sep 30, 2009 at 5:54 PM, Peter Verswyvelen bugf...@gmail.com wrote:
 I guess this is related to the expression problem.
 Suppose I have a datatype
 data Actor = Ball ... | Paddle ... | Wall ...
 and a function
 move (Ball ...) =
 move (Paddle ...) =
 move (Wall ...) =
 in Haskell one must put Actor and move into a single file.
 This is rather cumbersome if you work with multiple people or want to keep
 the files small and readable.
 Surely it is possible to use type classes, existentials, etc to split the
 data type into multiple ones, but that's already advanced stuff in a sense.
 But wouldn't it be possible to allow these to be put into multiple files,
 and let the compiler merge them back into one? A bit like C#'s partial
 keyword:
 in file Ball.hs:
 partial data Actor = Ball ...
 move (Ball ...) =
 in Paddle.hs
 partial data Actor = Paddle ...
 move (Paddle ...) =
 The compiler would then merge all partial data types and functions into one.
 As far as no overlap exists in the pattern matches in move, so that the
 order of the pattern matches does not matter at all, the partial trick
 should be possible no?
 Cheers,
 Peter










 ___
 Haskell-Cafe mailing list
 Haskell-Cafe@haskell.org
 http://www.haskell.org/mailman/listinfo/haskell-cafe


___
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


Re: [Haskell-cafe] Splitting data and function declarations over multiple files

2009-09-30 Thread Ryan Ingram
On Wed, Sep 30, 2009 at 8:54 AM, Peter Verswyvelen bugf...@gmail.comwrote:

 I guess this is related to the expression problem.


Actually, this is exactly the expression problem :)


 Suppose I have a datatype

 *data Actor = Ball ... | Paddle ... | Wall ...*

 and a function

 *move (Ball ...) = *
 *move (Paddle ...) = *
 *move (Wall ...) = *

 in Haskell one must put *Actor* and *move* into a single file.

 This is rather cumbersome if you work with multiple people or want to keep
 the files small and readable.

 Surely it is possible to use type classes, existentials, etc to split the
 data type into multiple ones, but that's already advanced stuff in a sense.


Yes, and type classes are the current solution.  I think the most elegant
solution right now is provided by Data Types a la Carte; see
http://www.cse.chalmers.se/~wouter/publications.html


 But wouldn't it be possible to allow these to be put into multiple files,
 and let the compiler merge them back into one? A bit like C#'s partial
 keyword:

 in file Ball.hs:
 *partial data Actor = Ball ...*
 *move (Ball ...) =*

 in Paddle.hs
 *partial data Actor = Paddle ...*
 *move (Paddle ...) =*

 The compiler would then merge all partial data types and functions into
 one.

 As far as no overlap exists in the pattern matches in move, so that the
 order of the pattern matches does not matter at all, the partial trick
 should be possible no?


Yes, that's true.  There's some good reading about this proposal here:
http://www.haskell.org/haskellwiki/Extensible_datatypes

  -- ryan
___
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe


Re: [Haskell-cafe] Splitting data and function declarations over multiple files

2009-09-30 Thread Luke Palmer
On Wed, Sep 30, 2009 at 9:54 AM, Peter Verswyvelen bugf...@gmail.com wrote:
 I guess this is related to the expression problem.
 Suppose I have a datatype
 data Actor = Ball ... | Paddle ... | Wall ...
 and a function
 move (Ball ...) =
 move (Paddle ...) =
 move (Wall ...) =
 in Haskell one must put Actor and move into a single file.
 This is rather cumbersome if you work with multiple people or want to keep
 the files small and readable.
 Surely it is possible to use type classes, existentials, etc to split the
 data type into multiple ones, but that's already advanced stuff in a sense.

You can do it without type classes and existentials.  The
functionality you want is already supported by Haskell, you just have
to let go of your syntactical expectations.  The trick is that you
should rewrite your data type not as an algebra (a set of
constructors), but as a coalgebra (a set of projections).

Let's say your two open functions are:

move :: Actor - Actor
isAlive :: Actor - Bool

This gives rise to the definition of an Actor type:

data Actor = Actor { move :: Actor, isAlive :: Bool }

And then the alternatives of your open data type are just values of type Actor:

ball :: Vector - Vector - Actor
ball pos vel = Actor {
move = ball (pos + vel) vel,
isAlive = True
  }

etc.

This trick works well until you get to the encoding of functions that
pattern match on multiple Actors at the same time.  As far as I can
tell, that cannot be encoded in this style in any reasonable way.
Such functions must be rephrased in a coalgebraic style; i.e. instead
of asking about constructors, using projection functions it knows are
available.

So for example instead of implementing collide by asking about
pairs, add functions which report a shape function and a normal, or
whatever your collide algorithm needs from shapes.

You would probably end up having to do this anyway even with your
proposed extension, because watch:

partial data Actor = Ball ...

collide (Ball ...) (Ball ...) = ...
collide (Ball ...) x = ...

We don't know about any other constructors, so the second line has to
contain a pattern-free x.  So you would have to use projection
functions to get any information about it, exactly as you would when
you're writing in the coalgebraic style.

So, Yes!  Haskell can do that!

Luke
___
Haskell-Cafe mailing list
Haskell-Cafe@haskell.org
http://www.haskell.org/mailman/listinfo/haskell-cafe