{-# OPTIONS --warning=error --safe --without-K #-} open import LogicalFormulae open import Numbers.Naturals.Definition open import Numbers.Naturals.Semiring open import Numbers.Naturals.Naturals open import Numbers.Naturals.Order open import Numbers.Naturals.Order.Lemmas open import Numbers.Naturals.Order.WellFounded open import KeyValue.KeyValue open import Orders.Total.Definition open import Orders.Partial.Definition open import Vectors open import Maybe open import Semirings.Definition open import Numbers.Naturals.EuclideanAlgorithm module Numbers.Primes.PrimeNumbers where open TotalOrder ℕTotalOrder open Semiring ℕSemiring open import Decidable.Lemmas ℕDecideEquality dividesEqualityLemma'' : {a b : ℕ} → (quot1 quot2 : ℕ) → .(quot1 ≡ quot2) → (rem : ℕ) → .(pr1 : (quot1 +N a *N quot1) +N rem ≡ b) → .(pr2 : (quot2 +N a *N quot2) +N rem ≡ b) → (y : rem 1 : 1 1 : 1 1 = n>1 ; divisor = divisor ; dividesN = dividesN ; divisorLessN = divisorLessN ; divisorNot1 = divisorNot1 } record { p>1 = p>1 ; pr = pr } = lessImpliesNotEqual divisorNot1 (equalityCommutative div=1) where div=1 : divisor ≡ 1 div=1 = pr {divisor} dividesN divisorLessN (TotalOrder.1 = p>1 ; pr = pr } = zeroNeverGreater p>1 oneIsNotPrime : Prime 1 → False oneIsNotPrime record { p>1 = (le x proof) ; pr = pr } = naughtE (equalityCommutative absurd') where absurd : x +N 1 ≡ 0 absurd = succInjective proof absurd' : succ x ≡ 0 absurd' rewrite Semiring.commutative ℕSemiring 1 x = absurd twoIsPrime : Prime 2 Prime.p>1 twoIsPrime = succPreservesInequality (succIsPositive 0) Prime.pr twoIsPrime {i} i|2 i<2 01 threeIsPrime = le 1 refl Prime.pr threeIsPrime {succ zero} i|3 i<3 _ = refl Prime.pr threeIsPrime {succ (succ zero)} (divides record { quot = (succ (succ (succ zero))) ; rem = zero ; pr = () ; remIsSmall = remIsSmall ; quotSmall = quotSmall } x) i<3 _ Prime.pr threeIsPrime {succ (succ zero)} (divides record { quot = (succ (succ (succ (succ quot)))) ; rem = zero ; pr = () ; remIsSmall = remIsSmall ; quotSmall = quotSmall } x) i<3 _ Prime.pr threeIsPrime {succ (succ (succ i))} i|3 (le (succ (succ zero)) ()) _ Prime.pr threeIsPrime {succ (succ (succ i))} i|3 (le (succ (succ (succ x))) ()) _ compositeImpliesNotPrime : (m p : ℕ) → (succ zero 1 = (le x ()) ; pr = pr } primesAreBiggerThanOne {succ zero} pr = exFalso (oneIsNotPrime pr) primesAreBiggerThanOne {succ (succ p)} pr = succPreservesInequality (succIsPositive p) primesAreBiggerThanZero : {p : ℕ} → Prime p → 0 1 = 11 = pr ; divisor = succ (succ firstPoss) ; dividesN = _&&_.fst x1 ; divisorLessN = _&&_.snd x1 ; divisorNot1 = succPreservesInequality (succIsPositive firstPoss) ; divisorPrime = record { p>1 = succPreservesInequality (succIsPositive firstPoss) ; pr = compositeOrPrimeLemma {succ (succ firstPoss)} {a} x (_&&_.fst x1) } }) go' (succ (succ (succ firstPoss))) | inl (inl x) | inr y rewrite y = inr x go' (succ (succ (succ firstPoss))) | inl (inr x) = inl (inr x) go' (succ (succ (succ firstPoss))) | inr x = inr x go {zero} pr = inl (inl (record { previousDoNotDivide = λ x 11 = p>1 ; pr = pr } p1|p2 | inl (inl p1p2) = exFalso (zeroIsNotPrime pr2) primeDivPrimeImpliesEqual {p1} {succ p2} pr1 pr2 p1|p2 | inl (inr p1>p2) = exFalso (divisorIsSmaller p1|p2 p1>p2) primeDivPrimeImpliesEqual {p1} {p2} pr1 pr2 p1|p2 | inr p1=p2 = p1=p2 mult1Lemma : {a b : ℕ} → a *N succ b ≡ 1 → (a ≡ 1) && (b ≡ 0) mult1Lemma {a} {b} pr = record { fst = _&&_.fst p ; snd = q} where p : (a ≡ 1) && (succ b ≡ 1) p = productOneImpliesOperandsOne pr q : b ≡ zero q = succInjective (_&&_.snd p) oneHasNoDivisors : {a : ℕ} → a ∣ 1 → a ≡ 1 oneHasNoDivisors {a} (divides record { quot = zero ; rem = .0 ; pr = pr ; remIsSmall = remIsSmall } refl) rewrite Semiring.sumZeroRight ℕSemiring (a *N zero) | multiplicationNIsCommutative a zero | Semiring.sumZeroRight ℕSemiring a = exFalso (naughtE pr) oneHasNoDivisors {a} (divides record { quot = (succ quot) ; rem = .0 ; pr = pr ; remIsSmall = remIsSmall } refl) rewrite Semiring.sumZeroRight ℕSemiring (a *N succ quot) = _&&_.fst (mult1Lemma pr) notSmallerMeansGE : {a b : ℕ} → (a