Haskell has the sum function
sum :: Num a => [a] -> a
Which can be nicely composed to sum a matrix by
sum . map sum :: Num a => [[a]] -> a
Going deeper, however, such as summing a cube, creates the restriction Num [a]
sum . map sum . map sum :: (Num a, Num [a]) => [[[a]]] -> a
Which, if you think about it, is natural. So with the former attempt to define the sumcube function blowing up in one's face, we need to find a different path. One such attempt would be:
sum . map sum . map (map sum) :: Num a => [[[a]]] -> a
Which seems nowhere as natural as the summatrix function.
In my quest to posessing the mental tools for problem solving in Haskell, I am interested in knowing how to tackle this problem of summing a structure of any depth by, say, stacking map sum
s as in my third code example. Is this at all possible? And in that case, how would you do it?
How about typeclasses?
class Summable a where
total :: a -> Int
instance Summable Int where
total = id
instance Summable x => Summable [x] where
total = sum . map total
total ([[[1,2,3],[4,5]],[[6],[7,8,9,10]]] :: [[[Int]]])
--55
You'll have to work from the inside out. When you have a function f
for summing a data structure, then sum . map f
is the way to sum a list of those data structures.
sum :: Num a => [a] -> a
sum . map sum :: Num a => [[a]] -> a
sum . map (sum . map sum) :: Num a => [[[a]]] -> a
Maybe this? Assumes associativity, but adding new layer is simple
sum . concat . concat :: Num c => [[[c]]] -> c
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With