Search code examples
haskellcurryingfunction-compositionpartial-application

Function Composition - Haskell


again another question generated by my attempts at the Project Euler questions (follow on from a previous question). I'm having trouble understanding the following line:

print (maximum (map (product . take 13) (tails number)))

Specifically

map (product . take 13) (tails number)

The type signature for the first argument of map from ghci is [c] -> c:

ghci> :t (product . take 13)
(product . take 13) :: Num c => [c] -> c

The type signature for map (product . take 13) from ghci is [[b]] -> [b]:

ghci> :t map (product . take 13)
map (product . take 13) :: Num b => [[b]] -> [b]

Am I right in saying that as the first argument of map should be a function, [[b]] is not referring to a list of lists, but rather to a list of (partially applied) functions generated by (product . take 13), with the second argument for the partial functions coming from (tails number)?


Solution

  • Here is a point-free version:

    euler8 :: (Ord c, Num c) => [c] -> c
    euler8 = maximum . map (product . take 13) . tails
    

    let's make this a bit more obvious:

    euler8' numbers = 
      let segments = tails numbers
          groups   = map (take 13) segments -- only take up to 13 numbers from each segment
          products = map product groups
          max      = maximum products
      in max
    

    so as you can see - it first gets the final-segments of the numbers-list (this is a list again)

    then it uses map to get the product for each of these segments (again a list)

    and finaly it searches for the maximum of those products and returns it

    PS: I striped the print in both versions - I think the IO will just complicate matters and it's not really important ... you can always print it out afterwards ;)