Documentation

Mathlib.Data.Nat.Basic

Basic operations on the natural numbers #

This file contains:

Many theorems that used to live in this file have been moved to Data.Nat.Order, so that this file requires fewer imports. For each section here there is a corresponding section in that file with additional results. It may be possible to move some of these results here, by tweaking their proofs.

instances #

Extra instances to short-circuit type class resolution and ensure computability

Equations
Equations
Equations
Equations
Equations
Equations
Equations
theorem Nat.nsmul_eq_mul (m : ) (n : ) :
m n = m * n
Equations

Recursion and forall/exists #

theorem Nat.and_forall_succ {p : Prop} :
p 0 ((n : ) → p (n + 1)) (n : ) → p n
theorem Nat.or_exists_succ {p : Prop} :
(p 0 n, p (n + 1)) n, p n

succ #

theorem LT.lt.nat_succ_le {n : } {m : } (h : n < m) :
theorem Nat.eq_of_lt_succ_of_not_lt {a : } {b : } (h1 : a < b + 1) (h2 : ¬a < b) :
a = b
theorem Nat.eq_of_le_of_lt_succ {n : } {m : } (h₁ : n m) (h₂ : m < n + 1) :
m = n
@[simp]
theorem Nat.succ_pos' {n : } :
theorem Nat.succ_ne_succ {n : } {m : } :
@[simp]
theorem Nat.max_succ_succ {m : } {n : } :
theorem Nat.lt_succ_iff {m : } {n : } :
m < Nat.succ n m n
theorem Nat.succ_le_iff {m : } {n : } :
Nat.succ m n m < n
theorem Nat.lt_iff_add_one_le {m : } {n : } :
m < n m + 1 n
theorem Nat.lt_add_one_iff {a : } {b : } :
a < b + 1 a b
theorem Nat.lt_one_add_iff {a : } {b : } :
a < 1 + b a b
theorem Nat.add_one_le_iff {a : } {b : } :
a + 1 b a < b
theorem Nat.one_add_le_iff {a : } {b : } :
1 + a b a < b
theorem Nat.of_le_succ {n : } {m : } (H : n Nat.succ m) :
n m n = Nat.succ m
theorem Nat.div_le_iff_le_mul_add_pred {m : } {n : } {k : } (n0 : 0 < n) :
m / n k m n * k + (n - 1)
theorem Nat.two_lt_of_ne {n : } :
n 0n 1n 22 < n
theorem Nat.forall_lt_succ {P : Prop} {n : } :
((m : ) → m < n + 1P m) ((m : ) → m < nP m) P n
theorem Nat.exists_lt_succ {P : Prop} {n : } :
(m, m < n + 1 P m) (m, m < n P m) P n

add #

@[simp]
theorem Nat.add_def {a : } {b : } :
Nat.add a b = a + b
@[simp]
theorem Nat.mul_def {a : } {b : } :
Nat.mul a b = a * b
theorem Nat.exists_eq_add_of_le {m : } {n : } (h : m n) :
k, n = m + k
theorem Nat.exists_eq_add_of_le' {m : } {n : } (h : m n) :
k, n = k + m
theorem Nat.exists_eq_add_of_lt {m : } {n : } (h : m < n) :
k, n = m + k + 1

pred #

@[simp]
theorem Nat.add_succ_sub_one (n : ) (m : ) :
n + Nat.succ m - 1 = n + m
@[simp]
theorem Nat.succ_add_sub_one (n : ) (m : ) :
Nat.succ n + m - 1 = n + m
theorem Nat.pred_eq_of_eq_succ {m : } {n : } (H : m = Nat.succ n) :
@[simp]
theorem Nat.pred_eq_succ_iff {n : } {m : } :
Nat.pred n = Nat.succ m n = m + 2
theorem Nat.pred_sub (n : ) (m : ) :
Nat.pred n - m = Nat.pred (n - m)
theorem Nat.le_of_pred_lt {m : } {n : } :
Nat.pred m < nm n
theorem Nat.self_add_sub_one (n : ) :
n + (n - 1) = 2 * n - 1
theorem Nat.sub_one_add_self (n : ) :
n - 1 + n = 2 * n - 1
theorem Nat.self_add_pred (n : ) :
n + Nat.pred n = Nat.pred (2 * n)
theorem Nat.pred_add_self (n : ) :
Nat.pred n + n = Nat.pred (2 * n)
@[simp]
theorem Nat.pred_one_add (n : ) :
Nat.pred (1 + n) = n

