@@ -10,9 +10,12 @@ import Prelude.Classes
1010%access public
1111%default total
1212
13−%elim data Nat
14− = Z
15− | S Nat
13+||| Unary natural numbers
14+%elim data Nat =
15+ ||| Zero
16+ Z |
17+ ||| Successor
18+ S Nat
1619
1720-- name hints for interactive editing
1821%name Nat k,j,i,n,m
@@ -33,14 +36,19 @@ isSucc (S n) = True
3336-- Basic arithmetic functions
3437--------------------------------------------------------------------------------
3538
36−total plus : Nat -> Nat -> Nat
39+||| Add two natural numbers.
40+||| @ n the number to case-split on
41+||| @ m the other number
42+total plus : (n, m : Nat) -> Nat
3743plus Z right = right
3844plus (S left) right = S (plus left right)
3945
46+||| Multiply natural numbers
4047total mult : Nat -> Nat -> Nat
4148mult Z right = Z
4249mult (S left) right = plus right $ mult left right
4350
51+||| Convert an Integer to a Nat, mapping negative numbers to 0
4452fromIntegerNat : Integer -> Nat
4553fromIntegerNat 0 = Z
4654fromIntegerNat n =
@@ -49,15 +57,18 @@ fromIntegerNat n =
4957 else
5058 Z
5159
60+||| Convert a Nat to an Integer
5261toIntegerNat : Nat -> Integer
5362toIntegerNat Z = 0
5463toIntegerNat (S k) = 1 + toIntegerNat k
5564
65+||| Subtract natural numbers. If the second number is larger than the first, return 0.
5666total minus : Nat -> Nat -> Nat
5767minus Z right = Z
5868minus left Z = left
5969minus (S left) (S right) = minus left right
6070
71+||| Exponentiation of natural numbers
6172total power : Nat -> Nat -> Nat
6273power base Z = S Z
6374power base (S exp) = mult base $ power base exp
@@ -74,33 +85,46 @@ hyper (S pn) a (S pb) = hyper pn a (hyper (S pn) a pb)
7485-- Comparisons
7586--------------------------------------------------------------------------------
7687
77−data LTE : Nat -> Nat -> Type where
88+||| Proofs that `n` is less than or equal to `m`
89+||| @ n the smaller number
90+||| @ m the larger number
91+data LTE : (n, m : Nat) -> Type where
92+ ||| Zero is the smallest Nat
7893 lteZero : LTE Z right
94+ ||| If n <= m, then n + 1 <= m + 1
7995 lteSucc : LTE left right -> LTE (S left) (S right)
8096
97+||| Greater than or equal to
8198total GTE : Nat -> Nat -> Type
8299GTE left right = LTE right left
83100
101+||| Strict less than
84102total LT : Nat -> Nat -> Type
85103LT left right = LTE (S left) right
86104
105+||| Strict greater than
87106total GT : Nat -> Nat -> Type
88107GT left right = LT right left
89108
109+||| Boolean test than one Nat is less than or equal to another
90110total lte : Nat -> Nat -> Bool
91111lte Z right = True
92112lte left Z = False
93113lte (S left) (S right) = lte left right
94114
115+||| Boolean test than one Nat is greater than or equal to another
95116total gte : Nat -> Nat -> Bool
96117gte left right = lte right left
97118
119+||| Boolean test than one Nat is strictly less than another
98120total lt : Nat -> Nat -> Bool
99121lt left right = lte (S left) right
100122
123+||| Boolean test than one Nat is strictly greater than another
101124total gt : Nat -> Nat -> Bool
102125gt left right = lt right left
103126
127+||| Find the least of two natural numbers
104128total minimum : Nat -> Nat -> Nat
105129minimum left right =
106130 if lte left right then
@@ -108,6 +132,7 @@ minimum left right =
108132 else
109133 right
110134
135+||| Find the greatest of two natural numbers
111136total maximum : Nat -> Nat -> Nat
112137maximum left right =
113138 if lte left right then
@@ -148,9 +173,11 @@ instance MinBound Nat where
148173instance Cast Integer Nat where
149174 cast = fromInteger
150175
176+||| A wrapper for Nat that specifies the semigroup and monad instances that use (+)
151177record Multiplicative : Type where
152178 getMultiplicative : Nat -> Multiplicative
153179
180+||| A wrapper for Nat that specifies the semigroup and monad instances that use (*)
154181record Additive : Type where
155182 getAdditive : Nat -> Additive
156183
@@ -210,6 +237,7 @@ instance Cast Nat Int where
210237-- Auxilliary notions
211238--------------------------------------------------------------------------------
212239
240+||| The predecessor of a natural number. `pred Z` is `Z`.
213241total pred : Nat -> Nat
214242pred Z = Z
215243pred (S n) = n
@@ -218,11 +246,13 @@ pred (S n) = n
218246-- Fibonacci and factorial
219247--------------------------------------------------------------------------------
220248
249+||| Fibonacci numbers
221250total fib : Nat -> Nat
222251fib Z = Z
223252fib (S Z) = S Z
224253fib (S (S n)) = fib (S n) + fib n
225254
255+||| Factorial function
226256total fact : Nat -> Nat
227257fact Z = S Z
228258fact (S n) = (S n) * fact n
@@ -283,10 +313,13 @@ lcm x y = divNat (x * y) (gcd x y)
283313--------------------------------------------------------------------------------
284314
285315-- Succ
316+
317+||| S preserves equality
286318total eqSucc : (left : Nat) -> (right : Nat) -> (p : left = right) ->
287319 S left = S right
288320eqSucc left _ refl = refl
289321
322+||| S is injective
290323total succInjective : (left : Nat) -> (right : Nat) -> (p : S left = S right) ->
291324 left = right
292325succInjective left _ refl = refl