File: Mathlib/Tactic/Zify.lean

full_name: Mathlib.Tactic.Zify.zify
code: /--
The `zify` tactic is used to shift propositions from `Nat` to `Int`.
This is often useful since `Int` has well-behaved subtraction.
```
example (a b c x y z : Nat) (h : ¬ x*y*z < 0) : c < a + 3*b := by
  zify
  zify at h
  /-
  h : ¬↑x * ↑y * ↑z < 0
  ⊢ ↑c < ↑a + 3 * ↑b
  -/
```
`zify` can be given extra lemmas to use in simplification. This is especially useful in the
presence of nat subtraction: passing `≤` arguments will allow `push_cast` to do more work.
```
example (a b c : Nat) (h : a - b < c) (hab : b ≤ a) : false := by
  zify [hab] at h
  /- h : ↑a - ↑b < ↑c -/
```
`zify` makes use of the `@[zify_simps]` attribute to move propositions,
and the `push_cast` tactic to simplify the `Int`-valued expressions.
`zify` is in some sense dual to the `lift` tactic.
`lift (z : Int) to Nat` will change the type of an
integer `z` (in the supertype) to `Nat` (the subtype), given a proof that `z ≥ 0`;
propositions concerning `z` will still be over `Int`.
`zify` changes propositions about `Nat` (the subtype) to propositions about `Int` (the supertype),
without changing the type of any variable.
-/
syntax (name := zify) "zify" (simpArgs)? (location)? : tactic
goal: Lean.ParserDescr

full_name: Mathlib.Tactic.Zify._aux_Mathlib_Tactic_Zify___macroRules_Mathlib_Tactic_Zify_zify_1
code: macro_rules
| `(tactic| zify $[[$simpArgs,*]]? $[at $location]?) =>
  let args := simpArgs.map (·.getElems) |>.getD #[]
  `(tactic|
    simp (config := {decide := false}) only [zify_simps, push_cast, $args,*] $[at $location]?)
goal: Lean.Macro

full_name: Mathlib.Tactic.Zify.mkZifyContext
code: /-- The `Simp.Context` generated by `zify`. -/
def mkZifyContext (simpArgs : Option (Syntax.TSepArray `Lean.Parser.Tactic.simpStar ",")) :
    TacticM MkSimpContextResult 
goal: Lean.Elab.Tactic.TacticM Lean.Elab.Tactic.MkSimpContextResult

full_name: Mathlib.Tactic.Zify.applySimpResultToProp'
code: /-- A variant of `applySimpResultToProp` that cannot close the goal, but does not need a meta
variable and returns a tuple of a proof and the corresponding simplified proposition. -/
def applySimpResultToProp' (proof : Expr) (prop : Expr) (r : Simp.Result) : MetaM (Expr × Expr) 
goal: Lean.MetaM (Lean.Expr × Lean.Expr)

full_name: Mathlib.Tactic.Zify.zifyProof
code: /-- Translate a proof and the proposition into a zified form. -/
def zifyProof (simpArgs : Option (Syntax.TSepArray `Lean.Parser.Tactic.simpStar ","))
    (proof : Expr) (prop : Expr) : TacticM (Expr × Expr) 
goal: Lean.Elab.Tactic.TacticM (Lean.Expr × Lean.Expr)

full_name: Mathlib.Tactic.Zify.natCast_eq
code: @[zify_simps] lemma natCast_eq (a b : Nat) : a = b ↔ (a : Int) = (b : Int) 
goal: a = b ↔ ↑a = ↑b

full_name: Mathlib.Tactic.Zify.natCast_le
code: @[zify_simps] lemma natCast_le (a b : Nat) : a ≤ b ↔ (a : Int) ≤ (b : Int) 
goal: a ≤ b ↔ ↑a ≤ ↑b

full_name: Mathlib.Tactic.Zify.natCast_lt
code: @[zify_simps] lemma natCast_lt (a b : Nat) : a < b ↔ (a : Int) < (b : Int) 
goal: a < b ↔ ↑a < ↑b

full_name: Mathlib.Tactic.Zify.natCast_ne
code: @[zify_simps] lemma natCast_ne (a b : Nat) : a ≠ b ↔ (a : Int) ≠ (b : Int) 
goal: a ≠ b ↔ ↑a ≠ ↑b

full_name: Mathlib.Tactic.Zify.natCast_dvd
code: @[zify_simps] lemma natCast_dvd (a b : Nat) : a ∣ b ↔ (a : Int) ∣ (b : Int) 
goal: a ∣ b ↔ ↑a ∣ ↑b

full_name: Mathlib.Tactic.Zify.Nat.cast_sub_of_add_le
code: @[norm_cast] theorem Nat.cast_sub_of_add_le {m n k} (h : m + k ≤ n) :
    ((n - m : ℕ) : R) = n - m 
goal: ↑(n - m) = ↑n - ↑m

full_name: Mathlib.Tactic.Zify.Nat.cast_sub_of_lt
code: @[norm_cast] theorem Nat.cast_sub_of_lt {m n} (h : m < n) :
    ((n - m : ℕ) : R) = n - m 
goal: ↑(n - m) = ↑n - ↑m