1 | module Data.Fin.Arith
3 | import public Data.Fin
5 | import Syntax.PreorderReasoning
13 | (+) : {m, n : Nat} -> Fin m -> Fin (S n) -> Fin (m + n)
14 | (+) FZ y = coerce (cong S $
plusCommutative n (pred m)) (weakenN (pred m) y)
15 | (+) (FS x) y = FS (x + y)
21 | (*) : {m, n : Nat} -> Fin (S m) -> Fin (S n) -> Fin (S (m * n))
23 | (*) {m = S _} (FS x) y = y + x * y
30 | finToNatPlusHomo : {m, n : Nat} -> (x : Fin m) -> (y : Fin (S n)) ->
31 | finToNat (x + y) = finToNat x + finToNat y
32 | finToNatPlusHomo FZ _
33 | = finToNatQuotient $
transitive
35 | (weakenNNeutral _ _)
36 | finToNatPlusHomo (FS x) y = cong S (finToNatPlusHomo x y)
39 | finToNatMultHomo : {m, n : Nat} -> (x : Fin (S m)) -> (y : Fin (S n)) ->
40 | finToNat (x * y) = finToNat x * finToNat y
41 | finToNatMultHomo FZ _ = Refl
42 | finToNatMultHomo {m = S _} (FS x) y = Calc $
43 | |~ finToNat (FS x * y)
44 | ~~ finToNat (y + x * y) ...( Refl )
45 | ~~ finToNat y + finToNat (x * y) ...( finToNatPlusHomo y (x * y) )
46 | ~~ finToNat y + finToNat x * finToNat y ...( cong (finToNat y +) (finToNatMultHomo x y) )
47 | ~~ finToNat (FS x) * finToNat y ...( Refl )
52 | plusPreservesLast : (m, n : Nat) -> Fin.last {n=m} + Fin.last {n} = Fin.last
53 | plusPreservesLast Z n
54 | = homoPointwiseIsEqual $
transitive
56 | (weakenNNeutral _ _)
57 | plusPreservesLast (S m) n = cong FS (plusPreservesLast m n)
60 | multPreservesLast : (m, n : Nat) -> Fin.last {n=m} * Fin.last {n} = Fin.last
61 | multPreservesLast Z n = Refl
62 | multPreservesLast (S m) n = Calc $
63 | |~ last + (last * last)
64 | ~~ last + last ...( cong (last +) (multPreservesLast m n) )
65 | ~~ last ...( plusPreservesLast n (m * n) )
70 | plusSuccRightSucc : {m, n : Nat} -> (left : Fin m) -> (right : Fin (S n)) ->
71 | FS (left + right) ~~~ left + FS right
72 | plusSuccRightSucc FZ right = FS $
congCoerce reflexive
73 | plusSuccRightSucc (FS left) right = FS $
plusSuccRightSucc left right
78 | shiftAsPlus : {m, n : Nat} -> (k : Fin (S m)) ->
79 | shift n k ~~~ last {n} + k
80 | shiftAsPlus {n=Z} k =
81 | symmetric $
transitive (coerceEq _) (weakenNNeutral _ _)
82 | shiftAsPlus {n=S n} k = FS (shiftAsPlus k)
85 | weakenNAsPlusFZ : {m, n : Nat} -> (k : Fin n) ->
86 | weakenN m k = k + the (Fin (S m)) FZ
87 | weakenNAsPlusFZ FZ = Refl
88 | weakenNAsPlusFZ (FS k) = cong FS (weakenNAsPlusFZ k)
91 | weakenNPlusHomo : {0 m, n : Nat} -> (k : Fin p) ->
92 | weakenN n (weakenN m k) ~~~ weakenN (m + n) k
93 | weakenNPlusHomo FZ = FZ
94 | weakenNPlusHomo (FS k) = FS (weakenNPlusHomo k)
98 | {m, n : Nat} -> (k : Fin m) -> (l : Fin (S n)) ->
99 | weakenN w (k + l) ~~~ weakenN w k + l
101 | = transitive (congWeakenN (coerceEq _))
102 | $
transitive (weakenNPlusHomo l)
103 | $
symmetric (coerceEq _)
104 | weakenNOfPlus (FS k) l = FS (weakenNOfPlus k l)
108 | plusZeroLeftNeutral : (k : Fin (S n)) -> FZ + k ~~~ k
109 | plusZeroLeftNeutral k = transitive (coerceEq _) (weakenNNeutral _ k)
112 | congPlusLeft : {m, n, p : Nat} -> {k : Fin m} -> {l : Fin n} ->
113 | (c : Fin (S p)) -> k ~~~ l -> k + c ~~~ l + c
115 | = transitive (plusZeroLeftNeutral c)
116 | (symmetric $
plusZeroLeftNeutral c)
117 | congPlusLeft c (FS prf) = FS (congPlusLeft c prf)
120 | plusZeroRightNeutral : (k : Fin m) -> k + FZ ~~~ k
121 | plusZeroRightNeutral FZ = FZ
122 | plusZeroRightNeutral (FS k) = FS (plusZeroRightNeutral k)
125 | congPlusRight : {m, n, p : Nat} -> {k : Fin (S n)} -> {l : Fin (S p)} ->
126 | (c : Fin m) -> k ~~~ l -> c + k ~~~ c + l
128 | = transitive (plusZeroRightNeutral c)
129 | (symmetric $
plusZeroRightNeutral c)
130 | congPlusRight {n = S _} {p = S _} c (FS prf)
131 | = transitive (symmetric $
plusSuccRightSucc c _)
132 | $
transitive (FS $
congPlusRight c prf)
133 | (plusSuccRightSucc c _)
134 | congPlusRight {p = Z} c (FS prf) impossible
137 | plusCommutative : {m, n : Nat} -> (left : Fin (S m)) -> (right : Fin (S n)) ->
138 | left + right ~~~ right + left
139 | plusCommutative FZ right
140 | = transitive (plusZeroLeftNeutral right)
141 | (symmetric $
plusZeroRightNeutral right)
142 | plusCommutative {m = S _} (FS left) right
143 | = transitive (FS (plusCommutative left right))
144 | (plusSuccRightSucc right left)
149 | (left : Fin m) -> (centre : Fin (S n)) -> (right : Fin (S p)) ->
150 | left + (centre + right) ~~~ (left + centre) + right
151 | plusAssociative FZ centre right
152 | = transitive (plusZeroLeftNeutral (centre + right))
153 | (congPlusLeft right (symmetric $
plusZeroLeftNeutral centre))
154 | plusAssociative (FS left) centre right = FS (plusAssociative left centre right)