This ensures that simp succeeds on pred (n + 1) = n.

mul #

theorem Nat.two_mul_ne_two_mul_add_one {n : } {m : } :
2 * n 2 * m + 1
theorem Nat.mul_ne_mul_left {a : } {b : } {c : } (ha : 0 < a) :
b * a c * a b c
theorem Nat.mul_ne_mul_right {a : } {b : } {c : } (ha : 0 < a) :
a * b a * c b c
theorem Nat.mul_right_eq_self_iff {a : } {b : } (ha : 0 < a) :
a * b = a b = 1
theorem Nat.mul_left_eq_self_iff {a : } {b : } (hb : 0 < b) :
a * b = b a = 1
theorem Nat.lt_succ_iff_lt_or_eq {n : } {i : } :
n < Nat.succ i n < i n = i
theorem Nat.one_lt_mul_iff {m : } {n : } :
1 < m * n 0 < m 0 < n (1 < m 1 < n)

The product of two natural numbers is greater than 1 if and only if at least one of them is greater than 1 and both are positive.

Recursion and induction principles #

This section is here due to dependencies -- the lemmas here require some of the lemmas proved above, and some of the results in later sections depend on the definitions in this section.

@[simp]
theorem Nat.rec_zero {C : Sort u} (h0 : C 0) (h : (n : ) → C nC (n + 1)) :
Nat.rec h0 h 0 = h0
@[simp]
theorem Nat.rec_add_one {C : Sort u} (h0 : C 0) (h : (n : ) → C nC (n + 1)) (n : ) :
Nat.rec h0 h (n + 1) = h n (Nat.rec h0 h n)
def Nat.leRecOn {C : Sort u} {n : } {m : } :
n m({k : } → C kC (k + 1)) → C nC m

Recursion starting at a non-zero number: given a map C k → C (k+1) for each k, there is a map from C n to each C m, n ≤ m. For a version where the assumption is only made when k ≥ n, see leRecOn.

