Problem: using fold, take from the list elements which are on the even positions:
GHCi> evenOnly [1..10]
[2,4,6,8,10]
GHCi> evenOnly ['a'..'z']
"bdfhjlnprtvxz"
evenOnly :: [a] -> [a]
evenOnly = undefined
I decided at first to get a list of alternating 0
-es and 1
-s: [0,1,0,1..]
Prelude> let g = iterate (x -> (x + 1) `mod` 2) 0
Prelude> take 10 $ g
[0,1,0,1,0,1,0,1,0,1]
Then zip it with the original list, getting a list of pairs: [(x1, 0), (x2,1), (x3,0) .. (xn, ?)]
:
Prelude> zip g [1,2,3,4,5]
[(0,1),(1,2),(0,3),(1,4),(0,5)]
After that, foldr
the list of pairs with a filtering function and an empty list as initialization value.
So I thought that this would work:
evenOnly :: [a] -> [a]
evenOnly xs = let g = iterate (x -> (x + 1) `mod` 2) 0
in
foldr ( (x, n) s -> if n == 1 then x : s else s) [] . (zip g xs)
But it gives an error, that I don't understand:
foldr.hs:44:59: error:
? Couldn't match expected type ‘a0 -> t0 (a1, Integer)’
with actual type ‘[(Integer, a)]’
? Possible cause: ‘zip’ is applied to too many arguments
In the second argument of ‘(.)’, namely ‘(zip g xs)’
In the expression:
foldr ( (x, n) s -> if n == 1 then x : s else s) [] . (zip g xs)
In the expression:
let g = iterate ( x -> (x + 1) `mod` 2) 0
in
foldr ( (x, n) s -> if n == 1 then x : s else s) [] . (zip g xs)
? Relevant bindings include
xs :: [a] (bound at foldr.hs:42:10)
evenOnly :: [a] -> [a] (bound at foldr.hs:42:1)
I think my idea is correct, I just did something wrong with the syntax.
See Question&Answers more detail:
os