2009-04-03 2 views
1

Как этот код:путаюсь о параллельном Haskell

parfib :: Int -> Int 
parfib 0 = 1 
parfib 1 = 1 
parfib n = nf2 `par` (nf1 `par` (nf1+nf2+1)) 
      where nf1 = parfib (n-1) 
       nf2 = parfib (n-2) 

лучше, чем это:

parfib :: Int -> Int 
parfib 0 = 1 
parfib 1 = 1 
parfib n = nf2 `par` (nf1 `seq` (nf1+nf2+1)) 
      where nf1 = parfib (n-1) 
       nf2 = parfib (n-2) 

Я не получаю Объяснения, которые я нашел в Интернете, что сказать: «Для того, чтобы гарантировать что основное выражение оценивается в правильном порядке (т. е. без блокировки основной задачи над дочерней задачей) используется аннотация seq ».

Почему используется seq? Я знаю, что это заставляет интерпретатора сначала оценить parfib (n-1), но зачем это необходимо?

При выполнении второй программы, не будет ли интерпретатор испускать новый процесс для оценки nf2, одновременно оценивая nf1 выражения nf1 + nf2 + 1? Что нужно сказать, чтобы указать, что он должен начинаться с nf1?

+0

Возможно, это будет 'pseq', а не' seq' (http://www.haskell.org/hoogle/?hoogle=pseq) – Matt

ответ

4

Не имеет смысла оценивать nf1 параллельно с nf1+..., поскольку последний зависит от nf1, поэтому все, что он будет делать, это блок на искру nf1. Используя seq, он попытается использовать только nf1, если вы знаете, что он был оценен.

0

это может быть потому, что мы хотим, чтобы свести к минимуму количества искр от моего понимания два vesrsion будут производить тот же результат

, но с первым вариантом вы будете искрение два дополнительных процесса (nf1, nf2). Но когда мы используем seq, мы просто вызываем только один дополнительный процесс (nf1).

Смежные вопросы