views:

113

answers:

1

I'm doing some homework and while I have some experience with SML, Haskell has some oddities. Consider this simple function:

type Pos = (Int, Int)
data Move = North | South | East | West
move :: Move -> Pos -> Pos
move North (x,y) = (x, y+1)
move South (x,y) = (x, y-1)
move East  (x,y) = (x+1, y)
move West  (x,y) = (x-1, y)

moves :: [Move] -> Pos -> Pos
moves (m:ms) (x,y) = moves ms (move m (x,y))
moves [] p = p

This code works. However, if I swap out the (x,y) tuple (which I dont use anyway) with a simple p it fails on invocation (the declaration works fine of course):

moves :: [Move] -> Pos -> Pos
moves (m:ms) p = moves ms (move m p)
moves [] p = p

*Main> let p = (1,1) :: Pos
*Main> move [North, North] p

<interactive>:1:5:
    Couldn't match expected type `Move' against inferred type `[a]'
    In the first argument of `move', namely `[North, North]'
    In the expression: move [North, North] p
    In the definition of `it': it = move [North, North] p

Which seems strange to me, as the second parameter is already typed as a Pos in the definition, so how come this chokes, and only on invocation? I'm using ghci btw.

+5  A: 

You did forget an "s" at the end of move**s** call, didn't you?

*Main> move [North, North] p
Pavel Shved
Yes, he did. He passed move something of type [a], when it was expecting `Move'. And amazingly, that's exactly what the error message says.
jrockway
Bah... >_>
Svend