data.nat.factorial.basic
⟷
Mathlib.Data.Nat.Factorial.Basic
The following section lists changes to this file in mathlib3 and mathlib4 that occured after the initial port. Most recent changes are shown first. Hovering over a commit will show all commits associated with the same mathlib3 commit.
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(no changes)
(last sync)
mathlib commit https://github.com/leanprover-community/mathlib/commit/65a1391a0106c9204fe45bc73a039f056558cb83
@@ -3,7 +3,7 @@ Copyright (c) 2018 Mario Carneiro. All rights reserved.
Released under Apache 2.0 license as described in the file LICENSE.
Authors: Mario Carneiro, Chris Hughes, Floris van Doorn, Yaël Dillies
-/
-import Data.Nat.Defs
+import Algebra.Group.Nat
import Data.Nat.Pow
#align_import data.nat.factorial.basic from "leanprover-community/mathlib"@"c3291da49cfa65f0d43b094750541c0731edc932"
mathlib commit https://github.com/leanprover-community/mathlib/commit/65a1391a0106c9204fe45bc73a039f056558cb83
@@ -3,7 +3,7 @@ Copyright (c) 2018 Mario Carneiro. All rights reserved.
Released under Apache 2.0 license as described in the file LICENSE.
Authors: Mario Carneiro, Chris Hughes, Floris van Doorn, Yaël Dillies
-/
-import Data.Nat.Basic
+import Data.Nat.Defs
import Data.Nat.Pow
#align_import data.nat.factorial.basic from "leanprover-community/mathlib"@"c3291da49cfa65f0d43b094750541c0731edc932"
@@ -117,7 +117,7 @@ theorem factorial_le {m n} (h : m ≤ n) : m ! ≤ n ! :=
theorem factorial_mul_pow_le_factorial : ∀ {m n : ℕ}, m ! * m.succ ^ n ≤ (m + n)!
| m, 0 => by simp
| m, n + 1 => by
- rw [← add_assoc, Nat.factorial_succ, mul_comm (Nat.succ _), pow_succ', ← mul_assoc] <;>
+ rw [← add_assoc, Nat.factorial_succ, mul_comm (Nat.succ _), pow_succ, ← mul_assoc] <;>
exact
mul_le_mul factorial_mul_pow_le_factorial (Nat.succ_le_succ (Nat.le_add_right _ _))
(Nat.zero_le _) (Nat.zero_le _)
@@ -333,7 +333,7 @@ theorem ascFactorial_of_sub {n k : ℕ} (h : k < n) :
theorem pow_succ_le_ascFactorial (n : ℕ) : ∀ k : ℕ, (n + 1) ^ k ≤ n.ascFactorial k
| 0 => by rw [asc_factorial_zero, pow_zero]
| k + 1 => by
- rw [pow_succ]
+ rw [pow_succ']
exact Nat.mul_le_mul (Nat.add_le_add_right le_self_add _) (pow_succ_le_asc_factorial k)
#align nat.pow_succ_le_asc_factorial Nat.pow_succ_le_ascFactorial
-/
@@ -341,7 +341,7 @@ theorem pow_succ_le_ascFactorial (n : ℕ) : ∀ k : ℕ, (n + 1) ^ k ≤ n.ascF
#print Nat.pow_lt_ascFactorial' /-
theorem pow_lt_ascFactorial' (n k : ℕ) : (n + 1) ^ (k + 2) < n.ascFactorial (k + 2) :=
by
- rw [pow_succ]
+ rw [pow_succ']
exact
Nat.mul_lt_mul (Nat.add_lt_add_right (Nat.lt_add_of_pos_right succ_pos') 1)
(pow_succ_le_asc_factorial n _) (pow_pos succ_pos' _)
@@ -360,7 +360,7 @@ theorem pow_lt_ascFactorial (n : ℕ) : ∀ {k : ℕ}, 2 ≤ k → (n + 1) ^ k <
theorem ascFactorial_le_pow_add (n : ℕ) : ∀ k : ℕ, n.ascFactorial k ≤ (n + k) ^ k
| 0 => by rw [asc_factorial_zero, pow_zero]
| k + 1 => by
- rw [asc_factorial_succ, pow_succ]
+ rw [asc_factorial_succ, pow_succ']
exact
Nat.mul_le_mul_of_nonneg_left
((asc_factorial_le_pow_add k).trans (Nat.pow_le_pow_left (le_succ _) _))
@@ -372,7 +372,7 @@ theorem ascFactorial_lt_pow_add (n : ℕ) : ∀ {k : ℕ}, 2 ≤ k → n.ascFact
| 0 => by rintro ⟨⟩
| 1 => by rintro (_ | ⟨⟨⟩⟩)
| k + 2 => fun _ => by
- rw [asc_factorial_succ, pow_succ]
+ rw [asc_factorial_succ, pow_succ']
refine'
Nat.mul_lt_mul' le_rfl
((asc_factorial_le_pow_add n _).trans_lt (pow_lt_pow_left (lt_add_one _) (succ_pos _)))
@@ -505,7 +505,7 @@ theorem descFactorial_eq_div {n k : ℕ} (h : k ≤ n) : n.descFactorial k = n !
theorem pow_sub_le_descFactorial (n : ℕ) : ∀ k : ℕ, (n + 1 - k) ^ k ≤ n.descFactorial k
| 0 => by rw [desc_factorial_zero, pow_zero]
| k + 1 => by
- rw [desc_factorial_succ, pow_succ, succ_sub_succ]
+ rw [desc_factorial_succ, pow_succ', succ_sub_succ]
exact
Nat.mul_le_mul_of_nonneg_left
(le_trans (Nat.pow_le_pow_left (tsub_le_tsub_right (le_succ _) _) k)
@@ -517,12 +517,12 @@ theorem pow_sub_le_descFactorial (n : ℕ) : ∀ k : ℕ, (n + 1 - k) ^ k ≤ n.
theorem pow_sub_lt_descFactorial' {n : ℕ} :
∀ {k : ℕ}, k + 2 ≤ n → (n - (k + 1)) ^ (k + 2) < n.descFactorial (k + 2)
| 0 => fun h => by
- rw [desc_factorial_succ, pow_succ, pow_one, desc_factorial_one]
+ rw [desc_factorial_succ, pow_succ', pow_one, desc_factorial_one]
exact
Nat.mul_lt_mul_of_pos_left (tsub_lt_self (lt_of_lt_of_le zero_lt_two h) zero_lt_one)
(tsub_pos_of_lt h)
| k + 1 => fun h => by
- rw [desc_factorial_succ, pow_succ]
+ rw [desc_factorial_succ, pow_succ']
refine'
Nat.mul_lt_mul_of_pos_left
((Nat.pow_le_pow_left (tsub_le_tsub_right (le_succ n) _) _).trans_lt _) (tsub_pos_of_lt h)
@@ -544,7 +544,7 @@ theorem pow_sub_lt_descFactorial {n : ℕ} :
theorem descFactorial_le_pow (n : ℕ) : ∀ k : ℕ, n.descFactorial k ≤ n ^ k
| 0 => by rw [desc_factorial_zero, pow_zero]
| k + 1 => by
- rw [desc_factorial_succ, pow_succ]
+ rw [desc_factorial_succ, pow_succ']
exact Nat.mul_le_mul (Nat.sub_le _ _) (desc_factorial_le_pow k)
#align nat.desc_factorial_le_pow Nat.descFactorial_le_pow
-/
@@ -554,7 +554,7 @@ theorem descFactorial_lt_pow {n : ℕ} (hn : 1 ≤ n) : ∀ {k : ℕ}, 2 ≤ k
| 0 => by rintro ⟨⟩
| 1 => by rintro (_ | ⟨⟨⟩⟩)
| k + 2 => fun _ => by
- rw [desc_factorial_succ, pow_succ', mul_comm]
+ rw [desc_factorial_succ, pow_succ, mul_comm]
exact
Nat.mul_lt_mul' (desc_factorial_le_pow _ _) (tsub_lt_self hn k.zero_lt_succ) (pow_pos hn _)
#align nat.desc_factorial_lt_pow Nat.descFactorial_lt_pow
mathlib commit https://github.com/leanprover-community/mathlib/commit/65a1391a0106c9204fe45bc73a039f056558cb83
@@ -163,11 +163,11 @@ theorem factorial_inj (hn : 1 < n !) : n ! = m ! ↔ n = m :=
by
refine' ⟨fun h => _, congr_arg _⟩
obtain hnm | rfl | hnm := lt_trichotomy n m
- · rw [← factorial_lt <| pos_of_gt <| one_lt_factorial.mp hn, h] at hnm
+ · rw [← factorial_lt <| pos_of_gt <| one_lt_factorial.mp hn, h] at hnm
cases lt_irrefl _ hnm
· rfl
- rw [h, one_lt_factorial] at hn
- rw [← factorial_lt (lt_trans one_pos hn), h] at hnm
+ rw [h, one_lt_factorial] at hn
+ rw [← factorial_lt (lt_trans one_pos hn), h] at hnm
cases lt_irrefl _ hnm
#align nat.factorial_inj Nat.factorial_inj
-/
mathlib commit https://github.com/leanprover-community/mathlib/commit/65a1391a0106c9204fe45bc73a039f056558cb83
@@ -243,7 +243,7 @@ theorem factorial_mul_pow_sub_le_factorial {n m : ℕ} (hnm : n ≤ m) : n ! * n
suffices n ! * (n + 1) ^ (m - n) ≤ m ! by
apply trans _ this
rw [mul_le_mul_left]
- apply pow_le_pow_of_le_left (zero_le n) (le_succ n)
+ apply pow_le_pow_left (zero_le n) (le_succ n)
exact factorial_pos n
convert Nat.factorial_mul_pow_le_factorial
exact (add_tsub_cancel_of_le hnm).symm
@@ -363,7 +363,7 @@ theorem ascFactorial_le_pow_add (n : ℕ) : ∀ k : ℕ, n.ascFactorial k ≤ (n
rw [asc_factorial_succ, pow_succ]
exact
Nat.mul_le_mul_of_nonneg_left
- ((asc_factorial_le_pow_add k).trans (Nat.pow_le_pow_of_le_left (le_succ _) _))
+ ((asc_factorial_le_pow_add k).trans (Nat.pow_le_pow_left (le_succ _) _))
#align nat.asc_factorial_le_pow_add Nat.ascFactorial_le_pow_add
-/
@@ -375,8 +375,7 @@ theorem ascFactorial_lt_pow_add (n : ℕ) : ∀ {k : ℕ}, 2 ≤ k → n.ascFact
rw [asc_factorial_succ, pow_succ]
refine'
Nat.mul_lt_mul' le_rfl
- ((asc_factorial_le_pow_add n _).trans_lt
- (pow_lt_pow_of_lt_left (lt_add_one _) (succ_pos _)))
+ ((asc_factorial_le_pow_add n _).trans_lt (pow_lt_pow_left (lt_add_one _) (succ_pos _)))
(succ_pos _)
#align nat.asc_factorial_lt_pow_add Nat.ascFactorial_lt_pow_add
-/
@@ -509,7 +508,7 @@ theorem pow_sub_le_descFactorial (n : ℕ) : ∀ k : ℕ, (n + 1 - k) ^ k ≤ n.
rw [desc_factorial_succ, pow_succ, succ_sub_succ]
exact
Nat.mul_le_mul_of_nonneg_left
- (le_trans (Nat.pow_le_pow_of_le_left (tsub_le_tsub_right (le_succ _) _) k)
+ (le_trans (Nat.pow_le_pow_left (tsub_le_tsub_right (le_succ _) _) k)
(pow_sub_le_desc_factorial k))
#align nat.pow_sub_le_desc_factorial Nat.pow_sub_le_descFactorial
-/
@@ -526,8 +525,7 @@ theorem pow_sub_lt_descFactorial' {n : ℕ} :
rw [desc_factorial_succ, pow_succ]
refine'
Nat.mul_lt_mul_of_pos_left
- ((Nat.pow_le_pow_of_le_left (tsub_le_tsub_right (le_succ n) _) _).trans_lt _)
- (tsub_pos_of_lt h)
+ ((Nat.pow_le_pow_left (tsub_le_tsub_right (le_succ n) _) _).trans_lt _) (tsub_pos_of_lt h)
rw [succ_sub_succ]
exact pow_sub_lt_desc_factorial' ((le_succ _).trans h)
#align nat.pow_sub_lt_desc_factorial' Nat.pow_sub_lt_descFactorial'
mathlib commit https://github.com/leanprover-community/mathlib/commit/ce64cd319bb6b3e82f31c2d38e79080d377be451
@@ -3,8 +3,8 @@ Copyright (c) 2018 Mario Carneiro. All rights reserved.
Released under Apache 2.0 license as described in the file LICENSE.
Authors: Mario Carneiro, Chris Hughes, Floris van Doorn, Yaël Dillies
-/
-import Mathbin.Data.Nat.Basic
-import Mathbin.Data.Nat.Pow
+import Data.Nat.Basic
+import Data.Nat.Pow
#align_import data.nat.factorial.basic from "leanprover-community/mathlib"@"c3291da49cfa65f0d43b094750541c0731edc932"
mathlib commit https://github.com/leanprover-community/mathlib/commit/32a7e535287f9c73f2e4d2aef306a39190f0b504
@@ -467,7 +467,7 @@ theorem descFactorial_eq_zero_iff_lt {n : ℕ} : ∀ {k : ℕ}, n.descFactorial
#align nat.desc_factorial_eq_zero_iff_lt Nat.descFactorial_eq_zero_iff_lt
-/
-alias desc_factorial_eq_zero_iff_lt ↔ _ desc_factorial_of_lt
+alias ⟨_, desc_factorial_of_lt⟩ := desc_factorial_eq_zero_iff_lt
#align nat.desc_factorial_of_lt Nat.descFactorial_of_lt
#print Nat.add_descFactorial_eq_ascFactorial /-
mathlib commit https://github.com/leanprover-community/mathlib/commit/32a7e535287f9c73f2e4d2aef306a39190f0b504
@@ -96,7 +96,7 @@ theorem factorial_dvd_factorial {m n} (h : m ≤ n) : m ! ∣ n ! :=
· simp [Nat.eq_zero_of_le_zero h]
obtain rfl | hl := h.eq_or_lt
· simp
- exact (IH (le_of_lt_succ hl)).mul_left _
+ exact (IH (le_of_lt_succ hl)).hMul_left _
#align nat.factorial_dvd_factorial Nat.factorial_dvd_factorial
-/
mathlib commit https://github.com/leanprover-community/mathlib/commit/8ea5598db6caeddde6cb734aa179cc2408dbd345
@@ -2,15 +2,12 @@
Copyright (c) 2018 Mario Carneiro. All rights reserved.
Released under Apache 2.0 license as described in the file LICENSE.
Authors: Mario Carneiro, Chris Hughes, Floris van Doorn, Yaël Dillies
-
-! This file was ported from Lean 3 source module data.nat.factorial.basic
-! leanprover-community/mathlib commit c3291da49cfa65f0d43b094750541c0731edc932
-! Please do not edit these lines, except to modify the commit id
-! if you have ported upstream changes.
-/
import Mathbin.Data.Nat.Basic
import Mathbin.Data.Nat.Pow
+#align_import data.nat.factorial.basic from "leanprover-community/mathlib"@"c3291da49cfa65f0d43b094750541c0731edc932"
+
/-!
# Factorial and variants
mathlib commit https://github.com/leanprover-community/mathlib/commit/9fb8964792b4237dac6200193a0d533f1b3f7423
@@ -39,7 +39,6 @@ def factorial : ℕ → ℕ
#align nat.factorial Nat.factorial
-/
--- mathport name: nat.factorial
scoped notation:10000 n "!" => Nat.factorial n
section Factorial
mathlib commit https://github.com/leanprover-community/mathlib/commit/cca40788df1b8755d5baf17ab2f27dacc2e17acb
@@ -167,11 +167,11 @@ theorem factorial_inj (hn : 1 < n !) : n ! = m ! ↔ n = m :=
by
refine' ⟨fun h => _, congr_arg _⟩
obtain hnm | rfl | hnm := lt_trichotomy n m
- · rw [← factorial_lt <| pos_of_gt <| one_lt_factorial.mp hn, h] at hnm
+ · rw [← factorial_lt <| pos_of_gt <| one_lt_factorial.mp hn, h] at hnm
cases lt_irrefl _ hnm
· rfl
- rw [h, one_lt_factorial] at hn
- rw [← factorial_lt (lt_trans one_pos hn), h] at hnm
+ rw [h, one_lt_factorial] at hn
+ rw [← factorial_lt (lt_trans one_pos hn), h] at hnm
cases lt_irrefl _ hnm
#align nat.factorial_inj Nat.factorial_inj
-/
mathlib commit https://github.com/leanprover-community/mathlib/commit/917c3c072e487b3cccdbfeff17e75b40e45f66cb
@@ -489,9 +489,7 @@ theorem add_descFactorial_eq_ascFactorial (n : ℕ) :
for the version using ℕ-division. -/
theorem factorial_mul_descFactorial : ∀ {n k : ℕ}, k ≤ n → (n - k)! * n.descFactorial k = n !
| n, 0 => fun _ => by rw [desc_factorial_zero, mul_one, tsub_zero]
- | 0, succ k => fun h => by
- exfalso
- exact not_succ_le_zero k h
+ | 0, succ k => fun h => by exfalso; exact not_succ_le_zero k h
| succ n, succ k => fun h => by
rw [succ_desc_factorial_succ, succ_sub_succ, ← mul_assoc, mul_comm (n - k)!, mul_assoc,
factorial_mul_desc_factorial (Nat.succ_le_succ_iff.1 h), factorial_succ]
@@ -544,9 +542,7 @@ theorem pow_sub_lt_descFactorial {n : ℕ} :
∀ {k : ℕ}, 2 ≤ k → k ≤ n → (n + 1 - k) ^ k < n.descFactorial k
| 0 => by rintro ⟨⟩
| 1 => by rintro (_ | ⟨⟨⟩⟩)
- | k + 2 => fun _ h => by
- rw [succ_sub_succ]
- exact pow_sub_lt_desc_factorial' h
+ | k + 2 => fun _ h => by rw [succ_sub_succ]; exact pow_sub_lt_desc_factorial' h
#align nat.pow_sub_lt_desc_factorial Nat.pow_sub_lt_descFactorial
-/
mathlib commit https://github.com/leanprover-community/mathlib/commit/3180fab693e2cee3bff62675571264cb8778b212
@@ -421,7 +421,7 @@ theorem descFactorial_succ (n k : ℕ) : n.descFactorial k.succ = (n - k) * n.de
#print Nat.zero_descFactorial_succ /-
theorem zero_descFactorial_succ (k : ℕ) : (0 : ℕ).descFactorial k.succ = 0 := by
- rw [desc_factorial_succ, zero_tsub, zero_mul]
+ rw [desc_factorial_succ, zero_tsub, MulZeroClass.zero_mul]
#align nat.zero_desc_factorial_succ Nat.zero_descFactorial_succ
-/
mathlib commit https://github.com/leanprover-community/mathlib/commit/bd9851ca476957ea4549eb19b40e7b5ade9428cc
Make use of Nat
-specific lemmas from Std rather than the general ones provided by mathlib.
The ultimate goal here is to carve out Data
, Algebra
and Order
sublibraries.
@@ -3,9 +3,7 @@ Copyright (c) 2018 Mario Carneiro. All rights reserved.
Released under Apache 2.0 license as described in the file LICENSE.
Authors: Mario Carneiro, Chris Hughes, Floris van Doorn, Yaël Dillies
-/
-import Mathlib.Algebra.Divisibility.Basic
-import Mathlib.Data.Nat.Basic
-import Mathlib.Order.Monotone.Basic
+import Mathlib.Data.Nat.Defs
import Mathlib.Tactic.GCongr.Core
import Mathlib.Tactic.Common
import Mathlib.Tactic.Monotonicity.Attr
@@ -73,15 +71,13 @@ theorem factorial_ne_zero (n : ℕ) : n ! ≠ 0 :=
#align nat.factorial_ne_zero Nat.factorial_ne_zero
theorem factorial_dvd_factorial {m n} (h : m ≤ n) : m ! ∣ n ! := by
- induction' n with n IH
- · simp [Nat.eq_zero_of_le_zero h]
- obtain rfl | hl := h.eq_or_lt
- · simp
- exact (IH (le_of_lt_succ hl)).mul_left _
+ induction' h with n _ ih
+ · exact Nat.dvd_refl _
+ · exact Nat.dvd_trans ih (Nat.dvd_mul_left _ _)
#align nat.factorial_dvd_factorial Nat.factorial_dvd_factorial
theorem dvd_factorial : ∀ {m n}, 0 < m → m ≤ n → m ∣ n !
- | succ _, _, _, h => dvd_of_mul_right_dvd (factorial_dvd_factorial h)
+ | succ _, _, _, h => Nat.dvd_trans (Nat.dvd_mul_right _ _) (factorial_dvd_factorial h)
#align nat.dvd_factorial Nat.dvd_factorial
@[mono, gcongr]
@@ -92,22 +88,19 @@ theorem factorial_le {m n} (h : m ≤ n) : m ! ≤ n ! :=
theorem factorial_mul_pow_le_factorial : ∀ {m n : ℕ}, m ! * (m + 1) ^ n ≤ (m + n)!
| m, 0 => by simp
| m, n + 1 => by
- rw [← add_assoc, factorial_succ, mul_comm (_ + 1), Nat.pow_succ, ← mul_assoc]
+ rw [← Nat.add_assoc, factorial_succ, Nat.mul_comm (_ + 1), Nat.pow_succ, ← Nat.mul_assoc]
exact Nat.mul_le_mul factorial_mul_pow_le_factorial (succ_le_succ (le_add_right _ _))
#align nat.factorial_mul_pow_le_factorial Nat.factorial_mul_pow_le_factorial
-theorem monotone_factorial : Monotone factorial := fun _ _ => factorial_le
-#align nat.monotone_factorial Nat.monotone_factorial
-
theorem factorial_lt (hn : 0 < n) : n ! < m ! ↔ n < m := by
- refine' ⟨fun h => not_le.mp fun hmn => not_le_of_lt h (factorial_le hmn), fun h => _⟩
+ refine' ⟨fun h => not_le.mp fun hmn => Nat.not_le_of_lt h (factorial_le hmn), fun h => _⟩
have : ∀ {n}, 0 < n → n ! < (n + 1)! := by
intro k hk
rw [factorial_succ, succ_mul, Nat.lt_add_left_iff_pos]
exact Nat.mul_pos hk k.factorial_pos
induction' h with k hnk ih generalizing hn
· exact this hn
- · exact (ih hn).trans (this <| hn.trans <| lt_of_succ_le hnk)
+ · exact lt_trans (ih hn) $ this <| lt_trans hn <| lt_of_succ_le hnk
#align nat.factorial_lt Nat.factorial_lt
@[gcongr]
@@ -147,25 +140,19 @@ theorem self_le_factorial : ∀ n : ℕ, n ≤ n !
#align nat.self_le_factorial Nat.self_le_factorial
theorem lt_factorial_self {n : ℕ} (hi : 3 ≤ n) : n < n ! := by
- have : 0 < n := Nat.zero_lt_two.trans (succ_le_iff.mp hi)
+ have : 0 < n := by omega
have hn : 1 < pred n := le_pred_of_lt (succ_le_iff.mp hi)
rw [← succ_pred_eq_of_pos ‹0 < n›, factorial_succ]
- exact (Nat.lt_mul_iff_one_lt_right (pred n).succ_pos).2 (hn.trans_le (self_le_factorial _))
+ exact (Nat.lt_mul_iff_one_lt_right (pred n).succ_pos).2
+ ((Nat.lt_of_lt_of_le hn (self_le_factorial _)))
#align nat.lt_factorial_self Nat.lt_factorial_self
theorem add_factorial_succ_lt_factorial_add_succ {i : ℕ} (n : ℕ) (hi : 2 ≤ i) :
i + (n + 1)! < (i + n + 1)! := by
- rw [factorial_succ (i + _), add_mul, one_mul]
- have : i ≤ i + n := le.intro rfl
- exact Nat.add_lt_add_of_lt_of_le
- (this.trans_lt
- ((Nat.lt_mul_iff_one_lt_right ((by decide : 0 < 2).trans_le (hi.trans this))).mpr
- (lt_iff_le_and_ne.mpr
- ⟨(i + n).factorial_pos, fun g =>
- Nat.not_succ_le_self 1 ((hi.trans this).trans (factorial_eq_one.mp g.symm))⟩)))
- (factorial_le
- ((le_of_eq (add_comm n 1)).trans
- (Nat.add_le_add_iff_right.2 ((by decide : 1 ≤ 2).trans hi))))
+ rw [factorial_succ (i + _), Nat.add_mul, Nat.one_mul]
+ have := (i + n).self_le_factorial
+ refine Nat.add_lt_add_of_lt_of_le (Nat.lt_of_le_of_lt ?_ ((Nat.lt_mul_iff_one_lt_right ?_).2 ?_))
+ (factorial_le ?_) <;> omega
#align nat.add_factorial_succ_lt_factorial_add_succ Nat.add_factorial_succ_lt_factorial_add_succ
theorem add_factorial_lt_factorial_add {i n : ℕ} (hi : 2 ≤ i) (hn : 1 ≤ n) :
@@ -179,14 +166,14 @@ theorem add_factorial_lt_factorial_add {i n : ℕ} (hi : 2 ≤ i) (hn : 1 ≤ n)
theorem add_factorial_succ_le_factorial_add_succ (i : ℕ) (n : ℕ) :
i + (n + 1)! ≤ (i + (n + 1))! := by
cases (le_or_lt (2 : ℕ) i)
- · rw [← add_assoc]
+ · rw [← Nat.add_assoc]
apply Nat.le_of_lt
apply add_factorial_succ_lt_factorial_add_succ
assumption
· match i with
| 0 => simp
| 1 =>
- rw [← add_assoc, factorial_succ (1 + n), add_mul, one_mul, add_comm 1 n,
+ rw [← Nat.add_assoc, factorial_succ (1 + n), Nat.add_mul, Nat.one_mul, Nat.add_comm 1 n,
Nat.add_le_add_iff_right]
exact Nat.mul_pos n.succ_pos n.succ.factorial_pos
| succ (succ n) => contradiction
@@ -205,7 +192,7 @@ theorem factorial_mul_pow_sub_le_factorial {n m : ℕ} (hnm : n ≤ m) : n ! * n
#align nat.factorial_mul_pow_sub_le_factorial Nat.factorial_mul_pow_sub_le_factorial
lemma factorial_le_pow : ∀ n, n ! ≤ n ^ n
- | 0 => le_rfl
+ | 0 => le_refl _
| n + 1 =>
calc
_ ≤ (n + 1) * n ^ n := Nat.mul_le_mul_left _ n.factorial_le_pow
@@ -237,31 +224,30 @@ theorem ascFactorial_succ {n k : ℕ} : n.ascFactorial k.succ = (n + k) * n.ascF
theorem zero_ascFactorial : ∀ (k : ℕ), (0 : ℕ).ascFactorial k.succ = 0
| 0 => by
- rw [ascFactorial_succ, ascFactorial_zero, zero_add, zero_mul]
+ rw [ascFactorial_succ, ascFactorial_zero, Nat.zero_add, Nat.zero_mul]
| (k+1) => by
- rw [ascFactorial_succ, zero_ascFactorial k, mul_zero]
+ rw [ascFactorial_succ, zero_ascFactorial k, Nat.mul_zero]
@[simp]
theorem one_ascFactorial : ∀ (k : ℕ), (1 : ℕ).ascFactorial k = k.factorial
| 0 => ascFactorial_zero 1
| (k+1) => by
- rw [ascFactorial_succ, one_ascFactorial k, add_comm, factorial_succ]
+ rw [ascFactorial_succ, one_ascFactorial k, Nat.add_comm, factorial_succ]
theorem succ_ascFactorial (n : ℕ) :
∀ k, n * n.succ.ascFactorial k = (n + k) * n.ascFactorial k
- | 0 => by rw [add_zero, ascFactorial_zero, ascFactorial_zero]
- | k + 1 => by
- rw [ascFactorial, mul_left_comm, succ_ascFactorial n k, ascFactorial, succ_add, ← add_assoc]
+ | 0 => by rw [Nat.add_zero, ascFactorial_zero, ascFactorial_zero]
+ | k + 1 => by rw [ascFactorial, Nat.mul_left_comm, succ_ascFactorial n k, ascFactorial, succ_add,
+ ← Nat.add_assoc]
#align nat.succ_asc_factorial Nat.succ_ascFactorial
/-- `(n + 1).ascFactorial k = (n + k) ! / n !` but without ℕ-division. See
`Nat.ascFactorial_eq_div` for the version with ℕ-division. -/
theorem factorial_mul_ascFactorial (n : ℕ) : ∀ k, n ! * (n + 1).ascFactorial k = (n + k)!
- | 0 => by
- rw [add_zero, ascFactorial_zero, mul_one]
+ | 0 => by rw [ascFactorial_zero, Nat.add_zero, Nat.mul_one]
| k + 1 => by
- rw [ascFactorial_succ, ← add_assoc, factorial_succ, mul_comm (n + 1 + k), ← mul_assoc,
- factorial_mul_ascFactorial n k, mul_comm, add_right_comm]
+ rw [ascFactorial_succ, ← Nat.add_assoc, factorial_succ, Nat.mul_comm (n + 1 + k),
+ ← Nat.mul_assoc, factorial_mul_ascFactorial n k, Nat.mul_comm, Nat.add_right_comm]
#align nat.factorial_mul_asc_factorial Nat.factorial_mul_ascFactorial
/-- `n.ascFactorial k = (n + k - 1)! / (n - 1)!` for `n > 0` but without ℕ-division. See
@@ -274,18 +260,13 @@ theorem factorial_mul_ascFactorial' (n k : ℕ) (h : 0 < n) :
rw [Nat.sub_one, factorial_mul_ascFactorial]
/-- Avoid in favor of `Nat.factorial_mul_ascFactorial` if you can. ℕ-division isn't worth it. -/
-theorem ascFactorial_eq_div (n k : ℕ) : (n + 1).ascFactorial k = (n + k)! / n ! := by
- apply mul_left_cancel₀ n.factorial_ne_zero
- rw [factorial_mul_ascFactorial]
- exact (Nat.mul_div_cancel_left' <| factorial_dvd_factorial <| le_add_right n k).symm
+theorem ascFactorial_eq_div (n k : ℕ) : (n + 1).ascFactorial k = (n + k)! / n ! :=
+ Nat.eq_div_of_mul_eq_right n.factorial_ne_zero (factorial_mul_ascFactorial _ _)
-/-- Avoid in favor of `Nat.factorial_mul_ascFactorial` if you can. -/
+/-- Avoid in favor of `Nat.factorial_mul_ascFactorial'` if you can. ℕ-division isn't worth it. -/
theorem ascFactorial_eq_div' (n k : ℕ) (h : 0 < n) :
- n.ascFactorial k = (n + k - 1)! / (n - 1) ! := by
- apply mul_left_cancel₀ (n-1).factorial_ne_zero
- rw [factorial_mul_ascFactorial' _ _ h]
- exact (Nat.mul_div_cancel_left' <| factorial_dvd_factorial <| Nat.sub_le_sub_right
- (le_add_right n k) 1).symm
+ n.ascFactorial k = (n + k - 1)! / (n - 1) ! :=
+ Nat.eq_div_of_mul_eq_right (n - 1).factorial_ne_zero (factorial_mul_ascFactorial' _ _ h)
#align nat.asc_factorial_eq_div Nat.ascFactorial_eq_div
theorem ascFactorial_of_sub {n k : ℕ}:
@@ -294,15 +275,15 @@ theorem ascFactorial_of_sub {n k : ℕ}:
#align nat.asc_factorial_of_sub Nat.ascFactorial_of_sub
theorem pow_succ_le_ascFactorial (n : ℕ) : ∀ k : ℕ, n ^ k ≤ n.ascFactorial k
- | 0 => by rw [ascFactorial_zero, pow_zero]
+ | 0 => by rw [ascFactorial_zero, Nat.pow_zero]
| k + 1 => by
- rw [Nat.pow_succ, mul_comm, ascFactorial_succ, ← succ_ascFactorial]
+ rw [Nat.pow_succ, Nat.mul_comm, ascFactorial_succ, ← succ_ascFactorial]
exact Nat.mul_le_mul (Nat.le_refl n)
- ((pow_le_pow_of_le_left (le_succ n) k).trans (pow_succ_le_ascFactorial n.succ k))
+ (Nat.le_trans (Nat.pow_le_pow_left (le_succ n) k) (pow_succ_le_ascFactorial n.succ k))
#align nat.pow_succ_le_asc_factorial Nat.pow_succ_le_ascFactorial
theorem pow_lt_ascFactorial' (n k : ℕ) : (n + 1) ^ (k + 2) < (n + 1).ascFactorial (k + 2) := by
- rw [Nat.pow_succ, ascFactorial, mul_comm]
+ rw [Nat.pow_succ, ascFactorial, Nat.mul_comm]
exact Nat.mul_lt_mul_of_lt_of_le' (Nat.lt_add_of_pos_right k.succ_pos)
(pow_succ_le_ascFactorial n.succ _) (Nat.pow_pos n.succ_pos)
#align nat.pow_lt_asc_factorial' Nat.pow_lt_ascFactorial'
@@ -314,24 +295,24 @@ theorem pow_lt_ascFactorial (n : ℕ) : ∀ {k : ℕ}, 2 ≤ k → (n + 1) ^ k <
#align nat.pow_lt_asc_factorial Nat.pow_lt_ascFactorial
theorem ascFactorial_le_pow_add (n : ℕ) : ∀ k : ℕ, (n+1).ascFactorial k ≤ (n + k) ^ k
- | 0 => by rw [ascFactorial_zero, pow_zero]
+ | 0 => by rw [ascFactorial_zero, Nat.pow_zero]
| k + 1 => by
- rw [ascFactorial_succ, Nat.pow_succ, mul_comm, ← add_assoc, add_right_comm n 1 k]
+ rw [ascFactorial_succ, Nat.pow_succ, Nat.mul_comm, ← Nat.add_assoc, Nat.add_right_comm n 1 k]
exact Nat.mul_le_mul_right _
- ((ascFactorial_le_pow_add _ k).trans (Nat.pow_le_pow_of_le_left (le_succ _) _))
+ (Nat.le_trans (ascFactorial_le_pow_add _ k) (Nat.pow_le_pow_left (le_succ _) _))
#align nat.asc_factorial_le_pow_add Nat.ascFactorial_le_pow_add
theorem ascFactorial_lt_pow_add (n : ℕ) : ∀ {k : ℕ}, 2 ≤ k → (n + 1).ascFactorial k < (n + k) ^ k
| 0 => by rintro ⟨⟩
| 1 => by intro; contradiction
| k + 2 => fun _ => by
- rw [Nat.pow_succ, mul_comm, ascFactorial_succ, succ_add_eq_add_succ n (k + 1)]
- exact Nat.mul_lt_mul_of_le_of_lt le_rfl ((ascFactorial_le_pow_add n _).trans_lt
+ rw [Nat.pow_succ, Nat.mul_comm, ascFactorial_succ, succ_add_eq_add_succ n (k + 1)]
+ exact Nat.mul_lt_mul_of_le_of_lt (le_refl _) (Nat.lt_of_le_of_lt (ascFactorial_le_pow_add n _)
(Nat.pow_lt_pow_left (Nat.lt_succ_self _) k.succ_ne_zero)) (succ_pos _)
#align nat.asc_factorial_lt_pow_add Nat.ascFactorial_lt_pow_add
theorem ascFactorial_pos (n k : ℕ) : 0 < (n + 1).ascFactorial k :=
- (Nat.pow_pos n.succ_pos).trans_le (pow_succ_le_ascFactorial (n + 1) k)
+ Nat.lt_of_lt_of_le (Nat.pow_pos n.succ_pos) (pow_succ_le_ascFactorial (n + 1) k)
#align nat.asc_factorial_pos Nat.ascFactorial_pos
end AscFactorial
@@ -357,7 +338,7 @@ theorem descFactorial_succ (n k : ℕ) : n.descFactorial (k + 1) = (n - k) * n.d
#align nat.desc_factorial_succ Nat.descFactorial_succ
theorem zero_descFactorial_succ (k : ℕ) : (0 : ℕ).descFactorial (k + 1) = 0 := by
- rw [descFactorial_succ, Nat.zero_sub, zero_mul]
+ rw [descFactorial_succ, Nat.zero_sub, Nat.zero_mul]
#align nat.zero_desc_factorial_succ Nat.zero_descFactorial_succ
theorem descFactorial_one (n : ℕ) : n.descFactorial 1 = n := by simp
@@ -365,17 +346,17 @@ theorem descFactorial_one (n : ℕ) : n.descFactorial 1 = n := by simp
theorem succ_descFactorial_succ (n : ℕ) :
∀ k : ℕ, (n + 1).descFactorial (k + 1) = (n + 1) * n.descFactorial k
- | 0 => by rw [descFactorial_zero, descFactorial_one, mul_one]
+ | 0 => by rw [descFactorial_zero, descFactorial_one, Nat.mul_one]
| succ k => by
rw [descFactorial_succ, succ_descFactorial_succ _ k, descFactorial_succ, succ_sub_succ,
- mul_left_comm]
+ Nat.mul_left_comm]
#align nat.succ_desc_factorial_succ Nat.succ_descFactorial_succ
theorem succ_descFactorial (n : ℕ) :
∀ k, (n + 1 - k) * (n + 1).descFactorial k = (n + 1) * n.descFactorial k
| 0 => by rw [Nat.sub_zero, descFactorial_zero, descFactorial_zero]
| k + 1 => by
- rw [descFactorial, succ_descFactorial _ k, descFactorial_succ, succ_sub_succ, mul_left_comm]
+ rw [descFactorial, succ_descFactorial _ k, descFactorial_succ, succ_sub_succ, Nat.mul_left_comm]
#align nat.succ_desc_factorial Nat.succ_descFactorial
theorem descFactorial_self : ∀ n : ℕ, n.descFactorial n = n !
@@ -388,7 +369,7 @@ theorem descFactorial_eq_zero_iff_lt {n : ℕ} : ∀ {k : ℕ}, n.descFactorial
| 0 => by simp only [descFactorial_zero, Nat.one_ne_zero, Nat.not_lt_zero]
| succ k => by
rw [descFactorial_succ, mul_eq_zero, descFactorial_eq_zero_iff_lt, Nat.lt_succ_iff,
- Nat.sub_eq_zero_iff_le, lt_iff_le_and_ne, or_iff_left_iff_imp, and_imp]
+ Nat.sub_eq_zero_iff_le, Nat.lt_iff_le_and_ne, or_iff_left_iff_imp, and_imp]
exact fun h _ => h
#align nat.desc_factorial_eq_zero_iff_lt Nat.descFactorial_eq_zero_iff_lt
@@ -414,26 +395,26 @@ theorem add_descFactorial_eq_ascFactorial' (n : ℕ) :
/-- `n.descFactorial k = n! / (n - k)!` but without ℕ-division. See `Nat.descFactorial_eq_div`
for the version using ℕ-division. -/
theorem factorial_mul_descFactorial : ∀ {n k : ℕ}, k ≤ n → (n - k)! * n.descFactorial k = n !
- | n, 0 => fun _ => by rw [descFactorial_zero, mul_one, Nat.sub_zero]
+ | n, 0 => fun _ => by rw [descFactorial_zero, Nat.mul_one, Nat.sub_zero]
| 0, succ k => fun h => by
exfalso
exact not_succ_le_zero k h
| succ n, succ k => fun h => by
- rw [succ_descFactorial_succ, succ_sub_succ, ← mul_assoc, mul_comm (n - k)!, mul_assoc,
- factorial_mul_descFactorial (Nat.succ_le_succ_iff.1 h), factorial_succ]
+ rw [succ_descFactorial_succ, succ_sub_succ, ← Nat.mul_assoc, Nat.mul_comm (n - k)!,
+ Nat.mul_assoc, factorial_mul_descFactorial (Nat.succ_le_succ_iff.1 h), factorial_succ]
#align nat.factorial_mul_desc_factorial Nat.factorial_mul_descFactorial
/-- Avoid in favor of `Nat.factorial_mul_descFactorial` if you can. ℕ-division isn't worth it. -/
theorem descFactorial_eq_div {n k : ℕ} (h : k ≤ n) : n.descFactorial k = n ! / (n - k)! := by
- apply mul_left_cancel₀ (factorial_ne_zero (n - k))
+ apply Nat.mul_left_cancel (n - k).factorial_pos
rw [factorial_mul_descFactorial h]
exact (Nat.mul_div_cancel' <| factorial_dvd_factorial <| Nat.sub_le n k).symm
#align nat.desc_factorial_eq_div Nat.descFactorial_eq_div
theorem pow_sub_le_descFactorial (n : ℕ) : ∀ k : ℕ, (n + 1 - k) ^ k ≤ n.descFactorial k
- | 0 => by rw [descFactorial_zero, pow_zero]
+ | 0 => by rw [descFactorial_zero, Nat.pow_zero]
| k + 1 => by
- rw [descFactorial_succ, Nat.pow_succ, succ_sub_succ, mul_comm]
+ rw [descFactorial_succ, Nat.pow_succ, succ_sub_succ, Nat.mul_comm]
apply Nat.mul_le_mul_left
exact (le_trans (Nat.pow_le_pow_left (Nat.sub_le_sub_right n.le_succ _) k)
(pow_sub_le_descFactorial n k))
@@ -441,16 +422,15 @@ theorem pow_sub_le_descFactorial (n : ℕ) : ∀ k : ℕ, (n + 1 - k) ^ k ≤ n.
theorem pow_sub_lt_descFactorial' {n : ℕ} :
∀ {k : ℕ}, k + 2 ≤ n → (n - (k + 1)) ^ (k + 2) < n.descFactorial (k + 2)
- | 0 => fun h => by
- rw [descFactorial_succ, pow_succ, pow_one, descFactorial_one]
- exact Nat.mul_lt_mul_of_pos_left (Nat.sub_lt_self Nat.zero_lt_one (Nat.zero_lt_two.trans_le h))
- (Nat.sub_pos_of_lt h)
- | k + 1 => fun h => by
- rw [descFactorial_succ, Nat.pow_succ, mul_comm]
+ | 0, h => by
+ rw [descFactorial_succ, Nat.pow_succ, Nat.pow_one, descFactorial_one]
+ exact Nat.mul_lt_mul_of_pos_left (by omega) (Nat.sub_pos_of_lt h)
+ | k + 1, h => by
+ rw [descFactorial_succ, Nat.pow_succ, Nat.mul_comm]
refine Nat.mul_lt_mul_of_pos_left ?_ (Nat.sub_pos_of_lt h)
- refine (Nat.pow_le_pow_left (Nat.sub_le_sub_right n.le_succ _) _).trans_lt ?_
+ refine Nat.lt_of_le_of_lt (Nat.pow_le_pow_left (Nat.sub_le_sub_right n.le_succ _) _) ?_
rw [succ_sub_succ]
- exact pow_sub_lt_descFactorial' ((le_succ _).trans h)
+ exact pow_sub_lt_descFactorial' (Nat.le_trans (le_succ _) h)
#align nat.pow_sub_lt_desc_factorial' Nat.pow_sub_lt_descFactorial'
theorem pow_sub_lt_descFactorial {n : ℕ} :
@@ -463,9 +443,9 @@ theorem pow_sub_lt_descFactorial {n : ℕ} :
#align nat.pow_sub_lt_desc_factorial Nat.pow_sub_lt_descFactorial
theorem descFactorial_le_pow (n : ℕ) : ∀ k : ℕ, n.descFactorial k ≤ n ^ k
- | 0 => by rw [descFactorial_zero, pow_zero]
+ | 0 => by rw [descFactorial_zero, Nat.pow_zero]
| k + 1 => by
- rw [descFactorial_succ, Nat.pow_succ, mul_comm _ n]
+ rw [descFactorial_succ, Nat.pow_succ, Nat.mul_comm _ n]
exact Nat.mul_le_mul (Nat.sub_le _ _) (descFactorial_le_pow _ k)
#align nat.desc_factorial_le_pow Nat.descFactorial_le_pow
@@ -473,7 +453,7 @@ theorem descFactorial_lt_pow {n : ℕ} (hn : 1 ≤ n) : ∀ {k : ℕ}, 2 ≤ k
| 0 => by rintro ⟨⟩
| 1 => by intro; contradiction
| k + 2 => fun _ => by
- rw [descFactorial_succ, pow_succ', mul_comm, mul_comm n]
+ rw [descFactorial_succ, pow_succ', Nat.mul_comm, Nat.mul_comm n]
exact Nat.mul_lt_mul_of_le_of_lt (descFactorial_le_pow _ _) (Nat.sub_lt hn k.zero_lt_succ)
(Nat.pow_pos (Nat.lt_of_succ_le hn))
#align nat.desc_factorial_lt_pow Nat.descFactorial_lt_pow
@@ -481,13 +461,13 @@ theorem descFactorial_lt_pow {n : ℕ} (hn : 1 ≤ n) : ∀ {k : ℕ}, 2 ≤ k
end DescFactorial
lemma factorial_two_mul_le (n : ℕ) : (2 * n)! ≤ (2 * n) ^ n * n ! := by
- rw [two_mul, ← factorial_mul_ascFactorial, mul_comm]
+ rw [Nat.two_mul, ← factorial_mul_ascFactorial, Nat.mul_comm]
exact Nat.mul_le_mul_right _ (ascFactorial_le_pow_add _ _)
lemma two_pow_mul_factorial_le_factorial_two_mul (n : ℕ) : 2 ^ n * n ! ≤ (2 * n) ! := by
obtain _ | n := n
· simp
- rw [mul_comm, two_mul]
+ rw [Nat.mul_comm, Nat.two_mul]
calc
_ ≤ (n + 1)! * (n + 2) ^ (n + 1) :=
Nat.mul_le_mul_left _ (pow_le_pow_of_le_left (le_add_left _ _) _)
Move basic Nat
lemmas from Data.Nat.Order.Basic
and Data.Nat.Pow
to Data.Nat.Defs
. Most proofs need adapting, but that's easily solved by replacing the general mathlib lemmas by the new Std Nat
-specific lemmas and using omega
.
Data.Nat.Pow
to Algebra.GroupPower.Order
Data.Nat.Pow
to Algebra.GroupPower.Order
bit
/bit0
/bit1
lemmas from Data.Nat.Order.Basic
to Data.Nat.Bits
Data.Nat.Order.Basic
anymoreNat
-specific lemmas to help fix the fallout (look for nolint simpNF
)Nat.mul_self_le_mul_self_iff
and Nat.mul_self_lt_mul_self_iff
around (they were misnamed)Nat.one_lt_pow
implicit@@ -3,9 +3,12 @@ Copyright (c) 2018 Mario Carneiro. All rights reserved.
Released under Apache 2.0 license as described in the file LICENSE.
Authors: Mario Carneiro, Chris Hughes, Floris van Doorn, Yaël Dillies
-/
+import Mathlib.Algebra.Divisibility.Basic
+import Mathlib.Data.Nat.Basic
+import Mathlib.Order.Monotone.Basic
import Mathlib.Tactic.GCongr.Core
import Mathlib.Tactic.Common
-import Mathlib.Algebra.GroupPower.Order
+import Mathlib.Tactic.Monotonicity.Attr
#align_import data.nat.factorial.basic from "leanprover-community/mathlib"@"d012cd09a9b256d870751284dd6a29882b0be105"
@@ -57,12 +60,12 @@ theorem factorial_succ (n : ℕ) : (n + 1)! = (n + 1) * n ! :=
#align nat.factorial_two Nat.factorial_two
theorem mul_factorial_pred (hn : 0 < n) : n * (n - 1)! = n ! :=
- tsub_add_cancel_of_le (Nat.succ_le_of_lt hn) ▸ rfl
+ Nat.sub_add_cancel (Nat.succ_le_of_lt hn) ▸ rfl
#align nat.mul_factorial_pred Nat.mul_factorial_pred
theorem factorial_pos : ∀ n, 0 < n !
- | 0 => zero_lt_one
- | succ n => mul_pos (succ_pos _) (factorial_pos n)
+ | 0 => Nat.zero_lt_one
+ | succ n => Nat.mul_pos (succ_pos _) (factorial_pos n)
#align nat.factorial_pos Nat.factorial_pos
theorem factorial_ne_zero (n : ℕ) : n ! ≠ 0 :=
@@ -100,8 +103,8 @@ theorem factorial_lt (hn : 0 < n) : n ! < m ! ↔ n < m := by
refine' ⟨fun h => not_le.mp fun hmn => not_le_of_lt h (factorial_le hmn), fun h => _⟩
have : ∀ {n}, 0 < n → n ! < (n + 1)! := by
intro k hk
- rw [factorial_succ, succ_mul, lt_add_iff_pos_left]
- exact mul_pos hk k.factorial_pos
+ rw [factorial_succ, succ_mul, Nat.lt_add_left_iff_pos]
+ exact Nat.mul_pos hk k.factorial_pos
induction' h with k hnk ih generalizing hn
· exact this hn
· exact (ih hn).trans (this <| hn.trans <| lt_of_succ_le hnk)
@@ -110,9 +113,7 @@ theorem factorial_lt (hn : 0 < n) : n ! < m ! ↔ n < m := by
@[gcongr]
lemma factorial_lt_of_lt {m n : ℕ} (hn : 0 < n) (h : n < m) : n ! < m ! := (factorial_lt hn).mpr h
-@[simp]
-theorem one_lt_factorial : 1 < n ! ↔ 1 < n :=
- factorial_lt one_pos
+@[simp] lemma one_lt_factorial : 1 < n ! ↔ 1 < n := factorial_lt Nat.one_pos
#align nat.one_lt_factorial Nat.one_lt_factorial
@[simp]
@@ -127,11 +128,11 @@ theorem factorial_eq_one : n ! = 1 ↔ n ≤ 1 := by
theorem factorial_inj (hn : 1 < n) : n ! = m ! ↔ n = m := by
refine' ⟨fun h => _, congr_arg _⟩
obtain hnm | rfl | hnm := lt_trichotomy n m
- · rw [← factorial_lt <| pos_of_gt hn, h] at hnm
+ · rw [← factorial_lt <| lt_of_succ_lt hn, h] at hnm
cases lt_irrefl _ hnm
· rfl
rw [← one_lt_factorial, h, one_lt_factorial] at hn
- rw [← factorial_lt <| pos_of_gt hn, h] at hnm
+ rw [← factorial_lt <| lt_of_succ_lt hn, h] at hnm
cases lt_irrefl _ hnm
#align nat.factorial_inj Nat.factorial_inj
@@ -141,33 +142,30 @@ theorem factorial_inj' (h : 1 < n ∨ 1 < m) : n ! = m ! ↔ n = m := by
· rw [eq_comm, factorial_inj hm, eq_comm]
theorem self_le_factorial : ∀ n : ℕ, n ≤ n !
- | 0 => zero_le_one
- | k + 1 => le_mul_of_one_le_right k.zero_lt_succ.le (Nat.one_le_of_lt <| Nat.factorial_pos _)
+ | 0 => Nat.zero_le _
+ | k + 1 => Nat.le_mul_of_pos_right _ (Nat.one_le_of_lt k.factorial_pos)
#align nat.self_le_factorial Nat.self_le_factorial
theorem lt_factorial_self {n : ℕ} (hi : 3 ≤ n) : n < n ! := by
- have : 0 < n := (zero_lt_two (α := ℕ)).trans (succ_le_iff.mp hi)
- have : 1 < pred n := le_pred_of_lt (succ_le_iff.mp hi)
+ have : 0 < n := Nat.zero_lt_two.trans (succ_le_iff.mp hi)
+ have hn : 1 < pred n := le_pred_of_lt (succ_le_iff.mp hi)
rw [← succ_pred_eq_of_pos ‹0 < n›, factorial_succ]
- exact
- lt_mul_of_one_lt_right (pred n).succ_pos
- ((‹1 < pred n›).trans_le (self_le_factorial _))
+ exact (Nat.lt_mul_iff_one_lt_right (pred n).succ_pos).2 (hn.trans_le (self_le_factorial _))
#align nat.lt_factorial_self Nat.lt_factorial_self
theorem add_factorial_succ_lt_factorial_add_succ {i : ℕ} (n : ℕ) (hi : 2 ≤ i) :
i + (n + 1)! < (i + n + 1)! := by
rw [factorial_succ (i + _), add_mul, one_mul]
have : i ≤ i + n := le.intro rfl
- exact
- add_lt_add_of_lt_of_le
+ exact Nat.add_lt_add_of_lt_of_le
(this.trans_lt
- ((lt_mul_iff_one_lt_right ((by decide : 0 < 2).trans_le (hi.trans this))).mpr
+ ((Nat.lt_mul_iff_one_lt_right ((by decide : 0 < 2).trans_le (hi.trans this))).mpr
(lt_iff_le_and_ne.mpr
⟨(i + n).factorial_pos, fun g =>
Nat.not_succ_le_self 1 ((hi.trans this).trans (factorial_eq_one.mp g.symm))⟩)))
(factorial_le
((le_of_eq (add_comm n 1)).trans
- ((add_le_add_iff_right n).mpr ((by decide : 1 ≤ 2).trans hi))))
+ (Nat.add_le_add_iff_right.2 ((by decide : 1 ≤ 2).trans hi))))
#align nat.add_factorial_succ_lt_factorial_add_succ Nat.add_factorial_succ_lt_factorial_add_succ
theorem add_factorial_lt_factorial_add {i n : ℕ} (hi : 2 ≤ i) (hn : 1 ≤ n) :
@@ -188,10 +186,9 @@ theorem add_factorial_succ_le_factorial_add_succ (i : ℕ) (n : ℕ) :
· match i with
| 0 => simp
| 1 =>
- rw [← add_assoc, factorial_succ (1 + n), add_mul, one_mul, add_comm 1 n, add_le_add_iff_right]
- apply one_le_mul
- · apply Nat.le_add_left
- · apply factorial_pos
+ rw [← add_assoc, factorial_succ (1 + n), add_mul, one_mul, add_comm 1 n,
+ Nat.add_le_add_iff_right]
+ exact Nat.mul_pos n.succ_pos n.succ.factorial_pos
| succ (succ n) => contradiction
#align nat.add_factorial_succ_le_factorial_add_succ Nat.add_factorial_succ_le_factorial_add_succ
@@ -203,7 +200,7 @@ theorem add_factorial_le_factorial_add (i : ℕ) {n : ℕ} (n1 : 1 ≤ n) : i +
theorem factorial_mul_pow_sub_le_factorial {n m : ℕ} (hnm : n ≤ m) : n ! * n ^ (m - n) ≤ m ! := by
calc
- _ ≤ n ! * (n + 1) ^ (m - n) := mul_le_mul_left' (Nat.pow_le_pow_left n.le_succ _) _
+ _ ≤ n ! * (n + 1) ^ (m - n) := Nat.mul_le_mul_left _ (Nat.pow_le_pow_left n.le_succ _)
_ ≤ _ := by simpa [hnm] using @Nat.factorial_mul_pow_le_factorial n (m - n)
#align nat.factorial_mul_pow_sub_le_factorial Nat.factorial_mul_pow_sub_le_factorial
@@ -211,8 +208,8 @@ lemma factorial_le_pow : ∀ n, n ! ≤ n ^ n
| 0 => le_rfl
| n + 1 =>
calc
- _ ≤ (n + 1) * n ^ n := mul_le_mul_left' n.factorial_le_pow _
- _ ≤ (n + 1) * (n + 1) ^ n := mul_le_mul_left' (Nat.pow_le_pow_left n.le_succ _) _
+ _ ≤ (n + 1) * n ^ n := Nat.mul_le_mul_left _ n.factorial_le_pow
+ _ ≤ (n + 1) * (n + 1) ^ n := Nat.mul_le_mul_left _ (Nat.pow_le_pow_left n.le_succ _)
_ = _ := by rw [pow_succ']
end Factorial
@@ -306,8 +303,8 @@ theorem pow_succ_le_ascFactorial (n : ℕ) : ∀ k : ℕ, n ^ k ≤ n.ascFactori
theorem pow_lt_ascFactorial' (n k : ℕ) : (n + 1) ^ (k + 2) < (n + 1).ascFactorial (k + 2) := by
rw [Nat.pow_succ, ascFactorial, mul_comm]
- exact Nat.mul_lt_mul_of_lt_of_le' (lt_add_of_pos_right (n + 1) (succ_pos k))
- (pow_succ_le_ascFactorial n.succ _) (NeZero.pos ((n + 1) ^ (k + 1)))
+ exact Nat.mul_lt_mul_of_lt_of_le' (Nat.lt_add_of_pos_right k.succ_pos)
+ (pow_succ_le_ascFactorial n.succ _) (Nat.pow_pos n.succ_pos)
#align nat.pow_lt_asc_factorial' Nat.pow_lt_ascFactorial'
theorem pow_lt_ascFactorial (n : ℕ) : ∀ {k : ℕ}, 2 ≤ k → (n + 1) ^ k < (n + 1).ascFactorial k
@@ -330,11 +327,11 @@ theorem ascFactorial_lt_pow_add (n : ℕ) : ∀ {k : ℕ}, 2 ≤ k → (n + 1).a
| k + 2 => fun _ => by
rw [Nat.pow_succ, mul_comm, ascFactorial_succ, succ_add_eq_add_succ n (k + 1)]
exact Nat.mul_lt_mul_of_le_of_lt le_rfl ((ascFactorial_le_pow_add n _).trans_lt
- (pow_lt_pow_left (@lt_add_one ℕ _ _ _ _ _ _ _) (zero_le _) k.succ_ne_zero)) (succ_pos _)
+ (Nat.pow_lt_pow_left (Nat.lt_succ_self _) k.succ_ne_zero)) (succ_pos _)
#align nat.asc_factorial_lt_pow_add Nat.ascFactorial_lt_pow_add
theorem ascFactorial_pos (n k : ℕ) : 0 < (n + 1).ascFactorial k :=
- (pow_pos (succ_pos n) k).trans_le (pow_succ_le_ascFactorial (n + 1) k)
+ (Nat.pow_pos n.succ_pos).trans_le (pow_succ_le_ascFactorial (n + 1) k)
#align nat.asc_factorial_pos Nat.ascFactorial_pos
end AscFactorial
@@ -360,7 +357,7 @@ theorem descFactorial_succ (n k : ℕ) : n.descFactorial (k + 1) = (n - k) * n.d
#align nat.desc_factorial_succ Nat.descFactorial_succ
theorem zero_descFactorial_succ (k : ℕ) : (0 : ℕ).descFactorial (k + 1) = 0 := by
- rw [descFactorial_succ, zero_tsub, zero_mul]
+ rw [descFactorial_succ, Nat.zero_sub, zero_mul]
#align nat.zero_desc_factorial_succ Nat.zero_descFactorial_succ
theorem descFactorial_one (n : ℕ) : n.descFactorial 1 = n := by simp
@@ -376,7 +373,7 @@ theorem succ_descFactorial_succ (n : ℕ) :
theorem succ_descFactorial (n : ℕ) :
∀ k, (n + 1 - k) * (n + 1).descFactorial k = (n + 1) * n.descFactorial k
- | 0 => by rw [tsub_zero, descFactorial_zero, descFactorial_zero]
+ | 0 => by rw [Nat.sub_zero, descFactorial_zero, descFactorial_zero]
| k + 1 => by
rw [descFactorial, succ_descFactorial _ k, descFactorial_succ, succ_sub_succ, mul_left_comm]
#align nat.succ_desc_factorial Nat.succ_descFactorial
@@ -391,7 +388,7 @@ theorem descFactorial_eq_zero_iff_lt {n : ℕ} : ∀ {k : ℕ}, n.descFactorial
| 0 => by simp only [descFactorial_zero, Nat.one_ne_zero, Nat.not_lt_zero]
| succ k => by
rw [descFactorial_succ, mul_eq_zero, descFactorial_eq_zero_iff_lt, Nat.lt_succ_iff,
- tsub_eq_zero_iff_le, lt_iff_le_and_ne, or_iff_left_iff_imp, and_imp]
+ Nat.sub_eq_zero_iff_le, lt_iff_le_and_ne, or_iff_left_iff_imp, and_imp]
exact fun h _ => h
#align nat.desc_factorial_eq_zero_iff_lt Nat.descFactorial_eq_zero_iff_lt
@@ -417,7 +414,7 @@ theorem add_descFactorial_eq_ascFactorial' (n : ℕ) :
/-- `n.descFactorial k = n! / (n - k)!` but without ℕ-division. See `Nat.descFactorial_eq_div`
for the version using ℕ-division. -/
theorem factorial_mul_descFactorial : ∀ {n k : ℕ}, k ≤ n → (n - k)! * n.descFactorial k = n !
- | n, 0 => fun _ => by rw [descFactorial_zero, mul_one, tsub_zero]
+ | n, 0 => fun _ => by rw [descFactorial_zero, mul_one, Nat.sub_zero]
| 0, succ k => fun h => by
exfalso
exact not_succ_le_zero k h
@@ -438,7 +435,7 @@ theorem pow_sub_le_descFactorial (n : ℕ) : ∀ k : ℕ, (n + 1 - k) ^ k ≤ n.
| k + 1 => by
rw [descFactorial_succ, Nat.pow_succ, succ_sub_succ, mul_comm]
apply Nat.mul_le_mul_left
- exact (le_trans (Nat.pow_le_pow_left (tsub_le_tsub_right (le_succ _) _) k)
+ exact (le_trans (Nat.pow_le_pow_left (Nat.sub_le_sub_right n.le_succ _) k)
(pow_sub_le_descFactorial n k))
#align nat.pow_sub_le_desc_factorial Nat.pow_sub_le_descFactorial
@@ -446,16 +443,14 @@ theorem pow_sub_lt_descFactorial' {n : ℕ} :
∀ {k : ℕ}, k + 2 ≤ n → (n - (k + 1)) ^ (k + 2) < n.descFactorial (k + 2)
| 0 => fun h => by
rw [descFactorial_succ, pow_succ, pow_one, descFactorial_one]
- exact
- Nat.mul_lt_mul_of_pos_left (tsub_lt_self (lt_of_lt_of_le zero_lt_two h) zero_lt_one)
- (tsub_pos_of_lt h)
+ exact Nat.mul_lt_mul_of_pos_left (Nat.sub_lt_self Nat.zero_lt_one (Nat.zero_lt_two.trans_le h))
+ (Nat.sub_pos_of_lt h)
| k + 1 => fun h => by
rw [descFactorial_succ, Nat.pow_succ, mul_comm]
- apply Nat.mul_lt_mul_of_pos_left
- · refine' ((Nat.pow_le_pow_left (tsub_le_tsub_right (le_succ n) _) _).trans_lt _)
- rw [succ_sub_succ]
- exact pow_sub_lt_descFactorial' ((le_succ _).trans h)
- · apply tsub_pos_of_lt; apply h
+ refine Nat.mul_lt_mul_of_pos_left ?_ (Nat.sub_pos_of_lt h)
+ refine (Nat.pow_le_pow_left (Nat.sub_le_sub_right n.le_succ _) _).trans_lt ?_
+ rw [succ_sub_succ]
+ exact pow_sub_lt_descFactorial' ((le_succ _).trans h)
#align nat.pow_sub_lt_desc_factorial' Nat.pow_sub_lt_descFactorial'
theorem pow_sub_lt_descFactorial {n : ℕ} :
@@ -479,22 +474,23 @@ theorem descFactorial_lt_pow {n : ℕ} (hn : 1 ≤ n) : ∀ {k : ℕ}, 2 ≤ k
| 1 => by intro; contradiction
| k + 2 => fun _ => by
rw [descFactorial_succ, pow_succ', mul_comm, mul_comm n]
- exact Nat.mul_lt_mul_of_le_of_lt (descFactorial_le_pow _ _) (tsub_lt_self hn k.zero_lt_succ)
- (pow_pos (Nat.lt_of_succ_le hn) _)
+ exact Nat.mul_lt_mul_of_le_of_lt (descFactorial_le_pow _ _) (Nat.sub_lt hn k.zero_lt_succ)
+ (Nat.pow_pos (Nat.lt_of_succ_le hn))
#align nat.desc_factorial_lt_pow Nat.descFactorial_lt_pow
end DescFactorial
lemma factorial_two_mul_le (n : ℕ) : (2 * n)! ≤ (2 * n) ^ n * n ! := by
rw [two_mul, ← factorial_mul_ascFactorial, mul_comm]
- exact mul_le_mul_right' (ascFactorial_le_pow_add _ _) _
+ exact Nat.mul_le_mul_right _ (ascFactorial_le_pow_add _ _)
lemma two_pow_mul_factorial_le_factorial_two_mul (n : ℕ) : 2 ^ n * n ! ≤ (2 * n) ! := by
obtain _ | n := n
· simp
rw [mul_comm, two_mul]
calc
- _ ≤ (n + 1)! * (n + 2) ^ (n + 1) := mul_le_mul_left' (pow_le_pow_of_le_left le_add_self _) _
+ _ ≤ (n + 1)! * (n + 2) ^ (n + 1) :=
+ Nat.mul_le_mul_left _ (pow_le_pow_of_le_left (le_add_left _ _) _)
_ ≤ _ := Nat.factorial_mul_pow_le_factorial
end Nat
This is a very large PR, but it has been reviewed piecemeal already in PRs to the bump/v4.7.0
branch as we update to intermediate nightlies.
Co-authored-by: Scott Morrison <scott.morrison@gmail.com> Co-authored-by: Kyle Miller <kmill31415@gmail.com> Co-authored-by: damiano <adomani@gmail.com>
@@ -89,7 +89,7 @@ theorem factorial_le {m n} (h : m ≤ n) : m ! ≤ n ! :=
theorem factorial_mul_pow_le_factorial : ∀ {m n : ℕ}, m ! * (m + 1) ^ n ≤ (m + n)!
| m, 0 => by simp
| m, n + 1 => by
- rw [← add_assoc, factorial_succ, mul_comm (_ + 1), pow_succ, ← mul_assoc]
+ rw [← add_assoc, factorial_succ, mul_comm (_ + 1), Nat.pow_succ, ← mul_assoc]
exact Nat.mul_le_mul factorial_mul_pow_le_factorial (succ_le_succ (le_add_right _ _))
#align nat.factorial_mul_pow_le_factorial Nat.factorial_mul_pow_le_factorial
@@ -299,13 +299,13 @@ theorem ascFactorial_of_sub {n k : ℕ}:
theorem pow_succ_le_ascFactorial (n : ℕ) : ∀ k : ℕ, n ^ k ≤ n.ascFactorial k
| 0 => by rw [ascFactorial_zero, pow_zero]
| k + 1 => by
- rw [pow_succ, mul_comm, ascFactorial_succ, ← succ_ascFactorial]
+ rw [Nat.pow_succ, mul_comm, ascFactorial_succ, ← succ_ascFactorial]
exact Nat.mul_le_mul (Nat.le_refl n)
((pow_le_pow_of_le_left (le_succ n) k).trans (pow_succ_le_ascFactorial n.succ k))
#align nat.pow_succ_le_asc_factorial Nat.pow_succ_le_ascFactorial
theorem pow_lt_ascFactorial' (n k : ℕ) : (n + 1) ^ (k + 2) < (n + 1).ascFactorial (k + 2) := by
- rw [pow_succ, ascFactorial, mul_comm]
+ rw [Nat.pow_succ, ascFactorial, mul_comm]
exact Nat.mul_lt_mul_of_lt_of_le' (lt_add_of_pos_right (n + 1) (succ_pos k))
(pow_succ_le_ascFactorial n.succ _) (NeZero.pos ((n + 1) ^ (k + 1)))
#align nat.pow_lt_asc_factorial' Nat.pow_lt_ascFactorial'
@@ -319,7 +319,7 @@ theorem pow_lt_ascFactorial (n : ℕ) : ∀ {k : ℕ}, 2 ≤ k → (n + 1) ^ k <
theorem ascFactorial_le_pow_add (n : ℕ) : ∀ k : ℕ, (n+1).ascFactorial k ≤ (n + k) ^ k
| 0 => by rw [ascFactorial_zero, pow_zero]
| k + 1 => by
- rw [ascFactorial_succ, pow_succ, mul_comm, ← add_assoc, add_right_comm n 1 k]
+ rw [ascFactorial_succ, Nat.pow_succ, mul_comm, ← add_assoc, add_right_comm n 1 k]
exact Nat.mul_le_mul_right _
((ascFactorial_le_pow_add _ k).trans (Nat.pow_le_pow_of_le_left (le_succ _) _))
#align nat.asc_factorial_le_pow_add Nat.ascFactorial_le_pow_add
@@ -328,7 +328,7 @@ theorem ascFactorial_lt_pow_add (n : ℕ) : ∀ {k : ℕ}, 2 ≤ k → (n + 1).a
| 0 => by rintro ⟨⟩
| 1 => by intro; contradiction
| k + 2 => fun _ => by
- rw [pow_succ, mul_comm, ascFactorial_succ, succ_add_eq_add_succ n (k + 1)]
+ rw [Nat.pow_succ, mul_comm, ascFactorial_succ, succ_add_eq_add_succ n (k + 1)]
exact Nat.mul_lt_mul_of_le_of_lt le_rfl ((ascFactorial_le_pow_add n _).trans_lt
(pow_lt_pow_left (@lt_add_one ℕ _ _ _ _ _ _ _) (zero_le _) k.succ_ne_zero)) (succ_pos _)
#align nat.asc_factorial_lt_pow_add Nat.ascFactorial_lt_pow_add
@@ -436,7 +436,7 @@ theorem descFactorial_eq_div {n k : ℕ} (h : k ≤ n) : n.descFactorial k = n !
theorem pow_sub_le_descFactorial (n : ℕ) : ∀ k : ℕ, (n + 1 - k) ^ k ≤ n.descFactorial k
| 0 => by rw [descFactorial_zero, pow_zero]
| k + 1 => by
- rw [descFactorial_succ, pow_succ, succ_sub_succ, mul_comm]
+ rw [descFactorial_succ, Nat.pow_succ, succ_sub_succ, mul_comm]
apply Nat.mul_le_mul_left
exact (le_trans (Nat.pow_le_pow_left (tsub_le_tsub_right (le_succ _) _) k)
(pow_sub_le_descFactorial n k))
@@ -450,7 +450,7 @@ theorem pow_sub_lt_descFactorial' {n : ℕ} :
Nat.mul_lt_mul_of_pos_left (tsub_lt_self (lt_of_lt_of_le zero_lt_two h) zero_lt_one)
(tsub_pos_of_lt h)
| k + 1 => fun h => by
- rw [descFactorial_succ, pow_succ, mul_comm]
+ rw [descFactorial_succ, Nat.pow_succ, mul_comm]
apply Nat.mul_lt_mul_of_pos_left
· refine' ((Nat.pow_le_pow_left (tsub_le_tsub_right (le_succ n) _) _).trans_lt _)
rw [succ_sub_succ]
@@ -470,7 +470,7 @@ theorem pow_sub_lt_descFactorial {n : ℕ} :
theorem descFactorial_le_pow (n : ℕ) : ∀ k : ℕ, n.descFactorial k ≤ n ^ k
| 0 => by rw [descFactorial_zero, pow_zero]
| k + 1 => by
- rw [descFactorial_succ, pow_succ, mul_comm _ n]
+ rw [descFactorial_succ, Nat.pow_succ, mul_comm _ n]
exact Nat.mul_le_mul (Nat.sub_le _ _) (descFactorial_le_pow _ k)
#align nat.desc_factorial_le_pow Nat.descFactorial_le_pow
@@ -3,9 +3,9 @@ Copyright (c) 2018 Mario Carneiro. All rights reserved.
Released under Apache 2.0 license as described in the file LICENSE.
Authors: Mario Carneiro, Chris Hughes, Floris van Doorn, Yaël Dillies
-/
-import Mathlib.Data.Nat.Pow
import Mathlib.Tactic.GCongr.Core
import Mathlib.Tactic.Common
+import Mathlib.Algebra.GroupPower.Order
#align_import data.nat.factorial.basic from "leanprover-community/mathlib"@"d012cd09a9b256d870751284dd6a29882b0be105"
@@ -390,7 +390,7 @@ theorem descFactorial_self : ∀ n : ℕ, n.descFactorial n = n !
theorem descFactorial_eq_zero_iff_lt {n : ℕ} : ∀ {k : ℕ}, n.descFactorial k = 0 ↔ n < k
| 0 => by simp only [descFactorial_zero, Nat.one_ne_zero, Nat.not_lt_zero]
| succ k => by
- rw [descFactorial_succ, mul_eq_zero, descFactorial_eq_zero_iff_lt, lt_succ_iff,
+ rw [descFactorial_succ, mul_eq_zero, descFactorial_eq_zero_iff_lt, Nat.lt_succ_iff,
tsub_eq_zero_iff_le, lt_iff_le_and_ne, or_iff_left_iff_imp, and_imp]
exact fun h _ => h
#align nat.desc_factorial_eq_zero_iff_lt Nat.descFactorial_eq_zero_iff_lt
Co-authored-by: Scott Morrison <scott.morrison@gmail.com> Co-authored-by: Eric Wieser <wieser.eric@gmail.com> Co-authored-by: Joachim Breitner <mail@joachim-breitner.de>
@@ -438,8 +438,8 @@ theorem pow_sub_le_descFactorial (n : ℕ) : ∀ k : ℕ, (n + 1 - k) ^ k ≤ n.
| k + 1 => by
rw [descFactorial_succ, pow_succ, succ_sub_succ, mul_comm]
apply Nat.mul_le_mul_left
- exact (le_trans (Nat.pow_le_pow_left (tsub_le_tsub_right (le_succ _) _) k)
- (pow_sub_le_descFactorial n k))
+ exact (le_trans (Nat.pow_le_pow_left (tsub_le_tsub_right (le_succ _) _) k)
+ (pow_sub_le_descFactorial n k))
#align nat.pow_sub_le_desc_factorial Nat.pow_sub_le_descFactorial
theorem pow_sub_lt_descFactorial' {n : ℕ} :
@@ -277,7 +277,7 @@ theorem factorial_mul_ascFactorial' (n k : ℕ) (h : 0 < n) :
rw [Nat.sub_one, factorial_mul_ascFactorial]
/-- Avoid in favor of `Nat.factorial_mul_ascFactorial` if you can. ℕ-division isn't worth it. -/
-theorem ascFactorial_eq_div (n k : ℕ) : (n + 1).ascFactorial k = (n + k)! / n ! := by
+theorem ascFactorial_eq_div (n k : ℕ) : (n + 1).ascFactorial k = (n + k)! / n ! := by
apply mul_left_cancel₀ n.factorial_ne_zero
rw [factorial_mul_ascFactorial]
exact (Nat.mul_div_cancel_left' <| factorial_dvd_factorial <| le_add_right n k).symm
@@ -306,7 +306,7 @@ theorem pow_succ_le_ascFactorial (n : ℕ) : ∀ k : ℕ, n ^ k ≤ n.ascFactori
theorem pow_lt_ascFactorial' (n k : ℕ) : (n + 1) ^ (k + 2) < (n + 1).ascFactorial (k + 2) := by
rw [pow_succ, ascFactorial, mul_comm]
- exact Nat.mul_lt_mul (lt_add_of_pos_right (n + 1) (succ_pos k))
+ exact Nat.mul_lt_mul_of_lt_of_le' (lt_add_of_pos_right (n + 1) (succ_pos k))
(pow_succ_le_ascFactorial n.succ _) (NeZero.pos ((n + 1) ^ (k + 1)))
#align nat.pow_lt_asc_factorial' Nat.pow_lt_ascFactorial'
@@ -320,7 +320,7 @@ theorem ascFactorial_le_pow_add (n : ℕ) : ∀ k : ℕ, (n+1).ascFactorial k
| 0 => by rw [ascFactorial_zero, pow_zero]
| k + 1 => by
rw [ascFactorial_succ, pow_succ, mul_comm, ← add_assoc, add_right_comm n 1 k]
- exact Nat.mul_le_mul_of_nonneg_right
+ exact Nat.mul_le_mul_right _
((ascFactorial_le_pow_add _ k).trans (Nat.pow_le_pow_of_le_left (le_succ _) _))
#align nat.asc_factorial_le_pow_add Nat.ascFactorial_le_pow_add
@@ -329,7 +329,7 @@ theorem ascFactorial_lt_pow_add (n : ℕ) : ∀ {k : ℕ}, 2 ≤ k → (n + 1).a
| 1 => by intro; contradiction
| k + 2 => fun _ => by
rw [pow_succ, mul_comm, ascFactorial_succ, succ_add_eq_add_succ n (k + 1)]
- exact Nat.mul_lt_mul' le_rfl ((ascFactorial_le_pow_add n _).trans_lt
+ exact Nat.mul_lt_mul_of_le_of_lt le_rfl ((ascFactorial_le_pow_add n _).trans_lt
(pow_lt_pow_left (@lt_add_one ℕ _ _ _ _ _ _ _) (zero_le _) k.succ_ne_zero)) (succ_pos _)
#align nat.asc_factorial_lt_pow_add Nat.ascFactorial_lt_pow_add
@@ -437,7 +437,7 @@ theorem pow_sub_le_descFactorial (n : ℕ) : ∀ k : ℕ, (n + 1 - k) ^ k ≤ n.
| 0 => by rw [descFactorial_zero, pow_zero]
| k + 1 => by
rw [descFactorial_succ, pow_succ, succ_sub_succ, mul_comm]
- apply Nat.mul_le_mul_of_nonneg_left
+ apply Nat.mul_le_mul_left
exact (le_trans (Nat.pow_le_pow_left (tsub_le_tsub_right (le_succ _) _) k)
(pow_sub_le_descFactorial n k))
#align nat.pow_sub_le_desc_factorial Nat.pow_sub_le_descFactorial
@@ -479,7 +479,7 @@ theorem descFactorial_lt_pow {n : ℕ} (hn : 1 ≤ n) : ∀ {k : ℕ}, 2 ≤ k
| 1 => by intro; contradiction
| k + 2 => fun _ => by
rw [descFactorial_succ, pow_succ', mul_comm, mul_comm n]
- exact Nat.mul_lt_mul' (descFactorial_le_pow _ _) (tsub_lt_self hn k.zero_lt_succ)
+ exact Nat.mul_lt_mul_of_le_of_lt (descFactorial_le_pow _ _) (tsub_lt_self hn k.zero_lt_succ)
(pow_pos (Nat.lt_of_succ_le hn) _)
#align nat.desc_factorial_lt_pow Nat.descFactorial_lt_pow
Nat
file (#9551)
Data.Nat.Basic
is currently made of two things:
I need the first ones earlier in the algebraic order hierarchy, hence the split.
@@ -3,7 +3,6 @@ Copyright (c) 2018 Mario Carneiro. All rights reserved.
Released under Apache 2.0 license as described in the file LICENSE.
Authors: Mario Carneiro, Chris Hughes, Floris van Doorn, Yaël Dillies
-/
-import Mathlib.Data.Nat.Basic
import Mathlib.Data.Nat.Pow
import Mathlib.Tactic.GCongr.Core
import Mathlib.Tactic.Common
@@ -18,9 +18,10 @@ This file defines the factorial, along with the ascending and descending variant
## Main declarations
* `Nat.factorial`: The factorial.
-* `Nat.ascFactorial`: The ascending factorial. Note that it runs from `n + 1` to `n + k`
- and *not* from `n` to `n + k - 1`. We might want to change that in the future.
-* `Nat.descFactorial`: The descending factorial. It runs from `n - k` to `n`.
+* `Nat.ascFactorial`: The ascending factorial. It is the product of natural numbers from `n` to
+ `n + k - 1`.
+* `Nat.descFactorial`: The descending factorial. It is the product of natural numbers from
+ `n - k + 1` to `n`.
-/
@@ -222,12 +223,11 @@ end Factorial
section AscFactorial
-/-- `n.ascFactorial k = (n + k)! / n!` (as seen in `Nat.ascFactorial_eq_div`), but implemented
-recursively to allow for "quick" computation when using `norm_num`. This is closely related to
-`ascPochhammer`, but much less general. -/
+/-- `n.ascFactorial k = n (n + 1) ⋯ (n + k - 1)`. This is closely related to `ascPochhammer`, but
+much less general. -/
def ascFactorial (n : ℕ) : ℕ → ℕ
| 0 => 1
- | k + 1 => (n + k + 1) * ascFactorial n k
+ | k + 1 => (n + k) * ascFactorial n k
#align nat.asc_factorial Nat.ascFactorial
@[simp]
@@ -235,87 +235,107 @@ theorem ascFactorial_zero (n : ℕ) : n.ascFactorial 0 = 1 :=
rfl
#align nat.asc_factorial_zero Nat.ascFactorial_zero
-@[simp]
-theorem zero_ascFactorial (k : ℕ) : (0 : ℕ).ascFactorial k = k ! := by
- induction' k with t ht
- · rfl
- rw [ascFactorial, ht, zero_add, Nat.factorial_succ]
-#align nat.zero_asc_factorial Nat.zero_ascFactorial
-
-theorem ascFactorial_succ {n k : ℕ} : n.ascFactorial (k + 1) = (n + k + 1) * n.ascFactorial k :=
+theorem ascFactorial_succ {n k : ℕ} : n.ascFactorial k.succ = (n + k) * n.ascFactorial k :=
rfl
#align nat.asc_factorial_succ Nat.ascFactorial_succ
+theorem zero_ascFactorial : ∀ (k : ℕ), (0 : ℕ).ascFactorial k.succ = 0
+ | 0 => by
+ rw [ascFactorial_succ, ascFactorial_zero, zero_add, zero_mul]
+ | (k+1) => by
+ rw [ascFactorial_succ, zero_ascFactorial k, mul_zero]
+
+@[simp]
+theorem one_ascFactorial : ∀ (k : ℕ), (1 : ℕ).ascFactorial k = k.factorial
+ | 0 => ascFactorial_zero 1
+ | (k+1) => by
+ rw [ascFactorial_succ, one_ascFactorial k, add_comm, factorial_succ]
+
theorem succ_ascFactorial (n : ℕ) :
- ∀ k, (n + 1) * n.succ.ascFactorial k = (n + k + 1) * n.ascFactorial k
+ ∀ k, n * n.succ.ascFactorial k = (n + k) * n.ascFactorial k
| 0 => by rw [add_zero, ascFactorial_zero, ascFactorial_zero]
| k + 1 => by
rw [ascFactorial, mul_left_comm, succ_ascFactorial n k, ascFactorial, succ_add, ← add_assoc]
#align nat.succ_asc_factorial Nat.succ_ascFactorial
-/-- `n.ascFactorial k = (n + k)! / n!` but without ℕ-division. See `Nat.ascFactorial_eq_div` for
-the version with ℕ-division. -/
-theorem factorial_mul_ascFactorial (n : ℕ) : ∀ k, n ! * n.ascFactorial k = (n + k)!
- | 0 => by simp
+/-- `(n + 1).ascFactorial k = (n + k) ! / n !` but without ℕ-division. See
+`Nat.ascFactorial_eq_div` for the version with ℕ-division. -/
+theorem factorial_mul_ascFactorial (n : ℕ) : ∀ k, n ! * (n + 1).ascFactorial k = (n + k)!
+ | 0 => by
+ rw [add_zero, ascFactorial_zero, mul_one]
| k + 1 => by
- rw [ascFactorial_succ, mul_left_comm, factorial_mul_ascFactorial n k, ← add_assoc, factorial]
+ rw [ascFactorial_succ, ← add_assoc, factorial_succ, mul_comm (n + 1 + k), ← mul_assoc,
+ factorial_mul_ascFactorial n k, mul_comm, add_right_comm]
#align nat.factorial_mul_asc_factorial Nat.factorial_mul_ascFactorial
+/-- `n.ascFactorial k = (n + k - 1)! / (n - 1)!` for `n > 0` but without ℕ-division. See
+`Nat.ascFactorial_eq_div` for the version with ℕ-division. Consider using
+`factorial_mul_ascFactorial` to avoid complications of ℕ-subtraction. -/
+theorem factorial_mul_ascFactorial' (n k : ℕ) (h : 0 < n) :
+ (n - 1) ! * n.ascFactorial k = (n + k - 1)! := by
+ rw [Nat.sub_add_comm h, Nat.sub_one]
+ nth_rw 2 [Nat.eq_add_of_sub_eq h rfl]
+ rw [Nat.sub_one, factorial_mul_ascFactorial]
+
/-- Avoid in favor of `Nat.factorial_mul_ascFactorial` if you can. ℕ-division isn't worth it. -/
-theorem ascFactorial_eq_div (n k : ℕ) : n.ascFactorial k = (n + k)! / n ! := by
+theorem ascFactorial_eq_div (n k : ℕ) : (n + 1).ascFactorial k = (n + k)! / n ! := by
apply mul_left_cancel₀ n.factorial_ne_zero
rw [factorial_mul_ascFactorial]
- exact (Nat.mul_div_cancel' <| factorial_dvd_factorial <| le.intro rfl).symm
+ exact (Nat.mul_div_cancel_left' <| factorial_dvd_factorial <| le_add_right n k).symm
+
+/-- Avoid in favor of `Nat.factorial_mul_ascFactorial` if you can. -/
+theorem ascFactorial_eq_div' (n k : ℕ) (h : 0 < n) :
+ n.ascFactorial k = (n + k - 1)! / (n - 1) ! := by
+ apply mul_left_cancel₀ (n-1).factorial_ne_zero
+ rw [factorial_mul_ascFactorial' _ _ h]
+ exact (Nat.mul_div_cancel_left' <| factorial_dvd_factorial <| Nat.sub_le_sub_right
+ (le_add_right n k) 1).symm
#align nat.asc_factorial_eq_div Nat.ascFactorial_eq_div
-theorem ascFactorial_of_sub {n k : ℕ} (h : k < n) :
- (n - k) * (n - k).ascFactorial k = (n - (k + 1)).ascFactorial (k + 1) := by
- let t := n - (k + 1)
- suffices h' : n - k = t + 1 by rw [h', succ_ascFactorial, ascFactorial_succ]
- rw [← tsub_tsub_assoc (succ_le_of_lt h) (succ_pos k), succ_sub_one]
+theorem ascFactorial_of_sub {n k : ℕ}:
+ (n - k) * (n - k + 1).ascFactorial k = (n - k).ascFactorial (k + 1) := by
+ rw [succ_ascFactorial, ascFactorial_succ]
#align nat.asc_factorial_of_sub Nat.ascFactorial_of_sub
-theorem pow_succ_le_ascFactorial (n : ℕ) : ∀ k : ℕ, (n + 1) ^ k ≤ n.ascFactorial k
+theorem pow_succ_le_ascFactorial (n : ℕ) : ∀ k : ℕ, n ^ k ≤ n.ascFactorial k
| 0 => by rw [ascFactorial_zero, pow_zero]
| k + 1 => by
- rw [pow_succ, mul_comm]
- exact Nat.mul_le_mul (Nat.add_le_add_right le_self_add _) (pow_succ_le_ascFactorial _ k)
+ rw [pow_succ, mul_comm, ascFactorial_succ, ← succ_ascFactorial]
+ exact Nat.mul_le_mul (Nat.le_refl n)
+ ((pow_le_pow_of_le_left (le_succ n) k).trans (pow_succ_le_ascFactorial n.succ k))
#align nat.pow_succ_le_asc_factorial Nat.pow_succ_le_ascFactorial
-theorem pow_lt_ascFactorial' (n k : ℕ) : (n + 1) ^ (k + 2) < n.ascFactorial (k + 2) := by
+theorem pow_lt_ascFactorial' (n k : ℕ) : (n + 1) ^ (k + 2) < (n + 1).ascFactorial (k + 2) := by
rw [pow_succ, ascFactorial, mul_comm]
- exact
- Nat.mul_lt_mul (Nat.add_lt_add_right (Nat.lt_add_of_pos_right succ_pos') 1)
- (pow_succ_le_ascFactorial n _) (pow_pos succ_pos' _)
+ exact Nat.mul_lt_mul (lt_add_of_pos_right (n + 1) (succ_pos k))
+ (pow_succ_le_ascFactorial n.succ _) (NeZero.pos ((n + 1) ^ (k + 1)))
#align nat.pow_lt_asc_factorial' Nat.pow_lt_ascFactorial'
-theorem pow_lt_ascFactorial (n : ℕ) : ∀ {k : ℕ}, 2 ≤ k → (n + 1) ^ k < n.ascFactorial k
+theorem pow_lt_ascFactorial (n : ℕ) : ∀ {k : ℕ}, 2 ≤ k → (n + 1) ^ k < (n + 1).ascFactorial k
| 0 => by rintro ⟨⟩
| 1 => by intro; contradiction
| k + 2 => fun _ => pow_lt_ascFactorial' n k
#align nat.pow_lt_asc_factorial Nat.pow_lt_ascFactorial
-theorem ascFactorial_le_pow_add (n : ℕ) : ∀ k : ℕ, n.ascFactorial k ≤ (n + k) ^ k
+theorem ascFactorial_le_pow_add (n : ℕ) : ∀ k : ℕ, (n+1).ascFactorial k ≤ (n + k) ^ k
| 0 => by rw [ascFactorial_zero, pow_zero]
| k + 1 => by
- rw [ascFactorial_succ, pow_succ, ← add_assoc, mul_comm _ (succ (n + k))]
- exact
- Nat.mul_le_mul_of_nonneg_left
- ((ascFactorial_le_pow_add _ k).trans (Nat.pow_le_pow_left (le_succ _) _))
+ rw [ascFactorial_succ, pow_succ, mul_comm, ← add_assoc, add_right_comm n 1 k]
+ exact Nat.mul_le_mul_of_nonneg_right
+ ((ascFactorial_le_pow_add _ k).trans (Nat.pow_le_pow_of_le_left (le_succ _) _))
#align nat.asc_factorial_le_pow_add Nat.ascFactorial_le_pow_add
-theorem ascFactorial_lt_pow_add (n : ℕ) : ∀ {k : ℕ}, 2 ≤ k → n.ascFactorial k < (n + k) ^ k
+theorem ascFactorial_lt_pow_add (n : ℕ) : ∀ {k : ℕ}, 2 ≤ k → (n + 1).ascFactorial k < (n + k) ^ k
| 0 => by rintro ⟨⟩
| 1 => by intro; contradiction
| k + 2 => fun _ => by
- rw [ascFactorial_succ, pow_succ]
- rw [add_assoc n (k + 1) 1, mul_comm <| (n + (k + 2)) ^ (k + 1)]
- exact mul_lt_mul_of_pos_left ((ascFactorial_le_pow_add n _).trans_lt <|
- Nat.pow_lt_pow_left (lt_add_one _) k.succ_ne_zero) (succ_pos _)
+ rw [pow_succ, mul_comm, ascFactorial_succ, succ_add_eq_add_succ n (k + 1)]
+ exact Nat.mul_lt_mul' le_rfl ((ascFactorial_le_pow_add n _).trans_lt
+ (pow_lt_pow_left (@lt_add_one ℕ _ _ _ _ _ _ _) (zero_le _) k.succ_ne_zero)) (succ_pos _)
#align nat.asc_factorial_lt_pow_add Nat.ascFactorial_lt_pow_add
-theorem ascFactorial_pos (n k : ℕ) : 0 < n.ascFactorial k :=
- (pow_pos (succ_pos n) k).trans_le (pow_succ_le_ascFactorial n k)
+theorem ascFactorial_pos (n k : ℕ) : 0 < (n + 1).ascFactorial k :=
+ (pow_pos (succ_pos n) k).trans_le (pow_succ_le_ascFactorial (n + 1) k)
#align nat.asc_factorial_pos Nat.ascFactorial_pos
end AscFactorial
@@ -379,13 +399,22 @@ theorem descFactorial_eq_zero_iff_lt {n : ℕ} : ∀ {k : ℕ}, n.descFactorial
alias ⟨_, descFactorial_of_lt⟩ := descFactorial_eq_zero_iff_lt
#align nat.desc_factorial_of_lt Nat.descFactorial_of_lt
-theorem add_descFactorial_eq_ascFactorial (n : ℕ) :
- ∀ k : ℕ, (n + k).descFactorial k = n.ascFactorial k
+theorem add_descFactorial_eq_ascFactorial (n : ℕ) : ∀ k : ℕ,
+ (n + k).descFactorial k = (n + 1).ascFactorial k
| 0 => by rw [ascFactorial_zero, descFactorial_zero]
- | succ k => by rw [Nat.add_succ, succ_descFactorial_succ, ascFactorial_succ,
- add_descFactorial_eq_ascFactorial _ k]
+ | succ k => by
+ rw [Nat.add_succ, succ_descFactorial_succ, ascFactorial_succ,
+ add_descFactorial_eq_ascFactorial _ k, Nat.add_right_comm]
#align nat.add_desc_factorial_eq_asc_factorial Nat.add_descFactorial_eq_ascFactorial
+theorem add_descFactorial_eq_ascFactorial' (n : ℕ) :
+ ∀ k : ℕ, (n + k - 1).descFactorial k = n.ascFactorial k
+ | 0 => by rw [ascFactorial_zero, descFactorial_zero]
+ | succ k => by
+ rw [descFactorial_succ, ascFactorial_succ, ← succ_add_eq_add_succ,
+ add_descFactorial_eq_ascFactorial' _ k, ← succ_ascFactorial, succ_add_sub_one,
+ Nat.add_sub_cancel]
+
/-- `n.descFactorial k = n! / (n - k)!` but without ℕ-division. See `Nat.descFactorial_eq_div`
for the version using ℕ-division. -/
theorem factorial_mul_descFactorial : ∀ {n k : ℕ}, k ≤ n → (n - k)! * n.descFactorial k = n !
@@ -207,6 +207,14 @@ theorem factorial_mul_pow_sub_le_factorial {n m : ℕ} (hnm : n ≤ m) : n ! * n
_ ≤ _ := by simpa [hnm] using @Nat.factorial_mul_pow_le_factorial n (m - n)
#align nat.factorial_mul_pow_sub_le_factorial Nat.factorial_mul_pow_sub_le_factorial
+lemma factorial_le_pow : ∀ n, n ! ≤ n ^ n
+ | 0 => le_rfl
+ | n + 1 =>
+ calc
+ _ ≤ (n + 1) * n ^ n := mul_le_mul_left' n.factorial_le_pow _
+ _ ≤ (n + 1) * (n + 1) ^ n := mul_le_mul_left' (Nat.pow_le_pow_left n.le_succ _) _
+ _ = _ := by rw [pow_succ']
+
end Factorial
/-! ### Ascending and descending factorials -/
$
with <|
(#9319)
See Zulip thread for the discussion.
@@ -302,7 +302,7 @@ theorem ascFactorial_lt_pow_add (n : ℕ) : ∀ {k : ℕ}, 2 ≤ k → n.ascFact
| k + 2 => fun _ => by
rw [ascFactorial_succ, pow_succ]
rw [add_assoc n (k + 1) 1, mul_comm <| (n + (k + 2)) ^ (k + 1)]
- exact mul_lt_mul_of_pos_left ((ascFactorial_le_pow_add n _).trans_lt $
+ exact mul_lt_mul_of_pos_left ((ascFactorial_le_pow_add n _).trans_lt <|
Nat.pow_lt_pow_left (lt_add_one _) k.succ_ne_zero) (succ_pos _)
#align nat.asc_factorial_lt_pow_add Nat.ascFactorial_lt_pow_add
and other basic results. Also include a positivity extension to encode that new result.
From LeanAPAP
@@ -449,4 +449,16 @@ theorem descFactorial_lt_pow {n : ℕ} (hn : 1 ≤ n) : ∀ {k : ℕ}, 2 ≤ k
end DescFactorial
+lemma factorial_two_mul_le (n : ℕ) : (2 * n)! ≤ (2 * n) ^ n * n ! := by
+ rw [two_mul, ← factorial_mul_ascFactorial, mul_comm]
+ exact mul_le_mul_right' (ascFactorial_le_pow_add _ _) _
+
+lemma two_pow_mul_factorial_le_factorial_two_mul (n : ℕ) : 2 ^ n * n ! ≤ (2 * n) ! := by
+ obtain _ | n := n
+ · simp
+ rw [mul_comm, two_mul]
+ calc
+ _ ≤ (n + 1)! * (n + 2) ^ (n + 1) := mul_le_mul_left' (pow_le_pow_of_le_left le_add_self _) _
+ _ ≤ _ := Nat.factorial_mul_pow_le_factorial
+
end Nat
The names for lemmas about monotonicity of (a ^ ·)
and (· ^ n)
were a mess. This PR tidies up everything related by following the naming convention for (a * ·)
and (· * b)
. Namely, (a ^ ·)
is pow_right
and (· ^ n)
is pow_left
in lemma names. All lemma renames follow the corresponding multiplication lemma names closely.
Algebra.GroupPower.Order
pow_mono
→ pow_right_mono
pow_le_pow
→ pow_le_pow_right
pow_le_pow_of_le_left
→ pow_le_pow_left
pow_lt_pow_of_lt_left
→ pow_lt_pow_left
strictMonoOn_pow
→ pow_left_strictMonoOn
pow_strictMono_right
→ pow_right_strictMono
pow_lt_pow
→ pow_lt_pow_right
pow_lt_pow_iff
→ pow_lt_pow_iff_right
pow_le_pow_iff
→ pow_le_pow_iff_right
self_lt_pow
→ lt_self_pow
strictAnti_pow
→ pow_right_strictAnti
pow_lt_pow_iff_of_lt_one
→ pow_lt_pow_iff_right_of_lt_one
pow_lt_pow_of_lt_one
→ pow_lt_pow_right_of_lt_one
lt_of_pow_lt_pow
→ lt_of_pow_lt_pow_left
le_of_pow_le_pow
→ le_of_pow_le_pow_left
pow_lt_pow₀
→ pow_lt_pow_right₀
Algebra.GroupPower.CovariantClass
pow_le_pow_of_le_left'
→ pow_le_pow_left'
nsmul_le_nsmul_of_le_right
→ nsmul_le_nsmul_right
pow_lt_pow'
→ pow_lt_pow_right'
nsmul_lt_nsmul
→ nsmul_lt_nsmul_left
pow_strictMono_left
→ pow_right_strictMono'
nsmul_strictMono_right
→ nsmul_left_strictMono
StrictMono.pow_right'
→ StrictMono.pow_const
StrictMono.nsmul_left
→ StrictMono.const_nsmul
pow_strictMono_right'
→ pow_left_strictMono
nsmul_strictMono_left
→ nsmul_right_strictMono
Monotone.pow_right
→ Monotone.pow_const
Monotone.nsmul_left
→ Monotone.const_nsmul
lt_of_pow_lt_pow'
→ lt_of_pow_lt_pow_left'
lt_of_nsmul_lt_nsmul
→ lt_of_nsmul_lt_nsmul_right
pow_le_pow'
→ pow_le_pow_right'
nsmul_le_nsmul
→ nsmul_le_nsmul_left
pow_le_pow_of_le_one'
→ pow_le_pow_right_of_le_one'
nsmul_le_nsmul_of_nonpos
→ nsmul_le_nsmul_left_of_nonpos
le_of_pow_le_pow'
→ le_of_pow_le_pow_left'
le_of_nsmul_le_nsmul'
→ le_of_nsmul_le_nsmul_right'
pow_le_pow_iff'
→ pow_le_pow_iff_right'
nsmul_le_nsmul_iff
→ nsmul_le_nsmul_iff_left
pow_lt_pow_iff'
→ pow_lt_pow_iff_right'
nsmul_lt_nsmul_iff
→ nsmul_lt_nsmul_iff_left
Data.Nat.Pow
Nat.pow_lt_pow_of_lt_left
→ Nat.pow_lt_pow_left
Nat.pow_le_iff_le_left
→ Nat.pow_le_pow_iff_left
Nat.pow_lt_iff_lt_left
→ Nat.pow_lt_pow_iff_left
pow_le_pow_iff_left
pow_lt_pow_iff_left
pow_right_injective
pow_right_inj
Nat.pow_le_pow_left
to have the correct name since Nat.pow_le_pow_of_le_left
is in Std.Nat.pow_le_pow_right
to have the correct name since Nat.pow_le_pow_of_le_right
is in Std.self_le_pow
was a duplicate of le_self_pow
.Nat.pow_lt_pow_of_lt_right
is defeq to pow_lt_pow_right
.Nat.pow_right_strictMono
is defeq to pow_right_strictMono
.Nat.pow_le_iff_le_right
is defeq to pow_le_pow_iff_right
.Nat.pow_lt_iff_lt_right
is defeq to pow_lt_pow_iff_right
.0 < n
or 1 ≤ n
to n ≠ 0
.Nat
lemmas have been protected
.@@ -202,13 +202,9 @@ theorem add_factorial_le_factorial_add (i : ℕ) {n : ℕ} (n1 : 1 ≤ n) : i +
#align nat.add_factorial_le_factorial_add Nat.add_factorial_le_factorial_add
theorem factorial_mul_pow_sub_le_factorial {n m : ℕ} (hnm : n ≤ m) : n ! * n ^ (m - n) ≤ m ! := by
- suffices n ! * (n + 1) ^ (m - n) ≤ m ! from by
- apply LE.le.trans _ this
- apply mul_le_mul_left
- apply pow_le_pow_of_le_left (le_succ n)
- have := @Nat.factorial_mul_pow_le_factorial n (m - n)
- simp? [hnm] at this says simp only [ge_iff_le, hnm, add_tsub_cancel_of_le] at this
- exact this
+ calc
+ _ ≤ n ! * (n + 1) ^ (m - n) := mul_le_mul_left' (Nat.pow_le_pow_left n.le_succ _) _
+ _ ≤ _ := by simpa [hnm] using @Nat.factorial_mul_pow_le_factorial n (m - n)
#align nat.factorial_mul_pow_sub_le_factorial Nat.factorial_mul_pow_sub_le_factorial
end Factorial
@@ -297,7 +293,7 @@ theorem ascFactorial_le_pow_add (n : ℕ) : ∀ k : ℕ, n.ascFactorial k ≤ (n
rw [ascFactorial_succ, pow_succ, ← add_assoc, mul_comm _ (succ (n + k))]
exact
Nat.mul_le_mul_of_nonneg_left
- ((ascFactorial_le_pow_add _ k).trans (Nat.pow_le_pow_of_le_left (le_succ _) _))
+ ((ascFactorial_le_pow_add _ k).trans (Nat.pow_le_pow_left (le_succ _) _))
#align nat.asc_factorial_le_pow_add Nat.ascFactorial_le_pow_add
theorem ascFactorial_lt_pow_add (n : ℕ) : ∀ {k : ℕ}, 2 ≤ k → n.ascFactorial k < (n + k) ^ k
@@ -306,11 +302,8 @@ theorem ascFactorial_lt_pow_add (n : ℕ) : ∀ {k : ℕ}, 2 ≤ k → n.ascFact
| k + 2 => fun _ => by
rw [ascFactorial_succ, pow_succ]
rw [add_assoc n (k + 1) 1, mul_comm <| (n + (k + 2)) ^ (k + 1)]
- refine'
- Nat.mul_lt_mul' le_rfl
- ((ascFactorial_le_pow_add n _).trans_lt
- (pow_lt_pow_of_lt_left (lt_add_one _) (succ_pos _)))
- (succ_pos _)
+ exact mul_lt_mul_of_pos_left ((ascFactorial_le_pow_add n _).trans_lt $
+ Nat.pow_lt_pow_left (lt_add_one _) k.succ_ne_zero) (succ_pos _)
#align nat.asc_factorial_lt_pow_add Nat.ascFactorial_lt_pow_add
theorem ascFactorial_pos (n k : ℕ) : 0 < n.ascFactorial k :=
@@ -409,7 +402,7 @@ theorem pow_sub_le_descFactorial (n : ℕ) : ∀ k : ℕ, (n + 1 - k) ^ k ≤ n.
| k + 1 => by
rw [descFactorial_succ, pow_succ, succ_sub_succ, mul_comm]
apply Nat.mul_le_mul_of_nonneg_left
- exact (le_trans (Nat.pow_le_pow_of_le_left (tsub_le_tsub_right (le_succ _) _) k)
+ exact (le_trans (Nat.pow_le_pow_left (tsub_le_tsub_right (le_succ _) _) k)
(pow_sub_le_descFactorial n k))
#align nat.pow_sub_le_desc_factorial Nat.pow_sub_le_descFactorial
@@ -423,7 +416,7 @@ theorem pow_sub_lt_descFactorial' {n : ℕ} :
| k + 1 => fun h => by
rw [descFactorial_succ, pow_succ, mul_comm]
apply Nat.mul_lt_mul_of_pos_left
- · refine' ((Nat.pow_le_pow_of_le_left (tsub_le_tsub_right (le_succ n) _) _).trans_lt _)
+ · refine' ((Nat.pow_le_pow_left (tsub_le_tsub_right (le_succ n) _) _).trans_lt _)
rw [succ_sub_succ]
exact pow_sub_lt_descFactorial' ((le_succ _).trans h)
· apply tsub_pos_of_lt; apply h
@@ -207,7 +207,7 @@ theorem factorial_mul_pow_sub_le_factorial {n m : ℕ} (hnm : n ≤ m) : n ! * n
apply mul_le_mul_left
apply pow_le_pow_of_le_left (le_succ n)
have := @Nat.factorial_mul_pow_le_factorial n (m - n)
- simp [hnm] at this
+ simp? [hnm] at this says simp only [ge_iff_le, hnm, add_tsub_cancel_of_le] at this
exact this
#align nat.factorial_mul_pow_sub_le_factorial Nat.factorial_mul_pow_sub_le_factorial
Nat.Factorial.Basic
(#8422)
Order.Concept
.@@ -39,23 +39,20 @@ section Factorial
variable {m n : ℕ}
-@[simp]
-theorem factorial_zero : 0! = 1 :=
+@[simp] theorem factorial_zero : 0! = 1 :=
rfl
#align nat.factorial_zero Nat.factorial_zero
-theorem factorial_succ (n : ℕ) : n.succ ! = (n + 1) * n ! :=
+theorem factorial_succ (n : ℕ) : (n + 1)! = (n + 1) * n ! :=
rfl
#align nat.factorial_succ Nat.factorial_succ
--- Porting note: can be proved by simp, @[simp] removed
-theorem factorial_one : 1! = 1 :=
+@[simp] theorem factorial_one : 1! = 1 :=
rfl
#align nat.factorial_one Nat.factorial_one
--- Porting note: can be proved by simp, @[simp] removed
-theorem factorial_two : 2! = 2 :=
+@[simp] theorem factorial_two : 2! = 2 :=
rfl
#align nat.factorial_two Nat.factorial_two
@@ -84,31 +81,24 @@ theorem dvd_factorial : ∀ {m n}, 0 < m → m ≤ n → m ∣ n !
| succ _, _, _, h => dvd_of_mul_right_dvd (factorial_dvd_factorial h)
#align nat.dvd_factorial Nat.dvd_factorial
-@[mono]
+@[mono, gcongr]
theorem factorial_le {m n} (h : m ≤ n) : m ! ≤ n ! :=
le_of_dvd (factorial_pos _) (factorial_dvd_factorial h)
#align nat.factorial_le Nat.factorial_le
--- Porting note: Interconversion between `succ` and `· + 1` has to be done manually
-theorem factorial_mul_pow_le_factorial : ∀ {m n : ℕ}, m ! * m.succ ^ n ≤ (m + n)!
+theorem factorial_mul_pow_le_factorial : ∀ {m n : ℕ}, m ! * (m + 1) ^ n ≤ (m + n)!
| m, 0 => by simp
| m, n + 1 => by
- rw [← add_assoc, ← Nat.succ_eq_add_one (m + n), Nat.factorial_succ, pow_succ',
- mul_comm (_ + 1), mul_comm (succ m), ← mul_assoc]
- exact
- mul_le_mul factorial_mul_pow_le_factorial (Nat.succ_le_succ (Nat.le_add_right _ _))
- (Nat.zero_le _) (Nat.zero_le _)
+ rw [← add_assoc, factorial_succ, mul_comm (_ + 1), pow_succ, ← mul_assoc]
+ exact Nat.mul_le_mul factorial_mul_pow_le_factorial (succ_le_succ (le_add_right _ _))
#align nat.factorial_mul_pow_le_factorial Nat.factorial_mul_pow_le_factorial
theorem monotone_factorial : Monotone factorial := fun _ _ => factorial_le
#align nat.monotone_factorial Nat.monotone_factorial
-@[gcongr]
-lemma factorial_le_of_le {m n : ℕ} (h : n ≤ m) : n ! ≤ m ! := monotone_factorial h
-
theorem factorial_lt (hn : 0 < n) : n ! < m ! ↔ n < m := by
refine' ⟨fun h => not_le.mp fun hmn => not_le_of_lt h (factorial_le hmn), fun h => _⟩
- have : ∀ {n}, 0 < n → n ! < n.succ ! := by
+ have : ∀ {n}, 0 < n → n ! < (n + 1)! := by
intro k hk
rw [factorial_succ, succ_mul, lt_add_iff_pos_left]
exact mul_pos hk k.factorial_pos
@@ -120,40 +110,43 @@ theorem factorial_lt (hn : 0 < n) : n ! < m ! ↔ n < m := by
@[gcongr]
lemma factorial_lt_of_lt {m n : ℕ} (hn : 0 < n) (h : n < m) : n ! < m ! := (factorial_lt hn).mpr h
+@[simp]
theorem one_lt_factorial : 1 < n ! ↔ 1 < n :=
factorial_lt one_pos
#align nat.one_lt_factorial Nat.one_lt_factorial
--- Porting note: `(_ | _)` notation for introduction with cases does not appear to be supported
+@[simp]
theorem factorial_eq_one : n ! = 1 ↔ n ≤ 1 := by
- apply Iff.intro <;> intro
- · rw [← not_lt, ← one_lt_factorial, ‹n ! = 1›]
+ constructor
+ · intro h
+ rw [← not_lt, ← one_lt_factorial, h]
apply lt_irrefl
- · cases ‹n ≤ 1›
- · rfl
- · cases ‹n ≤ 0›; rfl
+ · rintro (_|_|_) <;> rfl
#align nat.factorial_eq_one Nat.factorial_eq_one
-theorem factorial_inj (hn : 1 < n !) : n ! = m ! ↔ n = m := by
+theorem factorial_inj (hn : 1 < n) : n ! = m ! ↔ n = m := by
refine' ⟨fun h => _, congr_arg _⟩
obtain hnm | rfl | hnm := lt_trichotomy n m
- · rw [← factorial_lt <| pos_of_gt <| one_lt_factorial.mp hn, h] at hnm
+ · rw [← factorial_lt <| pos_of_gt hn, h] at hnm
cases lt_irrefl _ hnm
· rfl
- rw [h, one_lt_factorial] at hn
- rw [← factorial_lt (lt_trans one_pos hn), h] at hnm
+ rw [← one_lt_factorial, h, one_lt_factorial] at hn
+ rw [← factorial_lt <| pos_of_gt hn, h] at hnm
cases lt_irrefl _ hnm
#align nat.factorial_inj Nat.factorial_inj
+theorem factorial_inj' (h : 1 < n ∨ 1 < m) : n ! = m ! ↔ n = m := by
+ obtain hn|hm := h
+ · exact factorial_inj hn
+ · rw [eq_comm, factorial_inj hm, eq_comm]
+
theorem self_le_factorial : ∀ n : ℕ, n ≤ n !
| 0 => zero_le_one
| k + 1 => le_mul_of_one_le_right k.zero_lt_succ.le (Nat.one_le_of_lt <| Nat.factorial_pos _)
#align nat.self_le_factorial Nat.self_le_factorial
--- Porting note: `zero_lt_two` does not work since `ZeroLEOneClass` fails to be synthesised.
--- Porting note: `0 < 2` is proved `by decide` instead
theorem lt_factorial_self {n : ℕ} (hi : 3 ≤ n) : n < n ! := by
- have : 0 < n := (by decide : 0 < 2).trans (succ_le_iff.mp hi)
+ have : 0 < n := (zero_lt_two (α := ℕ)).trans (succ_le_iff.mp hi)
have : 1 < pred n := le_pred_of_lt (succ_le_iff.mp hi)
rw [← succ_pred_eq_of_pos ‹0 < n›, factorial_succ]
exact
@@ -163,7 +156,7 @@ theorem lt_factorial_self {n : ℕ} (hi : 3 ≤ n) : n < n ! := by
theorem add_factorial_succ_lt_factorial_add_succ {i : ℕ} (n : ℕ) (hi : 2 ≤ i) :
i + (n + 1)! < (i + n + 1)! := by
- rw [← Nat.succ_eq_add_one (i + _), factorial_succ (i + _), add_mul, one_mul]
+ rw [factorial_succ (i + _), add_mul, one_mul]
have : i ≤ i + n := le.intro rfl
exact
add_lt_add_of_lt_of_le
@@ -195,8 +188,7 @@ theorem add_factorial_succ_le_factorial_add_succ (i : ℕ) (n : ℕ) :
· match i with
| 0 => simp
| 1 =>
- rw [← add_assoc, ← Nat.succ_eq_add_one (1 + n), factorial_succ (1 + n),
- add_mul, one_mul, add_comm 1 n, add_le_add_iff_right]
+ rw [← add_assoc, factorial_succ (1 + n), add_mul, one_mul, add_comm 1 n, add_le_add_iff_right]
apply one_le_mul
· apply Nat.le_add_left
· apply factorial_pos
@@ -246,28 +238,23 @@ theorem zero_ascFactorial (k : ℕ) : (0 : ℕ).ascFactorial k = k ! := by
rw [ascFactorial, ht, zero_add, Nat.factorial_succ]
#align nat.zero_asc_factorial Nat.zero_ascFactorial
-theorem ascFactorial_succ {n k : ℕ} : n.ascFactorial k.succ = (n + k + 1) * n.ascFactorial k :=
+theorem ascFactorial_succ {n k : ℕ} : n.ascFactorial (k + 1) = (n + k + 1) * n.ascFactorial k :=
rfl
#align nat.asc_factorial_succ Nat.ascFactorial_succ
--- Porting note: Explicit arguments are required to show that the recursion terminates
theorem succ_ascFactorial (n : ℕ) :
∀ k, (n + 1) * n.succ.ascFactorial k = (n + k + 1) * n.ascFactorial k
| 0 => by rw [add_zero, ascFactorial_zero, ascFactorial_zero]
| k + 1 => by
- rw [ascFactorial, mul_left_comm, succ_ascFactorial n k, ascFactorial,
- succ_add, ← add_assoc, succ_eq_add_one]
+ rw [ascFactorial, mul_left_comm, succ_ascFactorial n k, ascFactorial, succ_add, ← add_assoc]
#align nat.succ_asc_factorial Nat.succ_ascFactorial
/-- `n.ascFactorial k = (n + k)! / n!` but without ℕ-division. See `Nat.ascFactorial_eq_div` for
the version with ℕ-division. -/
--- Porting note: Explicit arguments are required to show that the recursion terminates
--- Porting note: Interconversion between `succ` and `· + 1` has to be done manually
theorem factorial_mul_ascFactorial (n : ℕ) : ∀ k, n ! * n.ascFactorial k = (n + k)!
- | 0 => by rw [ascFactorial, add_zero, mul_one]
+ | 0 => by simp
| k + 1 => by
- rw [ascFactorial_succ, mul_left_comm, factorial_mul_ascFactorial n k,
- ← add_assoc, ← Nat.succ_eq_add_one (n + k), factorial]
+ rw [ascFactorial_succ, mul_left_comm, factorial_mul_ascFactorial n k, ← add_assoc, factorial]
#align nat.factorial_mul_asc_factorial Nat.factorial_mul_ascFactorial
/-- Avoid in favor of `Nat.factorial_mul_ascFactorial` if you can. ℕ-division isn't worth it. -/
@@ -279,10 +266,9 @@ theorem ascFactorial_eq_div (n k : ℕ) : n.ascFactorial k = (n + k)! / n ! := b
theorem ascFactorial_of_sub {n k : ℕ} (h : k < n) :
(n - k) * (n - k).ascFactorial k = (n - (k + 1)).ascFactorial (k + 1) := by
- let t := n - k.succ
- let ht : t = n - k.succ := rfl
- suffices h' : n - k = t.succ by rw [← ht, h', succ_ascFactorial, ascFactorial_succ]
- rw [ht, succ_eq_add_one, ← tsub_tsub_assoc (succ_le_of_lt h) (succ_pos _), succ_sub_one]
+ let t := n - (k + 1)
+ suffices h' : n - k = t + 1 by rw [h', succ_ascFactorial, ascFactorial_succ]
+ rw [← tsub_tsub_assoc (succ_le_of_lt h) (succ_pos k), succ_sub_one]
#align nat.asc_factorial_of_sub Nat.ascFactorial_of_sub
theorem pow_succ_le_ascFactorial (n : ℕ) : ∀ k : ℕ, (n + 1) ^ k ≤ n.ascFactorial k
@@ -308,8 +294,7 @@ theorem pow_lt_ascFactorial (n : ℕ) : ∀ {k : ℕ}, 2 ≤ k → (n + 1) ^ k <
theorem ascFactorial_le_pow_add (n : ℕ) : ∀ k : ℕ, n.ascFactorial k ≤ (n + k) ^ k
| 0 => by rw [ascFactorial_zero, pow_zero]
| k + 1 => by
- rw [ascFactorial_succ, pow_succ, ← add_assoc,
- ← Nat.succ_eq_add_one (n + k), mul_comm _ (succ (n + k))]
+ rw [ascFactorial_succ, pow_succ, ← add_assoc, mul_comm _ (succ (n + k))]
exact
Nat.mul_le_mul_of_nonneg_left
((ascFactorial_le_pow_add _ k).trans (Nat.pow_le_pow_of_le_left (le_succ _) _))
@@ -350,32 +335,17 @@ theorem descFactorial_zero (n : ℕ) : n.descFactorial 0 = 1 :=
#align nat.desc_factorial_zero Nat.descFactorial_zero
@[simp]
-theorem descFactorial_succ (n k : ℕ) : n.descFactorial k.succ = (n - k) * n.descFactorial k :=
+theorem descFactorial_succ (n k : ℕ) : n.descFactorial (k + 1) = (n - k) * n.descFactorial k :=
rfl
#align nat.desc_factorial_succ Nat.descFactorial_succ
-theorem zero_descFactorial_succ (k : ℕ) : (0 : ℕ).descFactorial k.succ = 0 := by
+theorem zero_descFactorial_succ (k : ℕ) : (0 : ℕ).descFactorial (k + 1) = 0 := by
rw [descFactorial_succ, zero_tsub, zero_mul]
#align nat.zero_desc_factorial_succ Nat.zero_descFactorial_succ
-/- Porting note: simp removed because this can be proved by
-simp only [Nat.descFactorial_succ, nonpos_iff_eq_zero, tsub_zero, Nat.descFactorial_zero, mul_one]
--/
--- @[simp]
-theorem descFactorial_one (n : ℕ) : n.descFactorial 1 = n := by
- rw [descFactorial_succ, descFactorial_zero, mul_one, tsub_zero]
+theorem descFactorial_one (n : ℕ) : n.descFactorial 1 = n := by simp
#align nat.desc_factorial_one Nat.descFactorial_one
-/- Porting note: simp removed because the lhs simplifies,
-according to the linter:
-Left-hand side simplifies from
- Nat.descFactorial (n + 1) (k + 1)
-to
- (n + 1 - k) * Nat.descFactorial (n + 1) k
-using
- simp only [Nat.descFactorial_succ]
--/
--- @[simp]
theorem succ_descFactorial_succ (n : ℕ) :
∀ k : ℕ, (n + 1).descFactorial (k + 1) = (n + 1) * n.descFactorial k
| 0 => by rw [descFactorial_zero, descFactorial_one, mul_one]
@@ -411,9 +381,8 @@ alias ⟨_, descFactorial_of_lt⟩ := descFactorial_eq_zero_iff_lt
theorem add_descFactorial_eq_ascFactorial (n : ℕ) :
∀ k : ℕ, (n + k).descFactorial k = n.ascFactorial k
| 0 => by rw [ascFactorial_zero, descFactorial_zero]
- | succ k => by
- rw [Nat.add_succ, Nat.succ_eq_add_one, Nat.succ_eq_add_one,
- succ_descFactorial_succ, ascFactorial_succ, add_descFactorial_eq_ascFactorial _ k]
+ | succ k => by rw [Nat.add_succ, succ_descFactorial_succ, ascFactorial_succ,
+ add_descFactorial_eq_ascFactorial _ k]
#align nat.add_desc_factorial_eq_asc_factorial Nat.add_descFactorial_eq_ascFactorial
/-- `n.descFactorial k = n! / (n - k)!` but without ℕ-division. See `Nat.descFactorial_eq_div`
@@ -338,7 +338,7 @@ section DescFactorial
/-- `n.descFactorial k = n! / (n - k)!` (as seen in `Nat.descFactorial_eq_div`), but
implemented recursively to allow for "quick" computation when using `norm_num`. This is closely
-related to `ascPochhammer`, but much less general. -/
+related to `descPochhammer`, but much less general. -/
def descFactorial (n : ℕ) : ℕ → ℕ
| 0 => 1
| k + 1 => (n - k) * descFactorial n k
@@ -27,7 +27,6 @@ This file defines the factorial, along with the ascending and descending variant
namespace Nat
/-- `Nat.factorial n` is the factorial of `n`. -/
-@[simp]
def factorial : ℕ → ℕ
| 0 => 1
| succ n => succ n * factorial n
@@ -229,7 +229,7 @@ section AscFactorial
/-- `n.ascFactorial k = (n + k)! / n!` (as seen in `Nat.ascFactorial_eq_div`), but implemented
recursively to allow for "quick" computation when using `norm_num`. This is closely related to
-`pochhammer`, but much less general. -/
+`ascPochhammer`, but much less general. -/
def ascFactorial (n : ℕ) : ℕ → ℕ
| 0 => 1
| k + 1 => (n + k + 1) * ascFactorial n k
@@ -339,7 +339,7 @@ section DescFactorial
/-- `n.descFactorial k = n! / (n - k)!` (as seen in `Nat.descFactorial_eq_div`), but
implemented recursively to allow for "quick" computation when using `norm_num`. This is closely
-related to `pochhammer`, but much less general. -/
+related to `ascPochhammer`, but much less general. -/
def descFactorial (n : ℕ) : ℕ → ℕ
| 0 => 1
| k + 1 => (n - k) * descFactorial n k
Many proofs use the "stream of consciousness" style from Lean 3, rather than have ... :=
or suffices ... from/by
.
This PR updates a fraction of these to the preferred Lean 4 style.
I think a good goal would be to delete the "deferred" versions of have
, suffices
, and let
at the bottom of Mathlib.Tactic.Have
(Anyone who would like to contribute more cleanup is welcome to push directly to this branch.)
Co-authored-by: Scott Morrison <scott.morrison@gmail.com>
@@ -282,7 +282,7 @@ theorem ascFactorial_of_sub {n k : ℕ} (h : k < n) :
(n - k) * (n - k).ascFactorial k = (n - (k + 1)).ascFactorial (k + 1) := by
let t := n - k.succ
let ht : t = n - k.succ := rfl
- suffices h' : n - k = t.succ; · rw [← ht, h', succ_ascFactorial, ascFactorial_succ]
+ suffices h' : n - k = t.succ by rw [← ht, h', succ_ascFactorial, ascFactorial_succ]
rw [ht, succ_eq_add_one, ← tsub_tsub_assoc (succ_le_of_lt h) (succ_pos _), succ_sub_one]
#align nat.asc_factorial_of_sub Nat.ascFactorial_of_sub
I know that this is contrary to what we've done previously, but:
norm_num
/ ring
/ linarith
)(Oh
Co-authored-by: Scott Morrison <scott.morrison@gmail.com>
@@ -6,6 +6,7 @@ Authors: Mario Carneiro, Chris Hughes, Floris van Doorn, Yaël Dillies
import Mathlib.Data.Nat.Basic
import Mathlib.Data.Nat.Pow
import Mathlib.Tactic.GCongr.Core
+import Mathlib.Tactic.Common
#align_import data.nat.factorial.basic from "leanprover-community/mathlib"@"d012cd09a9b256d870751284dd6a29882b0be105"
@@ -44,7 +44,6 @@ theorem factorial_zero : 0! = 1 :=
rfl
#align nat.factorial_zero Nat.factorial_zero
-@[simp]
theorem factorial_succ (n : ℕ) : n.succ ! = (n + 1) * n ! :=
rfl
#align nat.factorial_succ Nat.factorial_succ
@@ -406,7 +406,7 @@ theorem descFactorial_eq_zero_iff_lt {n : ℕ} : ∀ {k : ℕ}, n.descFactorial
exact fun h _ => h
#align nat.desc_factorial_eq_zero_iff_lt Nat.descFactorial_eq_zero_iff_lt
-alias descFactorial_eq_zero_iff_lt ↔ _ descFactorial_of_lt
+alias ⟨_, descFactorial_of_lt⟩ := descFactorial_eq_zero_iff_lt
#align nat.desc_factorial_of_lt Nat.descFactorial_of_lt
theorem add_descFactorial_eq_ascFactorial (n : ℕ) :
@@ -2,16 +2,13 @@
Copyright (c) 2018 Mario Carneiro. All rights reserved.
Released under Apache 2.0 license as described in the file LICENSE.
Authors: Mario Carneiro, Chris Hughes, Floris van Doorn, Yaël Dillies
-
-! This file was ported from Lean 3 source module data.nat.factorial.basic
-! leanprover-community/mathlib commit d012cd09a9b256d870751284dd6a29882b0be105
-! Please do not edit these lines, except to modify the commit id
-! if you have ported upstream changes.
-/
import Mathlib.Data.Nat.Basic
import Mathlib.Data.Nat.Pow
import Mathlib.Tactic.GCongr.Core
+#align_import data.nat.factorial.basic from "leanprover-community/mathlib"@"d012cd09a9b256d870751284dd6a29882b0be105"
+
/-!
# Factorial and variants
Rewrite the IMO 2019 q4 solution to make the "implicit" calc blocks (lots of lt_of_le_of_lt
) explicit, then automate some proofs.
This is not a golf in the sense of decreasing the number of lines (maybe it is if you take into account the number of lines like
intros; rw [sub_nonneg]; apply pow_le_pow; norm_num; apply le_of_lt; rwa [← mem_range]
in the original). So, if desired, I can make this an additional proof rather than a replacement to the existing proof.
@@ -10,6 +10,7 @@ Authors: Mario Carneiro, Chris Hughes, Floris van Doorn, Yaël Dillies
-/
import Mathlib.Data.Nat.Basic
import Mathlib.Data.Nat.Pow
+import Mathlib.Tactic.GCongr.Core
/-!
# Factorial and variants
@@ -106,6 +107,9 @@ theorem factorial_mul_pow_le_factorial : ∀ {m n : ℕ}, m ! * m.succ ^ n ≤ (
theorem monotone_factorial : Monotone factorial := fun _ _ => factorial_le
#align nat.monotone_factorial Nat.monotone_factorial
+@[gcongr]
+lemma factorial_le_of_le {m n : ℕ} (h : n ≤ m) : n ! ≤ m ! := monotone_factorial h
+
theorem factorial_lt (hn : 0 < n) : n ! < m ! ↔ n < m := by
refine' ⟨fun h => not_le.mp fun hmn => not_le_of_lt h (factorial_le hmn), fun h => _⟩
have : ∀ {n}, 0 < n → n ! < n.succ ! := by
@@ -117,6 +121,9 @@ theorem factorial_lt (hn : 0 < n) : n ! < m ! ↔ n < m := by
· exact (ih hn).trans (this <| hn.trans <| lt_of_succ_le hnk)
#align nat.factorial_lt Nat.factorial_lt
+@[gcongr]
+lemma factorial_lt_of_lt {m n : ℕ} (hn : 0 < n) (h : n < m) : n ! < m ! := (factorial_lt hn).mpr h
+
theorem one_lt_factorial : 1 < n ! ↔ 1 < n :=
factorial_lt one_pos
#align nat.one_lt_factorial Nat.one_lt_factorial
This is an extremely partial port of the mono*
tactic from Lean 3, implemented as a macro on top of solve_by_elim
. The original mono
had many configuration options and no documentation, so quite a bit is missing (and almost all the Lean 3 tests fail). Nonetheless I think it's worth merging this, because
@[mono]
mono
will succeed fairly often in the port even though it fails nearly all the testsCo-authored-by: thorimur <68410468+thorimur@users.noreply.github.com>
@@ -87,7 +87,7 @@ theorem dvd_factorial : ∀ {m n}, 0 < m → m ≤ n → m ∣ n !
| succ _, _, _, h => dvd_of_mul_right_dvd (factorial_dvd_factorial h)
#align nat.dvd_factorial Nat.dvd_factorial
--- Porting note: `mono` not yet implemented @[mono]
+@[mono]
theorem factorial_le {m n} (h : m ≤ n) : m ! ≤ n ! :=
le_of_dvd (factorial_pos _) (factorial_dvd_factorial h)
#align nat.factorial_le Nat.factorial_le
This PR is the result of a slight variant on the following "algorithm"
_
and make all uppercase letters into lowercase_
and make all uppercase letters into lowercase(original_lean3_name, OriginalLean4Name)
#align
statement just before the next empty line#align
statement to have been inserted too early)@@ -403,6 +403,7 @@ theorem descFactorial_eq_zero_iff_lt {n : ℕ} : ∀ {k : ℕ}, n.descFactorial
#align nat.desc_factorial_eq_zero_iff_lt Nat.descFactorial_eq_zero_iff_lt
alias descFactorial_eq_zero_iff_lt ↔ _ descFactorial_of_lt
+#align nat.desc_factorial_of_lt Nat.descFactorial_of_lt
theorem add_descFactorial_eq_ascFactorial (n : ℕ) :
∀ k : ℕ, (n + k).descFactorial k = n.ascFactorial k
Implements a linter for lean 3 declarations containing capital letters (as suggested on Zulip).
Co-authored-by: Mario Carneiro <di.gama@gmail.com>
@@ -410,7 +410,7 @@ theorem add_descFactorial_eq_ascFactorial (n : ℕ) :
| succ k => by
rw [Nat.add_succ, Nat.succ_eq_add_one, Nat.succ_eq_add_one,
succ_descFactorial_succ, ascFactorial_succ, add_descFactorial_eq_ascFactorial _ k]
-#align nat.add_descFactorial_eq_asc_factorial Nat.add_descFactorial_eq_ascFactorial
+#align nat.add_desc_factorial_eq_asc_factorial Nat.add_descFactorial_eq_ascFactorial
/-- `n.descFactorial k = n! / (n - k)!` but without ℕ-division. See `Nat.descFactorial_eq_div`
for the version using ℕ-division. -/
@@ -229,23 +229,23 @@ recursively to allow for "quick" computation when using `norm_num`. This is clos
def ascFactorial (n : ℕ) : ℕ → ℕ
| 0 => 1
| k + 1 => (n + k + 1) * ascFactorial n k
-#align nat.ascFactorial Nat.ascFactorial
+#align nat.asc_factorial Nat.ascFactorial
@[simp]
theorem ascFactorial_zero (n : ℕ) : n.ascFactorial 0 = 1 :=
rfl
-#align nat.ascFactorial_zero Nat.ascFactorial_zero
+#align nat.asc_factorial_zero Nat.ascFactorial_zero
@[simp]
theorem zero_ascFactorial (k : ℕ) : (0 : ℕ).ascFactorial k = k ! := by
induction' k with t ht
· rfl
rw [ascFactorial, ht, zero_add, Nat.factorial_succ]
-#align nat.zero_ascFactorial Nat.zero_ascFactorial
+#align nat.zero_asc_factorial Nat.zero_ascFactorial
theorem ascFactorial_succ {n k : ℕ} : n.ascFactorial k.succ = (n + k + 1) * n.ascFactorial k :=
rfl
-#align nat.ascFactorial_succ Nat.ascFactorial_succ
+#align nat.asc_factorial_succ Nat.ascFactorial_succ
-- Porting note: Explicit arguments are required to show that the recursion terminates
theorem succ_ascFactorial (n : ℕ) :
@@ -254,7 +254,7 @@ theorem succ_ascFactorial (n : ℕ) :
| k + 1 => by
rw [ascFactorial, mul_left_comm, succ_ascFactorial n k, ascFactorial,
succ_add, ← add_assoc, succ_eq_add_one]
-#align nat.succ_ascFactorial Nat.succ_ascFactorial
+#align nat.succ_asc_factorial Nat.succ_ascFactorial
/-- `n.ascFactorial k = (n + k)! / n!` but without ℕ-division. See `Nat.ascFactorial_eq_div` for
the version with ℕ-division. -/
@@ -265,14 +265,14 @@ theorem factorial_mul_ascFactorial (n : ℕ) : ∀ k, n ! * n.ascFactorial k = (
| k + 1 => by
rw [ascFactorial_succ, mul_left_comm, factorial_mul_ascFactorial n k,
← add_assoc, ← Nat.succ_eq_add_one (n + k), factorial]
-#align nat.factorial_mul_ascFactorial Nat.factorial_mul_ascFactorial
+#align nat.factorial_mul_asc_factorial Nat.factorial_mul_ascFactorial
/-- Avoid in favor of `Nat.factorial_mul_ascFactorial` if you can. ℕ-division isn't worth it. -/
theorem ascFactorial_eq_div (n k : ℕ) : n.ascFactorial k = (n + k)! / n ! := by
apply mul_left_cancel₀ n.factorial_ne_zero
rw [factorial_mul_ascFactorial]
exact (Nat.mul_div_cancel' <| factorial_dvd_factorial <| le.intro rfl).symm
-#align nat.ascFactorial_eq_div Nat.ascFactorial_eq_div
+#align nat.asc_factorial_eq_div Nat.ascFactorial_eq_div
theorem ascFactorial_of_sub {n k : ℕ} (h : k < n) :
(n - k) * (n - k).ascFactorial k = (n - (k + 1)).ascFactorial (k + 1) := by
@@ -280,27 +280,27 @@ theorem ascFactorial_of_sub {n k : ℕ} (h : k < n) :
let ht : t = n - k.succ := rfl
suffices h' : n - k = t.succ; · rw [← ht, h', succ_ascFactorial, ascFactorial_succ]
rw [ht, succ_eq_add_one, ← tsub_tsub_assoc (succ_le_of_lt h) (succ_pos _), succ_sub_one]
-#align nat.ascFactorial_of_sub Nat.ascFactorial_of_sub
+#align nat.asc_factorial_of_sub Nat.ascFactorial_of_sub
theorem pow_succ_le_ascFactorial (n : ℕ) : ∀ k : ℕ, (n + 1) ^ k ≤ n.ascFactorial k
| 0 => by rw [ascFactorial_zero, pow_zero]
| k + 1 => by
rw [pow_succ, mul_comm]
exact Nat.mul_le_mul (Nat.add_le_add_right le_self_add _) (pow_succ_le_ascFactorial _ k)
-#align nat.pow_succ_le_ascFactorial Nat.pow_succ_le_ascFactorial
+#align nat.pow_succ_le_asc_factorial Nat.pow_succ_le_ascFactorial
theorem pow_lt_ascFactorial' (n k : ℕ) : (n + 1) ^ (k + 2) < n.ascFactorial (k + 2) := by
rw [pow_succ, ascFactorial, mul_comm]
exact
Nat.mul_lt_mul (Nat.add_lt_add_right (Nat.lt_add_of_pos_right succ_pos') 1)
(pow_succ_le_ascFactorial n _) (pow_pos succ_pos' _)
-#align nat.pow_lt_ascFactorial' Nat.pow_lt_ascFactorial'
+#align nat.pow_lt_asc_factorial' Nat.pow_lt_ascFactorial'
theorem pow_lt_ascFactorial (n : ℕ) : ∀ {k : ℕ}, 2 ≤ k → (n + 1) ^ k < n.ascFactorial k
| 0 => by rintro ⟨⟩
| 1 => by intro; contradiction
| k + 2 => fun _ => pow_lt_ascFactorial' n k
-#align nat.pow_lt_ascFactorial Nat.pow_lt_ascFactorial
+#align nat.pow_lt_asc_factorial Nat.pow_lt_ascFactorial
theorem ascFactorial_le_pow_add (n : ℕ) : ∀ k : ℕ, n.ascFactorial k ≤ (n + k) ^ k
| 0 => by rw [ascFactorial_zero, pow_zero]
@@ -310,7 +310,7 @@ theorem ascFactorial_le_pow_add (n : ℕ) : ∀ k : ℕ, n.ascFactorial k ≤ (n
exact
Nat.mul_le_mul_of_nonneg_left
((ascFactorial_le_pow_add _ k).trans (Nat.pow_le_pow_of_le_left (le_succ _) _))
-#align nat.ascFactorial_le_pow_add Nat.ascFactorial_le_pow_add
+#align nat.asc_factorial_le_pow_add Nat.ascFactorial_le_pow_add
theorem ascFactorial_lt_pow_add (n : ℕ) : ∀ {k : ℕ}, 2 ≤ k → n.ascFactorial k < (n + k) ^ k
| 0 => by rintro ⟨⟩
@@ -323,11 +323,11 @@ theorem ascFactorial_lt_pow_add (n : ℕ) : ∀ {k : ℕ}, 2 ≤ k → n.ascFact
((ascFactorial_le_pow_add n _).trans_lt
(pow_lt_pow_of_lt_left (lt_add_one _) (succ_pos _)))
(succ_pos _)
-#align nat.ascFactorial_lt_pow_add Nat.ascFactorial_lt_pow_add
+#align nat.asc_factorial_lt_pow_add Nat.ascFactorial_lt_pow_add
theorem ascFactorial_pos (n k : ℕ) : 0 < n.ascFactorial k :=
(pow_pos (succ_pos n) k).trans_le (pow_succ_le_ascFactorial n k)
-#align nat.ascFactorial_pos Nat.ascFactorial_pos
+#align nat.asc_factorial_pos Nat.ascFactorial_pos
end AscFactorial
@@ -339,21 +339,21 @@ related to `pochhammer`, but much less general. -/
def descFactorial (n : ℕ) : ℕ → ℕ
| 0 => 1
| k + 1 => (n - k) * descFactorial n k
-#align nat.descFactorial Nat.descFactorial
+#align nat.desc_factorial Nat.descFactorial
@[simp]
theorem descFactorial_zero (n : ℕ) : n.descFactorial 0 = 1 :=
rfl
-#align nat.descFactorial_zero Nat.descFactorial_zero
+#align nat.desc_factorial_zero Nat.descFactorial_zero
@[simp]
theorem descFactorial_succ (n k : ℕ) : n.descFactorial k.succ = (n - k) * n.descFactorial k :=
rfl
-#align nat.descFactorial_succ Nat.descFactorial_succ
+#align nat.desc_factorial_succ Nat.descFactorial_succ
theorem zero_descFactorial_succ (k : ℕ) : (0 : ℕ).descFactorial k.succ = 0 := by
rw [descFactorial_succ, zero_tsub, zero_mul]
-#align nat.zero_descFactorial_succ Nat.zero_descFactorial_succ
+#align nat.zero_desc_factorial_succ Nat.zero_descFactorial_succ
/- Porting note: simp removed because this can be proved by
simp only [Nat.descFactorial_succ, nonpos_iff_eq_zero, tsub_zero, Nat.descFactorial_zero, mul_one]
@@ -361,7 +361,7 @@ simp only [Nat.descFactorial_succ, nonpos_iff_eq_zero, tsub_zero, Nat.descFactor
-- @[simp]
theorem descFactorial_one (n : ℕ) : n.descFactorial 1 = n := by
rw [descFactorial_succ, descFactorial_zero, mul_one, tsub_zero]
-#align nat.descFactorial_one Nat.descFactorial_one
+#align nat.desc_factorial_one Nat.descFactorial_one
/- Porting note: simp removed because the lhs simplifies,
according to the linter:
@@ -379,19 +379,19 @@ theorem succ_descFactorial_succ (n : ℕ) :
| succ k => by
rw [descFactorial_succ, succ_descFactorial_succ _ k, descFactorial_succ, succ_sub_succ,
mul_left_comm]
-#align nat.succ_descFactorial_succ Nat.succ_descFactorial_succ
+#align nat.succ_desc_factorial_succ Nat.succ_descFactorial_succ
theorem succ_descFactorial (n : ℕ) :
∀ k, (n + 1 - k) * (n + 1).descFactorial k = (n + 1) * n.descFactorial k
| 0 => by rw [tsub_zero, descFactorial_zero, descFactorial_zero]
| k + 1 => by
rw [descFactorial, succ_descFactorial _ k, descFactorial_succ, succ_sub_succ, mul_left_comm]
-#align nat.succ_descFactorial Nat.succ_descFactorial
+#align nat.succ_desc_factorial Nat.succ_descFactorial
theorem descFactorial_self : ∀ n : ℕ, n.descFactorial n = n !
| 0 => by rw [descFactorial_zero, factorial_zero]
| succ n => by rw [succ_descFactorial_succ, descFactorial_self n, factorial_succ]
-#align nat.descFactorial_self Nat.descFactorial_self
+#align nat.desc_factorial_self Nat.descFactorial_self
@[simp]
theorem descFactorial_eq_zero_iff_lt {n : ℕ} : ∀ {k : ℕ}, n.descFactorial k = 0 ↔ n < k
@@ -400,7 +400,7 @@ theorem descFactorial_eq_zero_iff_lt {n : ℕ} : ∀ {k : ℕ}, n.descFactorial
rw [descFactorial_succ, mul_eq_zero, descFactorial_eq_zero_iff_lt, lt_succ_iff,
tsub_eq_zero_iff_le, lt_iff_le_and_ne, or_iff_left_iff_imp, and_imp]
exact fun h _ => h
-#align nat.descFactorial_eq_zero_iff_lt Nat.descFactorial_eq_zero_iff_lt
+#align nat.desc_factorial_eq_zero_iff_lt Nat.descFactorial_eq_zero_iff_lt
alias descFactorial_eq_zero_iff_lt ↔ _ descFactorial_of_lt
@@ -410,7 +410,7 @@ theorem add_descFactorial_eq_ascFactorial (n : ℕ) :
| succ k => by
rw [Nat.add_succ, Nat.succ_eq_add_one, Nat.succ_eq_add_one,
succ_descFactorial_succ, ascFactorial_succ, add_descFactorial_eq_ascFactorial _ k]
-#align nat.add_descFactorial_eq_ascFactorial Nat.add_descFactorial_eq_ascFactorial
+#align nat.add_descFactorial_eq_asc_factorial Nat.add_descFactorial_eq_ascFactorial
/-- `n.descFactorial k = n! / (n - k)!` but without ℕ-division. See `Nat.descFactorial_eq_div`
for the version using ℕ-division. -/
@@ -422,14 +422,14 @@ theorem factorial_mul_descFactorial : ∀ {n k : ℕ}, k ≤ n → (n - k)! * n.
| succ n, succ k => fun h => by
rw [succ_descFactorial_succ, succ_sub_succ, ← mul_assoc, mul_comm (n - k)!, mul_assoc,
factorial_mul_descFactorial (Nat.succ_le_succ_iff.1 h), factorial_succ]
-#align nat.factorial_mul_descFactorial Nat.factorial_mul_descFactorial
+#align nat.factorial_mul_desc_factorial Nat.factorial_mul_descFactorial
/-- Avoid in favor of `Nat.factorial_mul_descFactorial` if you can. ℕ-division isn't worth it. -/
theorem descFactorial_eq_div {n k : ℕ} (h : k ≤ n) : n.descFactorial k = n ! / (n - k)! := by
apply mul_left_cancel₀ (factorial_ne_zero (n - k))
rw [factorial_mul_descFactorial h]
exact (Nat.mul_div_cancel' <| factorial_dvd_factorial <| Nat.sub_le n k).symm
-#align nat.descFactorial_eq_div Nat.descFactorial_eq_div
+#align nat.desc_factorial_eq_div Nat.descFactorial_eq_div
theorem pow_sub_le_descFactorial (n : ℕ) : ∀ k : ℕ, (n + 1 - k) ^ k ≤ n.descFactorial k
| 0 => by rw [descFactorial_zero, pow_zero]
@@ -438,7 +438,7 @@ theorem pow_sub_le_descFactorial (n : ℕ) : ∀ k : ℕ, (n + 1 - k) ^ k ≤ n.
apply Nat.mul_le_mul_of_nonneg_left
exact (le_trans (Nat.pow_le_pow_of_le_left (tsub_le_tsub_right (le_succ _) _) k)
(pow_sub_le_descFactorial n k))
-#align nat.pow_sub_le_descFactorial Nat.pow_sub_le_descFactorial
+#align nat.pow_sub_le_desc_factorial Nat.pow_sub_le_descFactorial
theorem pow_sub_lt_descFactorial' {n : ℕ} :
∀ {k : ℕ}, k + 2 ≤ n → (n - (k + 1)) ^ (k + 2) < n.descFactorial (k + 2)
@@ -454,7 +454,7 @@ theorem pow_sub_lt_descFactorial' {n : ℕ} :
rw [succ_sub_succ]
exact pow_sub_lt_descFactorial' ((le_succ _).trans h)
· apply tsub_pos_of_lt; apply h
-#align nat.pow_sub_lt_descFactorial' Nat.pow_sub_lt_descFactorial'
+#align nat.pow_sub_lt_desc_factorial' Nat.pow_sub_lt_descFactorial'
theorem pow_sub_lt_descFactorial {n : ℕ} :
∀ {k : ℕ}, 2 ≤ k → k ≤ n → (n + 1 - k) ^ k < n.descFactorial k
@@ -463,14 +463,14 @@ theorem pow_sub_lt_descFactorial {n : ℕ} :
| k + 2 => fun _ h => by
rw [succ_sub_succ]
exact pow_sub_lt_descFactorial' h
-#align nat.pow_sub_lt_descFactorial Nat.pow_sub_lt_descFactorial
+#align nat.pow_sub_lt_desc_factorial Nat.pow_sub_lt_descFactorial
theorem descFactorial_le_pow (n : ℕ) : ∀ k : ℕ, n.descFactorial k ≤ n ^ k
| 0 => by rw [descFactorial_zero, pow_zero]
| k + 1 => by
rw [descFactorial_succ, pow_succ, mul_comm _ n]
exact Nat.mul_le_mul (Nat.sub_le _ _) (descFactorial_le_pow _ k)
-#align nat.descFactorial_le_pow Nat.descFactorial_le_pow
+#align nat.desc_factorial_le_pow Nat.descFactorial_le_pow
theorem descFactorial_lt_pow {n : ℕ} (hn : 1 ≤ n) : ∀ {k : ℕ}, 2 ≤ k → n.descFactorial k < n ^ k
| 0 => by rintro ⟨⟩
@@ -479,7 +479,7 @@ theorem descFactorial_lt_pow {n : ℕ} (hn : 1 ≤ n) : ∀ {k : ℕ}, 2 ≤ k
rw [descFactorial_succ, pow_succ', mul_comm, mul_comm n]
exact Nat.mul_lt_mul' (descFactorial_le_pow _ _) (tsub_lt_self hn k.zero_lt_succ)
(pow_pos (Nat.lt_of_succ_le hn) _)
-#align nat.descFactorial_lt_pow Nat.descFactorial_lt_pow
+#align nat.desc_factorial_lt_pow Nat.descFactorial_lt_pow
end DescFactorial
This was done semi-automatically with some regular expressions in vim in contrast to the fully automatic https://github.com/leanprover-community/mathlib4/pull/1523.
Co-authored-by: Moritz Firsching <firsching@google.com>
@@ -174,16 +174,16 @@ theorem add_factorial_succ_lt_factorial_add_succ {i : ℕ} (n : ℕ) (hi : 2 ≤
((add_le_add_iff_right n).mpr ((by decide : 1 ≤ 2).trans hi))))
#align nat.add_factorial_succ_lt_factorial_add_succ Nat.add_factorial_succ_lt_factorial_add_succ
-theorem add_factorial_lt_factorial_add {i n : ℕ} (hi : 2 ≤ i) (hn : 1 ≤ n) : i + n ! < (i + n)! :=
- by
+theorem add_factorial_lt_factorial_add {i n : ℕ} (hi : 2 ≤ i) (hn : 1 ≤ n) :
+ i + n ! < (i + n)! := by
cases hn
· rw [factorial_one]
exact lt_factorial_self (succ_le_succ hi)
exact add_factorial_succ_lt_factorial_add_succ _ hi
#align nat.add_factorial_lt_factorial_add Nat.add_factorial_lt_factorial_add
-theorem add_factorial_succ_le_factorial_add_succ (i : ℕ) (n : ℕ) : i + (n + 1)! ≤ (i + (n + 1))! :=
- by
+theorem add_factorial_succ_le_factorial_add_succ (i : ℕ) (n : ℕ) :
+ i + (n + 1)! ≤ (i + (n + 1))! := by
cases (le_or_lt (2 : ℕ) i)
· rw [← add_assoc]
apply Nat.le_of_lt
@@ -453,7 +453,7 @@ theorem pow_sub_lt_descFactorial' {n : ℕ} :
· refine' ((Nat.pow_le_pow_of_le_left (tsub_le_tsub_right (le_succ n) _) _).trans_lt _)
rw [succ_sub_succ]
exact pow_sub_lt_descFactorial' ((le_succ _).trans h)
- · apply tsub_pos_of_lt h
+ · apply tsub_pos_of_lt; apply h
#align nat.pow_sub_lt_descFactorial' Nat.pow_sub_lt_descFactorial'
theorem pow_sub_lt_descFactorial {n : ℕ} :
@@ -477,8 +477,8 @@ theorem descFactorial_lt_pow {n : ℕ} (hn : 1 ≤ n) : ∀ {k : ℕ}, 2 ≤ k
| 1 => by intro; contradiction
| k + 2 => fun _ => by
rw [descFactorial_succ, pow_succ', mul_comm, mul_comm n]
- exact
- Nat.mul_lt_mul' (descFactorial_le_pow _ _) (tsub_lt_self hn k.zero_lt_succ) (pow_pos hn _)
+ exact Nat.mul_lt_mul' (descFactorial_le_pow _ _) (tsub_lt_self hn k.zero_lt_succ)
+ (pow_pos (Nat.lt_of_succ_le hn) _)
#align nat.descFactorial_lt_pow Nat.descFactorial_lt_pow
end DescFactorial
@@ -18,8 +18,8 @@ This file defines the factorial, along with the ascending and descending variant
## Main declarations
-* `nNat.factorial`: The factorial.
-* `at.ascFactorial`: The ascending factorial. Note that it runs from `n + 1` to `n + k`
+* `Nat.factorial`: The factorial.
+* `Nat.ascFactorial`: The ascending factorial. Note that it runs from `n + 1` to `n + k`
and *not* from `n` to `n + k - 1`. We might want to change that in the future.
* `Nat.descFactorial`: The descending factorial. It runs from `n - k` to `n`.
-/
@@ -248,13 +248,12 @@ theorem ascFactorial_succ {n k : ℕ} : n.ascFactorial k.succ = (n + k + 1) * n.
#align nat.ascFactorial_succ Nat.ascFactorial_succ
-- Porting note: Explicit arguments are required to show that the recursion terminates
--- Porting note: `rw` does not automatically try to apply `rfl` at the end
theorem succ_ascFactorial (n : ℕ) :
∀ k, (n + 1) * n.succ.ascFactorial k = (n + k + 1) * n.ascFactorial k
| 0 => by rw [add_zero, ascFactorial_zero, ascFactorial_zero]
| k + 1 => by
rw [ascFactorial, mul_left_comm, succ_ascFactorial n k, ascFactorial,
- succ_add, ← add_assoc]; rfl
+ succ_add, ← add_assoc, succ_eq_add_one]
#align nat.succ_ascFactorial Nat.succ_ascFactorial
/-- `n.ascFactorial k = (n + k)! / n!` but without ℕ-division. See `Nat.ascFactorial_eq_div` for
The unported dependencies are