0 | module Data.Prim.Integer
2 | import public Control.WellFounded
3 | import public Data.Prim.Ord
4 | import public Algebra.Solver.Ring
5 | import Syntax.PreorderReasoning
10 | unsafeRefl = believe_me (Refl {x = a})
18 | data (<) : (m,n : Integer) -> Type where
19 | LT : {0 m,n : Integer} -> (0 prf : (m < n) === True) -> m < n
25 | 0 mkLT : (0 prf : (m < n) === True) -> m < n
32 | 0 runLT : m < n -> (m < n) === True
33 | runLT (LT prf) = prf
38 | strictLT : (0 p : m < n) -> Lazy c -> c
39 | strictLT (LT prf) x = x
47 | 0 (>) : (m,n : Integer) -> Type
52 | 0 (<=) : (m,n : Integer) -> Type
53 | m <= n = Either (m < n) (m === n)
57 | 0 (>=) : (m,n : Integer) -> Type
62 | 0 (/=) : (m,n : Integer) -> Type
63 | m /= n = Either (m < n) (m > n)
69 | 0 ltNotEQ : m < n -> Not (m === n)
70 | ltNotEQ x = strictLT x $
assert_total (idris_crash "IMPOSSIBLE: LT and EQ")
72 | 0 ltNotGT : m < n -> Not (n < m)
73 | ltNotGT x = strictLT x $
assert_total (idris_crash "IMPOSSIBLE: LT and GT")
75 | 0 eqNotLT : m === n -> Not (m < n)
76 | eqNotLT = flip ltNotEQ
79 | comp : (m,n : Integer) -> Trichotomy (<) m n
80 | comp m n = case prim__lt_Integer m n of
81 | 0 => case prim__eq_Integer m n of
82 | 0 => GT (ltNotGT $
LT unsafeRefl) (ltNotEQ $
LT unsafeRefl) (LT unsafeRefl)
83 | x => EQ (eqNotLT unsafeRefl) (unsafeRefl) (eqNotLT unsafeRefl)
84 | x => LT (LT unsafeRefl) (ltNotEQ $
LT unsafeRefl) (ltNotGT $
LT unsafeRefl)
87 | Total Integer (<) where
89 | transLT p q = strictLT p $
strictLT q $
LT unsafeRefl
95 | replace' : (0 p : a -> Type) -> (0 _ : x = y) -> p x -> p y
96 | replace' p prf px = replace {p} prf px
98 | derive : {0 a,b : Type}
100 | -> FastDerivation a b
102 | derive x z = case Calc z of Refl => x
112 | 0 plusGT : (k,m,n : Integer) -> k < m -> n + k < n + m
113 | plusGT k m n x = strictLT x $
mkLT unsafeRefl
120 | 0 multPosPosGT0 : (m,n : Integer) -> 0 < m -> 0 < n -> 0 < m * n
121 | multPosPosGT0 _ _ p1 p2 = strictLT p1 $
strictLT p2 $
mkLT unsafeRefl
125 | 0 oneAfterZero : (n : Integer) -> 0 < n -> 1 <= n
126 | oneAfterZero n gt0 = case comp 1 n of
128 | EQ _ x _ => Right x
133 | $
idris_crash "IMPOSSIBLE: Integer between 0 and 1"
138 | 0 modLT : (n,d : Integer) -> 0 < d -> (0 <= mod n d, mod n d < d)
139 | modLT n d x with (mod n d)
140 | _ | 0 = (Right Refl, x)
141 | _ | _ = strictLT x (Left $
mkLT unsafeRefl, mkLT unsafeRefl)
144 | 0 modNegEQ : (n,d : Integer) -> d < 0 -> mod n d === mod n (neg d)
145 | modNegEQ n d x = strictLT x unsafeRefl
148 | 0 lawDivMod : (n,d : Integer) -> d /= 0 -> d * div n d + mod n d === n
149 | lawDivMod n d (Left x) = strictLT x unsafeRefl
150 | lawDivMod n d (Right x) = strictLT x unsafeRefl
157 | sdiv : (n,d : Integer) -> (0 prf : d /= 0) => Integer
158 | sdiv n d = n `div` d
162 | smod : (n,d : Integer) -> (0 prf : d /= 0) => Integer
163 | smod n d = n `mod` d
170 | 0 BoundedLT : (lowerBound : Integer) -> Integer -> Integer -> Type
171 | BoundedLT lowerBound x y = (lowerBound <= x, x < y)
174 | 0 BoundedGT : (upperBound : Integer) -> Integer -> Integer -> Type
175 | BoundedGT upperBound x y = (upperBound >= x, x > y)
180 | accessLT : (m : Integer) -> Accessible (BoundedLT lb) m
181 | accessLT m = Access $
\n,lt => accessLT (assert_smaller m n)
186 | accessGT : (m : Integer) -> Accessible (BoundedGT ub) m
187 | accessGT m = Access $
\n,gt => accessGT (assert_smaller m n)