Reputation: 5914
I was playing with Haskell and ghci when I found this which really bothers me:
foldl (++) [[3,4,5], [2,3,4], [2,1,1]] []
I expected to get this: [3,4,5,2,3,4,2,1,1]
However it gets:
[[3,4,5],[2,3,4],[2,1,1]]
As far as I understand foldl, it should be this:
(([] ++ [3, 4, 5]) ++ [2, 3, 4]) ++ [2, 1, 1]
If I type this in ghci it really is [3,4,5,2,3,4,2,1,1]
.
And the other strange thing is this:
Prelude> foldl1 (++) [[3,4,5], [2, 3, 4], [2, 1, 1]]
[3,4,5,2,3,4,2,1,1]
I expect foldl and foldl1 to behave in the same way. So what does foldl actually do?
Upvotes: 7
Views: 829
Reputation: 40336
You got the argument order wrong
Prelude> :t foldl
foldl :: (a -> b -> a) -> a -> [b] -> a
Prelude> :t foldl1
foldl1 :: (a -> a -> a) -> [a] -> a
The initial value comes first. In your case, your initial value was [[3,4,5],[2,3,4],[2,1,1]]
and you folded over the empty list, so you got back the initial value.
Upvotes: 2
Reputation: 370172
You switched the arguments around. foldl
takes the accumulator's starting value first, then the list to fold. So what happens in your case is that foldl
folds over the empty list and thus returns the starting value, which is [[3,4,5], [2, 3, 4], [2, 1, 1]]
. This will do what you want:
foldl (++) [] [[3,4,5], [2, 3, 4], [2, 1, 1]]
Upvotes: 5
Reputation: 3865
The order of arguments is wrong. The right one is:
foldl (++) [] [[3,4,5], [2,3,4], [2,1,1]]
(That is, first the accumulator, then the list.)
Upvotes: 21