parList vs parTraversable

Vũ *_* Tô 7 parallel-processing haskell

我在这里发现了一种"奇怪"的行为.我懂了:

{-# LANGUAGE BangPatterns #-}

import Data.List
import Control.Parallel
import Control.Parallel.Strategies

fib 0 = 1
fib 1 = 1
fib n = fib (n-1) + fib (n-2)

main =
  let xs = [ fib (20 + n `mod` 2) | n <- [0..1000] ]
              `using` test rseq
   in print (sum xs)

test :: Strategy a -> Strategy [a]
test strat xs = do
  parTraversable strat xs  -- case #1
  -- parList strat xs      -- case #2
  return xs
Run Code Online (Sandbox Code Playgroud)

case #1意思是使用parTraversable,case #2意思是使用parList.结果不同:

case #1: SPARKS: 1001 (1 converted, 0 overflowed, 0 dud, 1000 GC'd, 0 fizzled)
case #2: SPARKS: 1001 (1000 converted, 0 overflowed, 0 dud, 0 GC'd, 1 fizzled)
Run Code Online (Sandbox Code Playgroud)

据我所知,parList是一样的parTraversable.在Control/Parallel/Strategies.hs:

parTraversable :: Traversable t => Strategy a -> Strategy (t a)
parTraversable strat = evalTraversable (rparWith strat)

parList :: Strategy a -> Strategy [a]
parList = parTraversable
Run Code Online (Sandbox Code Playgroud)

所以我认为他们必须采取同样的行动.有什么需要在这里发现?

更新#1:

编译和运行的命令:

stack ghc -- -O2 -threaded -rtsopts -eventlog parlist2.hs
./parList2 +RTS -N2 -s
Run Code Online (Sandbox Code Playgroud)