У меня есть такой список: (псевдо-запись)
(X,...) -> (X,...) -> (X,...) -> ...
| | |
V V V
(Y,...) (Y,...) (Y,...)
| | |
V V V
(Z,...) (Z,...) (Z,...)
Тип: (Enum a, Bounded a) => [[(a,x)]]
.Но мне нужно что-то вроде этого:
(X, ... -> ... -> ... -> ...
|
V
(Y, ... -> ... -> ... -> ...
|
V
(Z, ... -> ... -> ... -> ...
Тип похож на (Enum a, Bounded a) => [(a,[x])]
x имеет произвольное количество элементов.Можно предположить, что каждый член x является ключом в каждом подсписке первого списка.
Как это преобразование возможно в виде ленивого алгоритма haskell (List не нужно оценивать полностью, чтобы вернуться (частично) результат)?
Тестовые данные
См. выше, что-то вроде этого:
--Input
[[(Foo,1),(Bar,1),(Baz,1)],[(Foo,2),(Bar,2),(Baz,2)],...]
--Output
[(Foo,[1,2,3,...]),(Bar,[1,2,3,...),(Baz,[1,2,3,...])]
Что я хочу сделать с данными
IВы хотите использовать его в такой функции:
myFunc :: [(MyEnum,[Int])]
myFunc x@((_,(_:[])):_) = x
myFunc x = foldTheListRecursively
Функция должна работать с большими объемами данных (~ 10 000 записей на перечисление), список должен собираться мусором системой времени выполнения (Список создается adhoc другой частью программы)
Моя (некрасивая) реализация
Я так и реализовал, но, очевидно, он не соответствует требованиям, так каксписок просматривают несколько раз:
restructList :: [[(a,x)]] -> [(a,[x])]
resturctList list = (\x -> (x,listFor x)) <$> keys where
keys = fst <$> head list
listFor x = snd <$> any ((==x).fst) <$> list
Я не дома, поэтому не могу проверить его, поэтому может быть ошибка.