Задача понимания параллельных и обобщенных (подобных SQL) списков в Haskell - PullRequest
4 голосов
/ 10 мая 2011

Возможно, я неправильно читаю документы (http://www.haskell.org/ghc/docs/7.0.1/html/users_guide/syntax-extns.html#parallel-list-comprehensions), но в следующем коде я ожидаю, что значения списка zs и zs 'будут иметь одно и то же значение. Однако они отличаются, как показано при основной печатидве разные строки:

{-# LANGUAGE ParallelListComp, TransformListComp #-}
import GHC.Exts

xs = [10,20..90]
ys = map (`mod`7) xs

zs = [(x,y) | x<-xs | y<-ys, then sortWith by y]
zs' = [(x,y) | (x,y) <- zip xs ys, then sortWith by y]

main = print zs >> print zs'

Я просто неправильно читаю документы или есть какая-то худшая проблема? Я удивлен, что система типов не уловила ошибку в реальном коде, от которого она была абстрагирована.

Этот вывод производится:

*Main> main
[(10,0),(20,1),(30,2),(40,3),(50,3),(60,4),(70,5),(80,6),(90,6)]
[(70,0),(50,1),(30,2),(10,3),(80,3),(60,4),(40,5),(20,6),(90,6)]

Спасибо.

Ответы [ 3 ]

1 голос
/ 10 мая 2011

Dons, спасибо, теперь я не уверен, что я сделал, что сделал правильный вывод. Да, этот код в моем комментарии является синтаксической ошибкой (и я не могу ее исправить или оставить комментарий, потому что у меня больше нет файла cookie браузера, вздох) Я не вижу способа исправить это, кроме как с помощью «zip», что немного разочаровывает, ну да ладно. (О, похоже, я могу вносить изменения в очередь, в отличие от mathoverflow).

1 голос
/ 10 мая 2011

Комментарий Солриза, кажется, правильный.Первый результат заключается в том, что планка ассоциируется более свободно, чем запятая.Это задокументировано в ссылке Донса в разделе «Понимание параллельного списка».Не уверен, что можно сделать с этим ...

Следующее ужасно некрасиво (дублирующие привязки (x, y)), но исправляет синтаксическую ошибку Solrize, кстати ...

zs <- [(x,y) | (x,y) <- [(x,y) | x<-xs | y<-ys], then sortWith by y]

То, что было бы идеально, было бы каким-то образом заключить в скобки | разделы параллельных списков, такие как следующее:

zs = [(x,y) | (x<-xs | y<-ys), then sortWith by y]
0 голосов
/ 10 мая 2011

Похоже, ошибка для меня. Это как минимум неспособность четко объяснить, что такое синтаксический перевод. Условная ссылка solrize гласит:

При условии параллельного понимания формы:

[ e | p1 <- e11, p2 <- e12, ... 
    | q1 <- e21, q2 <- e22, ... 
     ... 
 ] 

Это будет переведено на:

[ e | ((p1,p2), (q1,q2), ...) <- zipN [(p1,p2) | p1 <- e11, p2 <- e12, ...] 
                                      [(q1,q2) | q1 <- e21, q2 <- e22, ...] 
                                      ... 

Интуиция поместит , then sortWith by y в окончательный многоточие:

[ (x,y) | x <- xs
        | y <- ys
        , then sortWith by y ]

Что бы перевести на

-- this produces the same result as your zs'
[ (x,y) | (x,y) <- zip [x' | x' <- xs]
                       [y' | y' <- ys]
                       , then sortWith by y ]

Однако на самом деле, похоже, что он находится в месте второго-последнего многоточия:

[ (x,y) | x <- xs
        | y <- ys, then sortWith by y
        ]

Перевод на

-- this produces the same result as your zs
[ (x,y) | (x,y) <- zip [x' | x' <- xs]
                       [y' | y' <- ys, then sortWith by y']
                       ]
...