packages feed

non-negative-0.0.1: Test/Numeric/NonNegative/Chunky.hs

{- |
Copyright   :  (c) Henning Thielemann 2007

Maintainer  :  haskell@henning-thielemann.de
Stability   :  stable
Portability :  Haskell 98
-}
module Test.Numeric.NonNegative.Chunky (tests) where

-- import Test.Utility
import Test.QuickCheck (test, Property, (==>))

import qualified Numeric.NonNegative.Chunky  as Chunky
import qualified Numeric.NonNegative.Class   as NonNeg
import qualified Numeric.NonNegative.Wrapper as NonNegW
-- import Numeric.NonNegative.Class ((-|))

-- import Debug.Trace (trace)

import qualified Prelude as P
import Prelude hiding (min, max, abs, signum, compare)


infixl 5 $~

($~) :: NonNeg.C a =>
   (a -> b) -> (Chunky.T a -> b)
($~) f = f . Chunky.toNumber

infixl 4 ==~

(==~) :: NonNeg.C a =>
   Chunky.T a -> a -> Bool
(==~) xs ys =
   Chunky.toNumber xs == ys



add :: NonNeg.C a => Chunky.T a -> Chunky.T a -> Bool
add x y  =  x+y  ==~  (+) $~ x $~ y

sub :: NonNeg.C a => Chunky.T a -> Chunky.T a -> Bool
sub x y  =
   if x>y
     then x-y  ==~  (-) $~ x $~ y
     else y-x  ==~  (-) $~ y $~ x

mul :: NonNeg.C a => Chunky.T a -> Chunky.T a -> Bool
mul x y  =  x*y  ==~  (*) $~ x $~ y

min :: NonNeg.C a => Chunky.T a -> Chunky.T a -> Bool
min x y  =  P.min x y  ==~  P.min $~ x $~ y

max :: NonNeg.C a => Chunky.T a -> Chunky.T a -> Bool
max x y  =  P.max x y  ==~  P.max $~ x $~ y

abs :: NonNeg.C a => Chunky.T a -> Bool
abs x  =  P.abs x  ==~  P.abs $~ x

signum :: NonNeg.C a => Chunky.T a -> Bool
signum x  =  P.signum x  ==~  P.signum $~ x

equal :: NonNeg.C a => Chunky.T a -> Chunky.T a -> Bool
equal x y  =  (x == y)  ==  (==) $~ x $~ y

compare :: NonNeg.C a => Chunky.T a -> Chunky.T a -> Bool
compare x y  =  P.compare x y  ==  P.compare $~ x $~ y


infinity :: NonNeg.C a => a -> Chunky.T a
infinity = Chunky.fromChunks . repeat . (1+)

checkInfinity :: NonNeg.C a => a -> Chunky.T a -> Bool
checkInfinity limit x =
   let y = Chunky.fromNumber limit
   in  P.min x y == y

addInfiniteL :: NonNeg.C a => a -> a -> Chunky.T a -> Bool
addInfiniteL limit x y =
   checkInfinity limit (infinity x + y)

addInfiniteR :: NonNeg.C a => a -> a -> Chunky.T a -> Bool
addInfiniteR limit x y =
   checkInfinity limit (y + infinity x)


mulInfiniteL :: NonNeg.C a => a -> a -> Chunky.T a -> Property
mulInfiniteL limit x y =
   Chunky.isPositive y ==>
      checkInfinity limit (infinity x * y)

{- |
Without normalization the test would fail for
@y = Chunky.fromChunks [0,1]@
-}
mulInfiniteR :: NonNeg.C a => a -> a -> Chunky.T a -> Property
mulInfiniteR limit x y =
   Chunky.isPositive y ==>
      checkInfinity limit (Chunky.normalize y * infinity x)

{-
mulInfiniteL :: NonNeg.C a => a -> a -> Chunky.T a -> Bool
mulInfiniteL limit x y =
   if Chunky.isNull y
     then Chunky.isNull (infinity x * y)
     else checkInfinity limit (infinity x * y)

mulInfiniteR :: NonNeg.C a => a -> a -> Chunky.T a -> Bool
mulInfiniteR limit x y =
   if Chunky.isNull y
     then Chunky.isNull (y * infinity x)
     else checkInfinity limit (y * infinity x)
-}

minRecursiveL :: NonNeg.C a => Chunky.T a -> Chunky.T a -> Property
minRecursiveL x y =
   Chunky.isPositive x ==>
      let z = P.min (x+z) y
      in  z == y

