{-# LANGUAGE CPP #-}
{-# LANGUAGE FlexibleContexts #-}
{-# OPTIONS_GHC -fno-warn-orphans #-}
module Test.QuickCheck.Instances.Containers () where
import Prelude ()
import Prelude.Compat
import Data.Traversable (for)
import Test.QuickCheck
import qualified Data.Tree as Tree
instance Arbitrary1 Tree.Tree where
liftArbitrary arb = go
where
go = sized $ \n -> do
value <- arb
pars <- arbPartition (n - 1)
forest <- for pars $ \i -> resize i go
return $ Tree.Node value forest
arbPartition :: Int -> Gen [Int]
arbPartition k = case compare k 1 of
LT -> pure []
EQ -> pure [1]
GT -> do
first <- elements [1..k]
rest <- arbPartition $ k - first
return $ first : rest
liftShrink shr = go
where
go (Tree.Node val forest) = forest ++
[ Tree.Node e fs
| (e, fs) <- liftShrink2 shr (liftShrink go) (val, forest)
]
instance Arbitrary a => Arbitrary (Tree.Tree a) where
arbitrary = arbitrary1
shrink = shrink1
instance CoArbitrary a => CoArbitrary (Tree.Tree a) where
coarbitrary (Tree.Node val forest) =
coarbitrary val . coarbitrary forest