我遇到了将包含多个元组的列表转换为数据类型
的问题data SensorValue = SensorValue {a:: Integer, b:: Integer, c:: [Integer]} deriving (Show)
我的元组列表如下所示:
[(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])]),...]
基本上我的列表看起来像[(Integer, [(Integer, [Integer])])]
如果我从列表(1, [(2, [3,4,5])
中取出第一个元组,那么我的预期输出是:
一个SensorValue对象:
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
我知道如何使用fst
获取第一个元组但是如何进入第二个元组?
答案 0 :(得分:2)
您可以在此处使用模式匹配。你的功能看起来像这样:
f :: (Integer,[(Integer,[Integer])]) -> [SensorValue]
f (x,((y,z):zs)) = SensorValue x y z : f (x,zs) -- First element same for all
f(x,[]) = []
您仍需要指定处理其他情况的条件,例如如果构成外元组的第二个元素的列表为空,会发生什么?
答案 1 :(得分:2)
列出理解或做语法使这很好 - 假设你理解它们!
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
]
根据您想要做的事情,您甚至可以考虑在结果列表的每个元素中仅存储一个传感器值。像这样(上面的命名方案有一个变体,只是为了好玩):
data SensorValue = SensorValue { a, b, val :: Integer }
fromRawData abvalM =
[ SensorValue a b val
| (a, bvalM) <- abvalM
, (b, valM) <- bvalM
, val <- valM
]