minRecursiveR :: NonNeg.C a => Chunky.T a -> Chunky.T a -> Property
minRecursiveR x y =
   Chunky.isPositive x ==>
      let z = P.min y (x+z)
      in  z == y

minInfiniteL :: NonNeg.C a => a -> Chunky.T a -> Bool
minInfiniteL x y =
   P.min (infinity x) y  ==  y

minInfiniteR :: NonNeg.C a => a -> Chunky.T a -> Bool
minInfiniteR x y =
   P.min y (infinity x)  ==  y

maxInfiniteL :: NonNeg.C a => a -> a -> Chunky.T a -> Bool
maxInfiniteL limit x y =
   checkInfinity limit (P.max (infinity x) y)

maxInfiniteR :: NonNeg.C a => a -> a -> Chunky.T a -> Bool
maxInfiniteR limit x y =
   checkInfinity limit (P.max y (infinity x))

minInfiniteAssociative :: NonNeg.C a => a -> a -> Chunky.T a -> Bool
minInfiniteAssociative x y z =
   P.min (P.min (infinity x) (infinity y)) z  ==  z

maxInfiniteAssociative :: NonNeg.C a => a -> a -> a -> Chunky.T a -> Bool
maxInfiniteAssociative limit x y z =
   checkInfinity limit
      (P.max (P.max (infinity x) (infinity y)) z)

compareInfiniteL :: NonNeg.C a => a -> Chunky.T a -> Bool
compareInfiniteL x y =
   P.compare (infinity x) y == GT

compareInfiniteR :: NonNeg.C a => a -> Chunky.T a -> Bool
compareInfiniteR x y =
   P.compare y (infinity x) == LT





type Card = NonNegW.T Int

tests :: [(String, IO ())]
tests =
   ("add",
     test (add :: Chunky.T Card -> Chunky.T Card -> Bool)) :
   ("sub",
     test (sub :: Chunky.T Card -> Chunky.T Card -> Bool)) :
   ("mul",
     test (mul :: Chunky.T Card -> Chunky.T Card -> Bool)) :
   ("min",
     test (min :: Chunky.T Card -> Chunky.T Card -> Bool)) :
   ("max",
     test (max :: Chunky.T Card -> Chunky.T Card -> Bool)) :
   ("abs",
     test (abs :: Chunky.T Card -> Bool)) :
   ("signum",
     test (signum :: Chunky.T Card -> Bool)) :
   ("equal",
     test (equal :: Chunky.T Card -> Chunky.T Card -> Bool)) :
   ("compare",
     test (compare :: Chunky.T Card -> Chunky.T Card -> Bool)) :

   ("addInfiniteL",
     test (addInfiniteL :: Card -> Card -> Chunky.T Card -> Bool)) :
   ("addInfiniteR",
     test (addInfiniteR :: Card -> Card -> Chunky.T Card -> Bool)) :
   ("mulInfiniteL",
     test (mulInfiniteL :: Card -> Card -> Chunky.T Card -> Property)) :
   ("mulInfiniteR",
     test (mulInfiniteR :: Card -> Card -> Chunky.T Card -> Property)) :
   ("minRecursiveL",
     test (minRecursiveL :: Chunky.T Card -> Chunky.T Card -> Property)) :
   ("minRecursiveR",
     test (minRecursiveR :: Chunky.T Card -> Chunky.T Card -> Property)) :
   ("minInfiniteL",
     test (minInfiniteL :: Card -> Chunky.T Card -> Bool)) :
   ("minInfiniteR",
     test (minInfiniteR :: Card -> Chunky.T Card -> Bool)) :
   ("maxInfiniteL",
     test (maxInfiniteL :: Card -> Card -> Chunky.T Card -> Bool)) :
   ("maxInfiniteR",
     test (maxInfiniteR :: Card -> Card -> Chunky.T Card -> Bool)) :
   ("minInfiniteAssociative",
     test (minInfiniteAssociative :: Card -> Card -> Chunky.T Card -> Bool)) :
   ("maxInfiniteAssociative",
     test (maxInfiniteAssociative :: Card -> Card -> Card -> Chunky.T Card -> Bool)) :

   ("compareInfiniteL",
     test (compareInfiniteL :: Card -> Chunky.T Card -> Bool)) :
   ("compareInfiniteR",
     test (compareInfiniteR :: Card -> Chunky.T Card -> Bool)) :
   []