{-# LANGUAGE CPP #-}
#if __GLASGOW_HASKELL__ >= 800 && MIN_VERSION_dlist(1,0,0)
#define DNONEMPTY 1
#endif
module Main (main) where
import Criterion.Main
import Prelude ()
import Prelude.Compat
import Data.DList.Instances ()
import Data.Foldable (toList)
import Data.List (foldl')
import Data.Semigroup (Semigroup (..))
import qualified Data.DList as DList
import qualified Data.DList.NonEmpty as NEDList
import qualified Data.List.NonEmpty as NE
#ifdef DNONEMPTY
import qualified Data.DList.DNonEmpty as DNonEmpty
#endif
sumRight :: (Semigroup (f Int), Foldable f) => Int -> f Int -> Int
sumRight m x = foldl' (+) 0 $ toList $ go x m
where
go y n | n <= 0 = y
| otherwise = go (y <> x) (n - 1)
sumLeft :: (Semigroup (f Int), Foldable f) => Int -> f Int -> Int
sumLeft m x = foldl' (+) 0 $ toList $ go x m
where
go y n | n <= 0 = y
| otherwise = go (x <> y) (n - 1)
sumTree :: (Semigroup (f Int), Foldable f) => Int -> f Int -> Int
sumTree m x = foldl' (+) 0 $ toList $ go m
where
go n | n <= 0 = x
| otherwise = let y = go (n - 1) in y <> y
main :: IO ()
main = defaultMain
-- left append is fast
[ bgroup "left-append"
[ bench "List" $ whnf (sumLeft 1024) $ [1,2,3,4,5]
, bench "NonEmpty" $ whnf (sumLeft 1024) $ 1 NE.:| [2,3,4,5]
, bench "DList" $ whnf (sumLeft 1024) $ DList.fromList [1,2,3,4,5]
, bench "NonEmptyDList" $ whnf (sumLeft 1024) $ NEDList.fromNonEmpty $ 1 NE.:| [2,3,4,5]
#ifdef DNONEMPTY
, bench "DNonEmpty" $ whnf (sumLeft 1024) $ DNonEmpty.fromNonEmpty $ 1 NE.:| [2,3,4,5]
#endif
]
-- naive right append is quadratic for list
, bgroup "right-append"
[ bench "List" $ whnf (sumRight 1024) $ [1,2,3,4,5]
, bench "NonEmpty" $ whnf (sumRight 1024) $ 1 NE.:| [2,3,4,5]
, bench "DList" $ whnf (sumRight 1024) $ DList.fromList [1,2,3,4,5]
, bench "NonEmptyDList" $ whnf (sumRight 1024) $ NEDList.fromNonEmpty $ 1 NE.:| [2,3,4,5]
#ifdef DNONEMPTY
, bench "DNonEmpty" $ whnf (sumRight 1024) $ DNonEmpty.fromNonEmpty $ 1 NE.:| [2,3,4,5]
#endif
]
-- not sure what to expect
, bgroup "tree"
[ bench "List" $ whnf (sumTree 10) $ [1,2,3,4,5]
, bench "NonEmpty" $ whnf (sumTree 10) $ 1 NE.:| [2,3,4,5]
, bench "DList" $ whnf (sumTree 10) $ DList.fromList [1,2,3,4,5]
, bench "NonEmptyDList" $ whnf (sumTree 10) $ NEDList.fromNonEmpty $ 1 NE.:| [2,3,4,5]
#ifdef DNONEMPTY
, bench "DNonEmpty" $ whnf (sumTree 10) $ DNonEmpty.fromNonEmpty $ 1 NE.:| [2,3,4,5]
#endif
]
]