{-# OPTIONS_GHC -F -pgmF htfpp #-} module Main where import Test.Framework import Data.Numbers.Primes import Data.Numbers.Primes.Type import Data.Word instance (Arbitrary a, Integral a) => Arbitrary (Prime a) where arbitrary = getPrime <$> arbitrarySizedNatural main = htfMain htf_thisModulesTests -- | Some basic sanity checks. test_prime = do assertEqual (Just $ getPrime 0) (maybePrime 2) assertEqual (Just $ getPrime 5) (maybePrime 13) assertEqual (primeIndex 2) (Just 0) assertEqual (primeIndex 13) (Just 5) assertEqual (maybePrime 4) (Nothing) -- | These two properties show that Prime and its value are -- isomorphic if and only if the value is prime. -- (n in N but not in P are mapped to Nothing with no inverse.) -- prop_maybePrime :: Integral int => int -> Bool -- ^ This is too general to suit a prop. prop_maybePrime_Int = withQCArgs (\prop -> prop { maxSize = 1024 } ) prop_maybePrime_Int' where prop_maybePrime_Int' :: Int -> Bool prop_maybePrime_Int' x = r == Just x || r == Nothing where r :: Maybe Int r = getValue <$> maybePrime x prop_maybePrime_Integer = withQCArgs (\prop -> prop { maxSize = 1024 } ) prop_maybePrime_Integer' where prop_maybePrime_Integer' :: Integer -> Bool prop_maybePrime_Integer' x = r == Just x || r == Nothing where r :: Maybe Integer r = getValue <$> maybePrime x prop_maybePrime_Word = withQCArgs (\prop -> prop { maxSize = 5 } ) prop_maybePrime_Word' where prop_maybePrime_Word' :: Word8 -> Bool prop_maybePrime_Word' x = r == Just x || r == Nothing where r :: Maybe Word8 r = getValue <$> maybePrime x prop_getValue_Int = withQCArgs (\prop -> prop { maxSize = 1024 } ) prop_getValue_Int' where prop_getValue_Int' :: Int -> Bool prop_getValue_Int' n = (maybePrime . getValue $ p) == Just p where p :: Prime Int p | n < 0 = getPrime . abs $ n -- I know it's not super bright. | otherwise = getPrime n -- | These two properties show that Prime and its index are isomorphic. prop_primeIndex :: Int -> Bool prop_primeIndex n = m == (getIndex <$> getPrime) m where m = abs n prop_getIndex :: Int -> Bool prop_getIndex n = getPrime m == (getPrime . getIndex . getPrime) m where m = abs n -- | This property verifies the correctness of `deconstruct`. prop_deconstruct i = deconstruct p == (getValue p, getIndex p) where p = getPrime (abs i) -- | These two properties show that the enumeration associated with Prime is isomorphic. prop_fromEnum :: Prime Int -> Bool prop_fromEnum p = p == (toEnum . fromEnum) p prop_toEnum :: Int -> Bool prop_toEnum n' = n == (fromEnum . (toEnum :: Int -> Prime Int)) n where n = abs n' -- | Equality & ordering of primes is the same as the respective relations on their indices. prop_Eq = withQCArgs (\prop -> prop { maxSize = 256 } ) prop_Eq' where prop_Eq' :: (Int, Int) -> Bool prop_Eq' (i', j') = (i == j) == (getPrime i == getPrime j) where i = abs i' j = abs j' prop_compare = withQCArgs (\prop -> prop { maxSize = 256 } ) prop_compare' where prop_compare' :: (Int, Int) -> Bool prop_compare' (i', j') = i `compare` j == (getPrime i `compare` getPrime j) where i = abs i' j = abs j' -- | The list of indexed primes corresponds to its unzips. test_indexedPrimes = assertEqual (deconstruct <$> take 100 indexedPrimes) (take 100 $ zip primes [0..])