Reputation: 37
I’m trying to compute the mean, given a list that has this structure:
lData = [("A", "EXP1", 5),("A", "EXP2", 9),("B", "EXP15", 8),("C", "EXP16", 7),("B", "EXP24", 4)]
First I group the elements by the first element of the tuple, and get this list of tuples that has as second element the list where I’m willing to compute the mean:
[("A", [5,9]),("B", [8,4]), ("C", [7])]
When I try to call the function computeMean
I get an error.
I try to get the array of numbers first by doing
snd . head $ myGroup lData
and get [5,9]
and that’s OK. But don’t know how to go on from there.
I’ve created the function computeMean
that given a list, returns the mean of the elements of the list.
computeMean $ snd . head $ myGroup lData
gets the mean properly, but don’t know how apply it to all the elements.
The result I’m looking for is a list containing the first element of the tuple and the mean, such as:
[(“A”,7), (“B”,6), (“C”,7)]
But cannot get it right. Any advice?
import Data.Function (on)
import Data.List (sortBy, groupBy)
import Data.Ord (comparing)
fst3 :: (a, b, c) -> a
fst3 (x, _, _) = x
nextElem :: (a, b, c) -> (c)
nextElem (_, _, c) = (c)
myGroup :: (Eq a, Ord a) => [(a, b, c)] -> [(a, [c])]
myGroup = map (\l -> (fst3 . head $ l, map nextElem l)) . groupBy ((==) `on` fst3) . sortBy (comparing fst3)
computeMean :: [Double] -> Double
computeMean [] = 0
computeMean (a) = sum a / fromIntegral(length a)
lData = [("A", "EXP1", 5),("A", "EXP2", 9),("B", "EXP15", 8),("C", "EXP16", 7),("B", "EXP24", 4)]
main = do
print $ myGroup lData
computeMean $ snd . head $ myGroup lData
Upvotes: 0
Views: 65
Reputation: 1779
Well, you just lack the last step:
-- A new function to compute the mean value in the tuple
meanTuple :: (String, [Double]) -> (String, Double)
meanTuple (k, v) = (k, computeMean v)
main = print . map meanTuple . myGroup $ lData
Upvotes: 1