aern2-real-0.2.0.0: src/AERN2/Real/Tests.hs
{-# OPTIONS_GHC -Wno-orphans #-}
{-|
Module : AERN2.Real.Tests
Description : Tests for operations on Cauchy real numbers
Copyright : (c) Michal Konecny
License : BSD3
Maintainer : mikkonecny@gmail.com
Stability : experimental
Portability : portable
Tests for operations on Cauchy real numbers.
To run the tests using stack, execute:
@
stack test aern2-real --test-arguments "-a 1000 -m Real"
@
-}
module AERN2.Real.Tests
(
-- specCauchyReal, tCReal
)
where
import MixedTypesNumPrelude
-- import qualified Prelude as P
-- import Data.Ratio
-- import Text.Printf
import qualified Numeric.CollectErrors as CN
import Test.Hspec
import Test.QuickCheck
-- import qualified Test.Hspec.SmallCheck as SC
-- import AERN2.Norm
import AERN2.MP.Accuracy
--
import AERN2.MP
import AERN2.MP.Dyadic
import AERN2.Real.Type
import AERN2.Real.Field ()
instance Arbitrary CReal where
arbitrary =
frequency
[(int 1, creal <$> (arbitrarySmall 1000000 :: Gen Integer)),
(int 1, creal <$> (arbitrarySmall 1000000 :: Gen Rational)),
(int 2, (*) <$> (arbitrarySmall 1000000 :: Gen Integer) <*> arbitrarySignedBinary)
]
where
arbitrarySignedBinary =
signedBinary2Real <$> infiniteListOf (elements [-1,0,1])
signedBinary2Real sbits =
crealFromPrecFunction $ \ p -> cn $ balls !! p
where
balls = nextBit (mpBall (0,1)) $ zip sbits (map prec [10..])
nextBit ball ((sbit, p):rest) =
ball : nextBit newBall rest
where
newBall =
case sbit of
(-1) -> fromEndpointsAsIntervals l m
0 -> fromEndpointsAsIntervals l2 r2
1 -> fromEndpointsAsIntervals m r
_ -> error "in Arbitrary CReal"
(l_,r_) = endpointsAsIntervals ball
l = setPrecision p l_
r = setPrecision p r_
m = (l + r) * (dyadic 0.5)
l2 = (l + m) * (dyadic 0.5)
r2 = (r + m) * (dyadic 0.5)
nextBit _ _ = error "in Arbitrary CReal"
arbitrarySmall :: (Arbitrary a, HasOrderCertainly a Integer) => Integer -> Gen a
arbitrarySmall limit = aux
where
aux =
do
x <- arbitrary
if -limit !<=! x && x !<=! limit
then return x
else aux
{-|
A runtime representative of type @CReal@.
Used for specialising polymorphic tests to concrete types.
-}
tCReal :: T CReal
tCReal = T "CReal"
-- tCauchyRealAtAccuracy :: T CauchyRealAtAccuracy
-- tCauchyRealAtAccuracy = T "CReal(ac)"
specCRrespectsAccuracy1 ::
String ->
(CReal -> CReal) ->
(CReal -> Accuracy -> Bool) ->
Spec
specCRrespectsAccuracy1 opName op precond =
it (opName ++ " respects accuracy requests") $ do
property $
\ (x :: CReal) (ac :: Accuracy) ->
ac < (bits 1000) && precond x ac ==>
case CN.toEither ((op x) ? ac) of
Right v -> getAccuracy v >=$ ac
_ -> property True
(>=$) :: Accuracy -> Accuracy -> Property
(>=$) = printArgsIfFails2 ">=" (>=)
precondAnyReal :: CReal -> Accuracy -> Bool
precondAnyReal _x _ac = True
precondPositiveReal :: CReal -> Accuracy -> Bool
precondPositiveReal x ac = (x ? ac) !>! 0
precondNonZeroReal :: CReal -> Accuracy -> Bool
precondNonZeroReal x ac = (x ? ac) !/=! 0
precondSmallReal :: CReal -> Accuracy -> Bool
precondSmallReal x ac = abs (x ? ac) !<! 1000
precondPositiveSmallReal :: CReal -> Accuracy -> Bool
precondPositiveSmallReal x ac = 0 !<! b && b !<! 1000
where b = x ? ac
-- specCRrespectsAccuracy2 ::
-- String ->
-- (CReal -> CReal -> CReal) ->
-- (CReal -> Accuracy -> Bool) ->
-- (CReal -> Accuracy -> Bool) ->
-- Spec
-- specCRrespectsAccuracy2 opName op =
-- specCRrespectsAccuracy2CN opName (\ a b -> cn (op a b))
-- specCRrespectsAccuracy2CN ::
-- String ->
-- (CReal -> CReal -> CauchyRealCN) ->
-- (CReal -> Accuracy -> Bool) ->
-- (CReal -> Accuracy -> Bool) ->
-- Spec
-- specCRrespectsAccuracy2CN opName op precond1 precond2 =
-- it (opName ++ " respects accuracy requests") $ do
-- property $
-- \ (x :: CReal) (y :: CReal) (ac :: Accuracy) ->
-- let acSG = accuracySG ac in
-- ac < (bits 1000) && precond1 x acSG && precond2 y acSG ==>
-- case getMaybeValueCN ((op x y) ? acSG) of
-- Just v -> getAccuracy v >=$ ac
-- _ -> property True
-- specCRrespectsAccuracy2T ::
-- (Arbitrary t, Show t) =>
-- T t ->
-- String ->
-- (CReal -> t -> CReal) ->
-- (CReal -> Accuracy -> Bool) ->
-- (t -> Bool) ->
-- Spec
-- specCRrespectsAccuracy2T tt opName op =
-- specCRrespectsAccuracy2TCN tt opName (\ a b -> cn (op a b))
-- specCRrespectsAccuracy2TCN ::
-- (Arbitrary t, Show t) =>
-- T t ->
-- String ->
-- (CReal -> t -> CauchyRealCN) ->
-- (CReal -> Accuracy -> Bool) ->
-- (t -> Bool) ->
-- Spec
-- specCRrespectsAccuracy2TCN (T tName :: T t) opName op precond1 precond2 =
-- it (opName ++ " with " ++ tName ++ " respects accuracy requests") $ do
-- property $
-- \ (x :: CReal) (t :: t) (ac :: Accuracy) ->
-- let acSG = accuracySG ac in
-- ac < (bits 1000) && precond1 x acSG && precond2 t ==>
-- case getMaybeValueCN ((op x t) ? acSG) of
-- Just v -> getAccuracy v >=$ ac
-- _ -> property True
precondAnyT :: t -> Bool
precondAnyT _t = True
precondNonZeroT :: (HasEqCertainly t Integer) => t -> Bool
precondNonZeroT t = t !/=! 0
precondSmallT :: (HasOrderCertainly t Integer) => t -> Bool
precondSmallT t = -1000 !<=! t && t !<=! 1000
-- specCauchyReal :: Spec
-- specCauchyReal =
-- describe ("CReal") $ do
-- -- specConversion tInteger tCauchyReal real (fst . integerBounds)
-- describe "order" $ do
-- specHasEqNotMixed tCReal
-- -- specHasEq tInt tCReal tRational
-- -- specCanPickNonZero tCReal
-- specHasOrderNotMixed tCReal
-- -- specHasOrder tInt tCReal tRational
-- describe "min/max/abs" $ do
-- specCRrespectsAccuracy1 "abs" abs precondAnyReal
-- specCRrespectsAccuracy2 "max" max precondAnyReal precondAnyReal
-- specCRrespectsAccuracy2 "min" min precondAnyReal precondAnyReal
-- describe "ring" $ do
-- specCRrespectsAccuracy1 "negate" negate precondAnyReal
-- specCRrespectsAccuracy2 "+" add precondAnyReal precondAnyReal
-- specCRrespectsAccuracy2T tInteger "+" add precondAnyReal precondAnyT
-- specCRrespectsAccuracy2T tRational "+" add precondAnyReal precondAnyT
-- specCRrespectsAccuracy2T tDyadic "+" add precondAnyReal precondAnyT
-- specCRrespectsAccuracy2 "a-b" sub precondAnyReal precondAnyReal
-- specCRrespectsAccuracy2T tInteger "a-b" sub precondAnyReal precondAnyT
-- specCRrespectsAccuracy2T tRational "a-b" sub precondAnyReal precondAnyT
-- specCRrespectsAccuracy2T tDyadic "a-b" sub precondAnyReal precondAnyT
-- specCRrespectsAccuracy2 "*" mul precondAnyReal precondAnyReal
-- specCRrespectsAccuracy2T tInteger "*" mul precondAnyReal precondAnyT
-- specCRrespectsAccuracy2T tRational "*" mul precondAnyReal precondAnyT
-- specCRrespectsAccuracy2T tDyadic "*" mul precondAnyReal precondAnyT
-- describe "field" $ do
-- specCRrespectsAccuracy2CN "/" divide precondAnyReal precondNonZeroReal
-- specCRrespectsAccuracy2TCN tInteger "/" divide precondAnyReal precondNonZeroT
-- specCRrespectsAccuracy2TCN tRational "/" divide precondAnyReal precondNonZeroT
-- specCRrespectsAccuracy2TCN tDyadic "/" divide precondAnyReal precondNonZeroT
-- describe "elementary" $ do
-- specCRrespectsAccuracy1CN "sqrt" sqrt precondPositiveReal
-- specCRrespectsAccuracy1 "exp" exp precondSmallReal
-- specCRrespectsAccuracy1CN "log" log precondPositiveSmallReal
-- specCRrespectsAccuracy2CN "pow" pow precondPositiveSmallReal precondSmallReal
-- specCRrespectsAccuracy2TCN tInteger "pow" pow precondNonZeroReal precondSmallT
-- specCRrespectsAccuracy2TCN tRational "pow" pow precondPositiveSmallReal precondSmallT
-- specCRrespectsAccuracy2TCN tDyadic "pow" pow precondPositiveSmallReal precondSmallT
-- specCRrespectsAccuracy1 "cos" cos precondAnyReal
-- specCRrespectsAccuracy1 "sine" sin precondAnyReal