import System.Random
runningSumsOfValuesPerKey :: (Eq k, Num v) => [k] -> [(k, v)] -> [[v]]
runningSumsOfValuesPerKey allPossibleKeys = runningSums . allValuesPerKey
where
runningSums = map (scanl (+) 0)
allValuesPerKey pairs = [ valuesWithKey key pairs | key <- allPossibleKeys ]
valuesWithKey key = map snd . filter ((==key) . fst)
-- Testing
randomPairs :: [(Char, Integer)]
randomPairs = zip keys values
where
keys = randomRs ('a','z') rnd1
values = randomRs (0,9) rnd2
(rnd1,rnd2) = split (mkStdGen 0)
test = map (take 10) [rs `atKey` 'c', rs `atKey` 'z']
where
rs = runningSumsOfValuesPerKey ['a'..] randomPairs
xs `atKey` k = xs !! (fromEnum k - fromEnum 'a')