Equations
Instances For
    theorem Nat.leRecOn_self {C : Sort u} {n : } {h : n n} {next : {k : } → C kC (k + 1)} (x : C n) :
    Nat.leRecOn h (fun {k} => next k) x = x
    theorem Nat.leRecOn_succ {C : Sort u} {n : } {m : } (h1 : n m) {h2 : n m + 1} {next : {k : } → C kC (k + 1)} (x : C n) :
    Nat.leRecOn h2 next x = next m (Nat.leRecOn h1 next x)
    theorem Nat.leRecOn_succ' {C : Sort u} {n : } {h : n n + 1} {next : {k : } → C kC (k + 1)} (x : C n) :
    Nat.leRecOn h (fun {k} => next k) x = next n x
    theorem Nat.leRecOn_trans {C : Sort u} {n : } {m : } {k : } (hnm : n m) (hmk : m k) {next : {k : } → C kC (k + 1)} (x : C n) :
    Nat.leRecOn (_ : n k) next x = Nat.leRecOn hmk next (Nat.leRecOn hnm next x)
    theorem Nat.leRecOn_succ_left {C : Sort u} {n : } {m : } (h1 : n m) (h2 : n + 1 m) {next : {k : } → C kC (k + 1)} (x : C n) :
    Nat.leRecOn h2 (fun {k} => next k) (next n x) = Nat.leRecOn h1 (fun {k} => next k) x
    theorem Nat.leRecOn_injective {C : Sort u} {n : } {m : } (hnm : n m) (next : {k : } → C kC (k + 1)) (Hnext : ∀ (n : ), Function.Injective (next n)) :
    Function.Injective (Nat.leRecOn hnm fun {k} => next k)
    theorem Nat.leRecOn_surjective {C : Sort u} {n : } {m : } (hnm : n m) (next : {k : } → C kC (k + 1)) (Hnext : ∀ (n : ), Function.Surjective (next n)) :
    Function.Surjective (Nat.leRecOn hnm fun {k} => next k)
    def Nat.strongRec' {p : Sort u} (H : (n : ) → ((m : ) → m < np m) → p n) (n : ) :
    p n

    Recursion principle based on <.

    Equations
    Instances For
      def Nat.strongRecOn' {P : Sort u_1} (n : ) (h : (n : ) → ((m : ) → m < nP m) → P n) :
      P n

      Recursion principle based on < applied to some natural number.

      Equations
      Instances For
        theorem Nat.strongRecOn'_beta {P : Sort u_1} {h : (n : ) → ((m : ) → m < nP m) → P n} {n : } :
        Nat.strongRecOn' n h = h n fun m x => Nat.strongRecOn' m h
        theorem Nat.le_induction {m : } {P : (n : ) → m nProp} (base : P m (_ : m m)) (succ : (n : ) → (hn : m n) → P n hnP (n + 1) (_ : m n + 1)) (n : ) (hn : m n) :
        P n hn

        Induction principle starting at a non-zero number. For maps to a Sort* see le_rec_on. To use in an induction proof, the syntax is induction n, hn using Nat.le_induction (or the same for induction').

        def Nat.decreasingInduction {P : Sort u_1} (h : (n : ) → P (n + 1)P n) {m : } {n : } (mn : m n) (hP : P n) :
        P m

        Decreasing induction: if P (k+1) implies P k, then P n implies P m for all m ≤ n. Also works for functions to Sort*. For a version assuming only the assumption for k < n, see decreasing_induction'.

        Equations
        Instances For
          @[simp]
          theorem Nat.decreasingInduction_self {P : Sort u_1} (h : (n : ) → P (n + 1)P n) {n : } (nn : n n) (hP : P n) :
          theorem Nat.decreasingInduction_succ {P : Sort u_1} (h : (n : ) → P (n + 1)P n) {m : } {n : } (mn : m n) (msn : m n + 1) (hP : P (n + 1)) :
          @[simp]
          theorem Nat.decreasingInduction_succ' {P : Sort u_1} (h : (n : ) → P (n + 1)P n) {m : } (msm : m m + 1) (hP : P (m + 1)) :
          Nat.decreasingInduction h msm hP = h m hP
          theorem Nat.decreasingInduction_trans {P : Sort u_1} (h : (n : ) → P (n + 1)P n) {m : } {n : } {k : } (mn : m n) (nk : n k) (hP : P k) :
          theorem Nat.decreasingInduction_succ_left {P : Sort u_1} (h : (n : ) → P (n + 1)P n) {m : } {n : } (smn : m + 1 n) (mn : m n) (hP : P n) :
          def Nat.strongSubRecursion {P : Sort u_1} (H : (a b : ) → ((x y : ) → x < ay < bP x y) → P a b) (n : ) (m : ) :
          P n m

          Given P : ℕ → ℕ → Sort*, if for all a b : ℕ we can extend P from the rectangle strictly below (a,b) to P a b, then we have P n m for all n m : ℕ. Note that for non-Prop output it is preferable to use the equation compiler directly if possible, since this produces equation lemmas.

          Equations
          Instances For
            def Nat.pincerRecursion {P : Sort u_1} (Ha0 : (a : ) → P a 0) (H0b : (b : ) → P 0 b) (H : (x y : ) → P x (Nat.succ y)P (Nat.succ x) yP (Nat.succ x) (Nat.succ y)) (n : ) (m : ) :
            P n m

            Given P : ℕ → ℕ → Sort*, if we have P i 0 and P 0 i for all i : ℕ, and for any x y : ℕ we can extend P from (x,y+1) and (x+1,y) to (x+1,y+1) then we have P n m for all n m : ℕ. Note that for non-Prop output it is preferable to use the equation compiler directly if possible, since this produces equation lemmas.

            Equations
            Instances For
              def Nat.leRecOn' {C : Sort u_1} {n : } {m : } :
              n m(k : ⦄ → n kC kC (k + 1)) → C nC m

              Recursion starting at a non-zero number: given a map C k → C (k+1) for each k ≥ n, there is a map from C n to each C m, n ≤ m.

              Equations
              Instances For
                def Nat.decreasingInduction' {P : Sort u_1} {m : } {n : } (h : (k : ) → k < nm kP (k + 1)P k) (mn : m n) (hP : P n) :
                P m

                Decreasing induction: if P (k+1) implies P k for all m ≤ k < n, then P n implies P m. Also works for functions to Sort*. Weakens the assumptions of decreasing_induction.

                Equations
                • One or more equations did not get rendered due to their size.
                Instances For

                  div #

                  theorem Nat.div_lt_self' (n : ) (b : ) :
                  (n + 1) / (b + 2) < n + 1

                  A version of Nat.div_lt_self using successors, rather than additional hypotheses.

                  theorem Nat.le_div_iff_mul_le' {x : } {y : } {k : } (k0 : 0 < k) :
                  x y / k x * k y
                  theorem Nat.div_lt_iff_lt_mul' {x : } {y : } {k : } (k0 : 0 < k) :
                  x / k < y x < y * k
                  theorem Nat.one_le_div_iff {a : } {b : } (hb : 0 < b) :
                  1 a / b b a
                  theorem Nat.div_lt_one_iff {a : } {b : } (hb : 0 < b) :
                  a / b < 1 a < b
                  theorem Nat.div_le_div_right {n : } {m : } (h : n m) {k : } :
                  n / k m / k
                  theorem Nat.lt_of_div_lt_div {m : } {n : } {k : } :
                  m / k < n / km < n
                  theorem Nat.div_pos {a : } {b : } (hba : b a) (hb : 0 < b) :
                  0 < a / b
                  theorem Nat.lt_mul_of_div_lt {a : } {b : } {c : } (h : a / c < b) (w : 0 < c) :
                  a < b * c
                  theorem Nat.mul_div_le_mul_div_assoc (a : ) (b : ) (c : ) :
                  a * (b / c) a * b / c
                  theorem Nat.eq_mul_of_div_eq_right {a : } {b : } {c : } (H1 : b a) (H2 : a / b = c) :
                  a = b * c
                  theorem Nat.div_eq_iff_eq_mul_right {a : } {b : } {c : } (H : 0 < b) (H' : b a) :
                  a / b = c a = b * c
                  theorem Nat.div_eq_iff_eq_mul_left {a : } {b : } {c : } (H : 0 < b) (H' : b a) :
                  a / b = c a = c * b
                  theorem Nat.eq_mul_of_div_eq_left {a : } {b : } {c : } (H1 : b a) (H2 : a / b = c) :
                  a = c * b
                  theorem Nat.mul_div_cancel_left' {a : } {b : } (Hd : a b) :
                  a * (b / a) = b
                  theorem Nat.lt_div_mul_add {a : } {b : } (hb : 0 < b) :
                  a < a / b * b + b
                  @[simp]
                  theorem Nat.div_left_inj {a : } {b : } {d : } (hda : d a) (hdb : d b) :
                  a / d = b / d a = b

                  mod, dvd #

                  theorem Nat.mod_eq_iff_lt {a : } {b : } (h : b 0) :
                  a % b = a a < b
                  @[simp]
                  theorem Nat.mod_succ_eq_iff_lt {a : } {b : } :
                  a % Nat.succ b = a a < Nat.succ b
                  theorem Nat.mod_add_div' (m : ) (k : ) :
                  m % k + m / k * k = m
                  theorem Nat.div_add_mod' (m : ) (k : ) :
                  m / k * k + m % k = m
                  theorem Nat.div_mod_unique {n : } {k : } {m : } {d : } (h : 0 < k) :
                  n / k = d n % k = m m + k * d = n m < k

                  See also Nat.divModEquiv for a similar statement as an Equiv.

                  theorem Nat.dvd_add_left {k : } {m : } {n : } (h : k n) :
                  k m + n k m
                  theorem Nat.dvd_add_right {k : } {m : } {n : } (h : k m) :
                  k m + n k n
                  theorem Nat.mul_dvd_mul_iff_left {a : } {b : } {c : } (ha : 0 < a) :
                  a * b a * c b c
                  theorem Nat.mul_dvd_mul_iff_right {a : } {b : } {c : } (hc : 0 < c) :
                  a * c b * c a b
                  @[simp]
                  theorem Nat.mod_mod_of_dvd (n : ) {m : } {k : } (h : m k) :
                  n % k % m = n % m
                  theorem Nat.add_mod_eq_add_mod_right {m : } {n : } {k : } (i : ) (H : m % n = k % n) :
                  (m + i) % n = (k + i) % n
                  theorem Nat.add_mod_eq_add_mod_left {m : } {n : } {k : } (i : ) (H : m % n = k % n) :
                  (i + m) % n = (i + k) % n
                  theorem Nat.mul_dvd_of_dvd_div {a : } {b : } {c : } (hab : c b) (h : a b / c) :
                  c * a b
                  theorem Nat.eq_of_dvd_of_div_eq_one {a : } {b : } (w : a b) (h : b / a = 1) :
                  a = b
                  theorem Nat.eq_zero_of_dvd_of_div_eq_zero {a : } {b : } (w : a b) (h : b / a = 0) :
                  b = 0
                  theorem Nat.div_le_div_left {a : } {b : } {c : } (h₁ : c b) (h₂ : 0 < c) :
                  a / b a / c
                  theorem Nat.lt_iff_le_pred {m : } {n : } :
                  0 < n → (m < n m n - 1)
                  theorem Nat.lt_mul_div_succ (m : ) {n : } (n0 : 0 < n) :
                  m < n * (m / n + 1)
                  theorem Nat.mul_add_mod (a : ) (b : ) (c : ) :
                  (a * b + c) % b = c % b
                  theorem Nat.mul_add_mod_of_lt {a : } {b : } {c : } (h : c < b) :
                  (a * b + c) % b = c
                  theorem Nat.pred_eq_self_iff {n : } :
                  Nat.pred n = n n = 0

                  find #

                  theorem Nat.find_eq_iff {m : } {p : Prop} [DecidablePred p] (h : n, p n) :
                  Nat.find h = m p m ∀ (n : ), n < m¬p n
                  @[simp]
                  theorem Nat.find_lt_iff {p : Prop} [DecidablePred p] (h : n, p n) (n : ) :
                  Nat.find h < n m, m < n p m
                  @[simp]
                  theorem Nat.find_le_iff {p : Prop} [DecidablePred p] (h : n, p n) (n : ) :
                  Nat.find h n m, m n p m
                  @[simp]
                  theorem Nat.le_find_iff {p : Prop} [DecidablePred p] (h : n, p n) (n : ) :
                  n Nat.find h ∀ (m : ), m < n¬p m
                  @[simp]
                  theorem Nat.lt_find_iff {p : Prop} [DecidablePred p] (h : n, p n) (n : ) :
                  n < Nat.find h ∀ (m : ), m n¬p m
                  @[simp]
                  theorem Nat.find_eq_zero {p : Prop} [DecidablePred p] (h : n, p n) :
                  Nat.find h = 0 p 0
                  theorem Nat.find_mono {p : Prop} {q : Prop} [DecidablePred p] [DecidablePred q] (h : (n : ) → q np n) {hp : n, p n} {hq : n, q n} :
                  theorem Nat.find_le {n : } {p : Prop} [DecidablePred p] {h : n, p n} (hn : p n) :
                  theorem Nat.find_comp_succ {p : Prop} [DecidablePred p] (h₁ : n, p n) (h₂ : n, p (n + 1)) (h0 : ¬p 0) :
                  Nat.find h₁ = Nat.find h₂ + 1

                  find_greatest #

                  def Nat.findGreatest (P : Prop) [DecidablePred P] :

                  find_greatest P b is the largest i ≤ bound such that P i holds, or 0 if no such i exists

                  Equations
                  Instances For
                    theorem Nat.findGreatest_succ {P : Prop} [DecidablePred P] (n : ) :
                    Nat.findGreatest P (n + 1) = if P (n + 1) then n + 1 else Nat.findGreatest P n
                    @[simp]
                    theorem Nat.findGreatest_eq {P : Prop} [DecidablePred P] {b : } :
                    P bNat.findGreatest P b = b
                    @[simp]
                    theorem Nat.findGreatest_of_not {P : Prop} [DecidablePred P] {b : } (h : ¬P (b + 1)) :

                    decidability of predicates #

                    instance Nat.decidableBallLT (n : ) (P : (k : ) → k < nProp) [(n : ) → (h : n < n) → Decidable (P n h)] :
                    Decidable ((n : ) → (h : n < n) → P n h)
                    Equations
                    • One or more equations did not get rendered due to their size.
                    instance Nat.decidableForallFin {n : } (P : Fin nProp) [DecidablePred P] :
                    Decidable ((i : Fin n) → P i)
                    Equations
                    instance Nat.decidableBallLe (n : ) (P : (k : ) → k nProp) [(n : ) → (h : n n) → Decidable (P n h)] :
                    Decidable ((n : ) → (h : n n) → P n h)
                    Equations
                    instance Nat.decidableExistsLT {P : Prop} [h : DecidablePred P] :
                    DecidablePred fun n => m, m < n P m
                    Equations
                    instance Nat.decidableExistsLe {P : Prop} [DecidablePred P] :
                    DecidablePred fun n => m, m n P m
                    Equations