Reputation: 359
I am having issues to convert a list with multiple tuples into a datatype
data SensorValue = SensorValue {a:: Integer, b:: Integer, c:: [Integer]} deriving (Show)
my list with tuples looks like this:
[(1, [(2, [3,4,5]), (2, [2,3,1]), (3, [2,3,7])]), (2, [(1, [4,4,1]), (2, [2,3,1]), (3, [9,0,3])]),...]
so basically my list looks like [(Integer, [(Integer, [Integer])])]
If I take the first tuple from my list (1, [(2, [3,4,5])
then my expected output is:
a SensorValue object with :
a = 1 -- first element of the first tuple
b = 2 -- first element of the second tuple
c = [3,4,5] -- second element of the second tuple
I know how to get to the first tuple with fst
but how do I get to the second tuple?
Upvotes: 1
Views: 246
Reputation: 21757
You can use pattern matching here. Your function would look something like this:
f :: (Integer,[(Integer,[Integer])]) -> [SensorValue]
f (x,((y,z):zs)) = SensorValue x y z : f (x,zs) -- First element same for all
f(x,[]) = []
You would still need to specify the conditions to handle other cases e.g. What happens if the list that forms the second element of the outer tuple is empty?
Upvotes: 2
Reputation: 152682
List comprehensions or do syntax make this quite nice -- assuming you understand them!
doSyntax, listComprehensions :: [(Integer, [(Integer, [Integer])])] -> [SensorValue]
doSyntax sensorPoints = do
(a, pointsAtA ) <- sensorPoints
(b, valuesAtAB) <- pointsAtA
return (SensorValue a b valuesAtAB)
listComprehensions sensorPoints =
[ SensorValue a b valuesAtAB
| (a, pointsAtA ) <- sensorPoints
, (b, valuesAtAB) <- pointsAtA
]
Depending on just what you want to do, you might even consider storing just one sensor value in each element of the result list. Like this (with a variant on the naming scheme above, just for fun):
data SensorValue = SensorValue { a, b, val :: Integer }
fromRawData abvalM =
[ SensorValue a b val
| (a, bvalM) <- abvalM
, (b, valM) <- bvalM
, val <- valM
]
Upvotes: 2