Учитывая типы
data Prisoner = P { _name :: String
, _rank :: Int
, _cereal :: Cereal }
data Cereal = C { _number :: Int
, _percentDailyValue :: Map String Float
, _mascot :: String }
Я мог бы получить имя кого-то, ранга и злака с помощью сопоставления с образцом:
getNameRankAndCerealNumber_0 :: Prisoner -> (String, Int, Int)
getNameRankAndCerealNumber_0 (P { _name=name
, _rank=rank
, _cereal = C { _number=cerealNumber }}
) = (name, rank, cerealNumber)
В качестве альтернативы, я мог бы использовать линзы для извлечения каждой части отдельно
makeLenses ''Cereal
makeLenses ''Prisoner
getNameRankAndCerealNumber_1 :: Prisoner -> (String, Int, Int)
getNameRankAndCerealNumber_1 p = (p ^. name, p ^. rank, p ^. cereal.number)
Есть ли способ извлечь все три одновременно в один обход структуры данных?
Как можно объединить Getter
s, Getter s a -> Getter s b -> Getter s (a,b)
?