haskelltypesfunctional-programmingtype-declaration

How does scanl in Haskell work on list of Either's - comparison of two cases


I am trying to use the scanl function in Haskell. I have narrowed down my problem which can be described in the following two cases, which can be run in the interpreter using just a normal library within Haskell that contains the scanl (Note that I am not necessarily interested in the Monadic value here, but just how to use scanl to ensure a type consistency):

Why does the following with pre-listed Right values work work:

*Defs> scanl (\x acc -> x ++ acc) [] [[(Right 1)], [(Right 2)]]  
[[],[Right 1],[Right 1,Right 2]]

when this doesn't work and causes the following error message:

*Defs> scanl (\x acc -> [x] ++ acc) [] [(Right 1), (Right 2)]

<interactive>:36:35: error:
    * Couldn't match expected type `[[a]]'
                  with actual type `Either a0 b0'
   ...

Solution

  • I think you have the value and accumulator swapped. Consider the type of scanl:

    ghci> :t scanl
    scanl :: (b -> a -> b) -> b -> [a] -> [b]
    

    The accumulator value is of the type b. It comes first.

    If you swap the arguments in your second example, it works:

    ghci> scanl (\acc x -> acc ++ [x]) [] [(Right 1), (Right 2)]
    [[],[Right 1],[Right 1,Right 2]]
    

    You can also swap the argument of the first example, and that, too, works:

    ghci> scanl (\acc x -> acc ++ x) [] [[(Right 1)], [(Right 2)]]
    [[],[Right 1],[Right 1,Right 2]]