Theorem: Nat.Prime.multiplicity_choose_prime_pow_add_multiplicity
File: Mathlib/Data/Nat/Multiplicity.lean

tactic: have hdisj :
  Disjoint ((Ico 1 n.succ).filter fun i => p ^ i ≤ k % p ^ i + (p ^ n - k) % p ^ i)
    ((Ico 1 n.succ).filter fun i => p ^ i ∣ k) := by
  simp (config := { contextual := true }) [disjoint_right, *, dvd_iff_mod_eq_zero,
    Nat.mod_lt _ (pow_pos hp.pos _)]
state_before: p n k : ℕ
hp : Prime p
hkn : k ≤ p ^ n
hk0 : k ≠ 0
⊢ multiplicity p ((p ^ n).choose k) + multiplicity p k ≤ ↑n
state_after: p n k : ℕ
hp : Prime p
hkn : k ≤ p ^ n
hk0 : k ≠ 0
hdisj :
  Disjoint (filter (fun i => p ^ i ≤ k % p ^ i + (p ^ n - k) % p ^ i) (Ico 1 n.succ))
    (filter (fun i => p ^ i ∣ k) (Ico 1 n.succ))
⊢ multiplicity p ((p ^ n).choose k) + multiplicity p k ≤ ↑n

tactic: rw [multiplicity_choose hp hkn (lt_succ_self _),
  multiplicity_eq_card_pow_dvd (ne_of_gt hp.one_lt) hk0.bot_lt
    (lt_succ_of_le (log_mono_right hkn)),
  ← Nat.cast_add, PartENat.coe_le_coe, log_pow hp.one_lt, ← card_union_of_disjoint hdisj,
  filter_union_right]
state_before: p n k : ℕ
hp : Prime p
hkn : k ≤ p ^ n
hk0 : k ≠ 0
hdisj :
  Disjoint (filter (fun i => p ^ i ≤ k % p ^ i + (p ^ n - k) % p ^ i) (Ico 1 n.succ))
    (filter (fun i => p ^ i ∣ k) (Ico 1 n.succ))
⊢ multiplicity p ((p ^ n).choose k) + multiplicity p k ≤ ↑n
state_after: p n k : ℕ
hp : Prime p
hkn : k ≤ p ^ n
hk0 : k ≠ 0
hdisj :
  Disjoint (filter (fun i => p ^ i ≤ k % p ^ i + (p ^ n - k) % p ^ i) (Ico 1 n.succ))
    (filter (fun i => p ^ i ∣ k) (Ico 1 n.succ))
⊢ (filter (fun x => p ^ x ≤ k % p ^ x + (p ^ n - k) % p ^ x ∨ p ^ x ∣ k) (Ico 1 n.succ)).card ≤ n

tactic: have filter_le_Ico := (Ico 1 n.succ).card_filter_le
  fun x => p ^ x ≤ k % p ^ x + (p ^ n - k) % p ^ x ∨ p ^ x ∣ k
state_before: p n k : ℕ
hp : Prime p
hkn : k ≤ p ^ n
hk0 : k ≠ 0
hdisj :
  Disjoint (filter (fun i => p ^ i ≤ k % p ^ i + (p ^ n - k) % p ^ i) (Ico 1 n.succ))
    (filter (fun i => p ^ i ∣ k) (Ico 1 n.succ))
⊢ (filter (fun x => p ^ x ≤ k % p ^ x + (p ^ n - k) % p ^ x ∨ p ^ x ∣ k) (Ico 1 n.succ)).card ≤ n
state_after: p n k : ℕ
hp : Prime p
hkn : k ≤ p ^ n
hk0 : k ≠ 0
hdisj :
  Disjoint (filter (fun i => p ^ i ≤ k % p ^ i + (p ^ n - k) % p ^ i) (Ico 1 n.succ))
    (filter (fun i => p ^ i ∣ k) (Ico 1 n.succ))
filter_le_Ico :
  (filter (fun x => p ^ x ≤ k % p ^ x + (p ^ n - k) % p ^ x ∨ p ^ x ∣ k) (Ico 1 n.succ)).card ≤ (Ico 1 n.succ).card
⊢ (filter (fun x => p ^ x ≤ k % p ^ x + (p ^ n - k) % p ^ x ∨ p ^ x ∣ k) (Ico 1 n.succ)).card ≤ n

tactic: rwa [card_Ico 1 n.succ] at filter_le_Ico
state_before: p n k : ℕ
hp : Prime p
hkn : k ≤ p ^ n
hk0 : k ≠ 0
hdisj :
  Disjoint (filter (fun i => p ^ i ≤ k % p ^ i + (p ^ n - k) % p ^ i) (Ico 1 n.succ))
    (filter (fun i => p ^ i ∣ k) (Ico 1 n.succ))
filter_le_Ico :
  (filter (fun x => p ^ x ≤ k % p ^ x + (p ^ n - k) % p ^ x ∨ p ^ x ∣ k) (Ico 1 n.succ)).card ≤ (Ico 1 n.succ).card
⊢ (filter (fun x => p ^ x ≤ k % p ^ x + (p ^ n - k) % p ^ x ∨ p ^ x ∣ k) (Ico 1 n.succ)).card ≤ n
state_after: no goals

tactic: simp (config := { contextual := true }) [disjoint_right, *, dvd_iff_mod_eq_zero,
  Nat.mod_lt _ (pow_pos hp.pos _)]
state_before: p n k : ℕ
hp : Prime p
hkn : k ≤ p ^ n
hk0 : k ≠ 0
⊢ Disjoint (filter (fun i => p ^ i ≤ k % p ^ i + (p ^ n - k) % p ^ i) (Ico 1 n.succ))
    (filter (fun i => p ^ i ∣ k) (Ico 1 n.succ))
state_after: no goals

tactic: rw [← hp.multiplicity_pow_self]
state_before: p n k : ℕ
hp : Prime p
hkn : k ≤ p ^ n
hk0 : k ≠ 0
⊢ ↑n ≤ multiplicity p ((p ^ n).choose k) + multiplicity p k
state_after: p n k : ℕ
hp : Prime p
hkn : k ≤ p ^ n
hk0 : k ≠ 0
⊢ multiplicity p (p ^ n) ≤ multiplicity p ((p ^ n).choose k) + multiplicity p k

tactic: exact multiplicity_le_multiplicity_choose_add hp _ _
state_before: p n k : ℕ
hp : Prime p
hkn : k ≤ p ^ n
hk0 : k ≠ 0
⊢ multiplicity p (p ^ n) ≤ multiplicity p ((p ^ n).choose k) + multiplicity p k
state_after: no goals