l3lab/ntp-mathlib huggingface dataset:
theorem IsCycle.eq_swap_of_apply_apply_eq_self {α : Type*} [DecidableEq α] {f : Perm α}
    (hf : IsCycle f) {x : α} (hfx : f x ≠ x) (hffx : f (f x) = x) : f = swap x (f x) :=
  Equiv.ext fun y =>
    let ⟨z, hz⟩ := hf
    let ⟨i, hi⟩ := hz.2 hfx
    if hyx : y = x then by simp [hyx]
    else
      if hfyx : y = f x then by simp [hfyx, hffx]
      else by
        rw [swap_apply_of_ne_of_ne hyx hfyx]
        refine' by_contradiction fun hy => _
        cases' hz.2 hy with j hj
        rw [← sub_add_cancel j i, zpow_add, mul_apply, hi] at hj
        cases' zpow_apply_eq_of_apply_apply_eq_self hffx (j - i) with hji hji
        · rw [← hj, hji] at hyx
          tauto
        · rw [← hj, hji] at hfyx
          

Proof state:
case intro.inr
ι : Type u_1
α✝ : Type u_2
β : Type u_3
f✝ g : Perm α✝
x✝ y✝ : α✝
inst✝² : DecidableEq α✝
inst✝¹ : Fintype α✝
α : Type u_4
inst✝ : DecidableEq α
f : Perm α
hf : IsCycle f
x : α
hfx : f x ≠ x
hffx : f (f x) = x
y z : α
hz : f z ≠ z ∧ ∀ ⦃y : α⦄, f y ≠ y → SameCycle f z y
i : ℤ
hi : (f ^ i) z = x
hyx : ¬y = x
hy : ¬f y = y
j : ℤ
hfyx : ¬f x = f x
hj : (f ^ (j - i)) x = y
hji : (f ^ (j - i)) x = f x
⊢ False

Next tactic:
tauto
theorem IsCycle.swap_mul {α : Type*} [DecidableEq α] {f : Perm α} (hf : IsCycle f) {x : α}
    (hx : f x ≠ x) (hffx : f (f x) ≠ x) : IsCycle (swap x (f x) * f) :=
  ⟨f x, by 

Proof state:
ι : Type u_1
α✝ : Type u_2
β : Type u_3
f✝ g : Perm α✝
x✝ y : α✝
inst✝² : DecidableEq α✝
inst✝¹ : Fintype α✝
α : Type u_4
inst✝ : DecidableEq α
f : Perm α
hf : IsCycle f
x : α
hx : f x ≠ x
hffx : f (f x) ≠ x
⊢ (swap x (f x) * f) (f x) ≠ f x

Next tactic:
simp [swap_apply_def, mul_apply, if_neg hffx, f.injective.eq_iff, if_neg hx, hx]
theorem IsCycle.swap_mul {α : Type*} [DecidableEq α] {f : Perm α} (hf : IsCycle f) {x : α}
    (hx : f x ≠ x) (hffx : f (f x) ≠ x) : IsCycle (swap x (f x) * f) :=
  ⟨f x, by simp [swap_apply_def, mul_apply, if_neg hffx, f.injective.eq_iff, if_neg hx, hx],
    fun y hy =>
    let ⟨i, hi⟩ := hf.exists_zpow_eq hx (ne_and_ne_of_swap_mul_apply_ne_self hy).1
    -- Porting note: Needed to add Perm α typehint, otherwise does not know how to coerce to fun
    have hi : (f ^ (i - 1) : Perm α) (f x) = y :=
      calc
        (f ^ (i - 1) : Perm α) (f x) = (f ^ (i - 1) * f ^ (1 : ℤ) : Perm α) x := by 

Proof state:
ι : Type u_1
α✝ : Type u_2
β : Type u_3
f✝ g : Perm α✝
x✝ y✝ : α✝
inst✝² : DecidableEq α✝
inst✝¹ : Fintype α✝
α : Type u_4
inst✝ : DecidableEq α
f : Perm α
hf : IsCycle f
x : α
hx : f x ≠ x
hffx : f (f x) ≠ x
y : α
hy : (swap x (f x) * f) y ≠ y
i : ℤ
hi : (f ^ i) x = y
⊢ (f ^ (i - 1)) (f x) = (f ^ (i - 1) * f ^ 1) x

Next tactic:
simp
theorem IsCycle.swap_mul {α : Type*} [DecidableEq α] {f : Perm α} (hf : IsCycle f) {x : α}
    (hx : f x ≠ x) (hffx : f (f x) ≠ x) : IsCycle (swap x (f x) * f) :=
  ⟨f x, by simp [swap_apply_def, mul_apply, if_neg hffx, f.injective.eq_iff, if_neg hx, hx],
    fun y hy =>
    let ⟨i, hi⟩ := hf.exists_zpow_eq hx (ne_and_ne_of_swap_mul_apply_ne_self hy).1
    -- Porting note: Needed to add Perm α typehint, otherwise does not know how to coerce to fun
    have hi : (f ^ (i - 1) : Perm α) (f x) = y :=
      calc
        (f ^ (i - 1) : Perm α) (f x) = (f ^ (i - 1) * f ^ (1 : ℤ) : Perm α) x := by simp
        _ = y := by 

Proof state:
ι : Type u_1
α✝ : Type u_2
β : Type u_3
f✝ g : Perm α✝
x✝ y✝ : α✝
inst✝² : DecidableEq α✝
inst✝¹ : Fintype α✝
α : Type u_4
inst✝ : DecidableEq α
f : Perm α
hf : IsCycle f
x : α
hx : f x ≠ x
hffx : f (f x) ≠ x
y : α
hy : (swap x (f x) * f) y ≠ y
i : ℤ
hi : (f ^ i) x = y
⊢ (f ^ (i - 1) * f ^ 1) x = y

Next tactic:
rwa [← zpow_add, sub_add_cancel]
theorem IsCycle.sign {f : Perm α} (hf : IsCycle f) : sign f = -(-1) ^ f.support.card :=
  let ⟨x, hx⟩ := hf
  calc
    Perm.sign f = Perm.sign (swap x (f x) * (swap x (f x) * f)) := by
      

Proof state:
ι : Type u_1
α : Type u_2
β : Type u_3
f✝ g : Perm α
x✝ y : α
inst✝¹ : DecidableEq α
inst✝ : Fintype α
f : Perm α
hf : IsCycle f
x : α
hx : f x ≠ x ∧ ∀ ⦃y : α⦄, f y ≠ y → SameCycle f x y
⊢ Perm.sign f = Perm.sign (swap x (f x) * (swap x (f x) * f))

Next tactic:
{rw [← mul_assoc, mul_def, mul_def, swap_swap, trans_refl]}
theorem IsCycle.sign {f : Perm α} (hf : IsCycle f) : sign f = -(-1) ^ f.support.card :=
  let ⟨x, hx⟩ := hf
  calc
    Perm.sign f = Perm.sign (swap x (f x) * (swap x (f x) * f)) := by
      {

Proof state:
ι : Type u_1
α : Type u_2
β : Type u_3
f✝ g : Perm α
x✝ y : α
inst✝¹ : DecidableEq α
inst✝ : Fintype α
f : Perm α
hf : IsCycle f
x : α
hx : f x ≠ x ∧ ∀ ⦃y : α⦄, f y ≠ y → SameCycle f x y
⊢ Perm.sign f = Perm.sign (swap x (f x) * (swap x (f x) * f))

Next tactic:
rw [← mul_assoc, mul_def, mul_def, swap_swap, trans_refl]
theorem IsCycle.sign {f : Perm α} (hf : IsCycle f) : sign f = -(-1) ^ f.support.card :=
  let ⟨x, hx⟩ := hf
  calc
    Perm.sign f = Perm.sign (swap x (f x) * (swap x (f x) * f)) := by
      {rw [← mul_assoc, mul_def, mul_def, swap_swap, trans_refl]}
    _ = -(-1) ^ f.support.card :=
      if h1 : f (f x) = x then by
        

Proof state:
ι : Type u_1
α : Type u_2
β : Type u_3
f✝ g : Perm α
x✝ y : α
inst✝¹ : DecidableEq α
inst✝ : Fintype α
f : Perm α
hf : IsCycle f
x : α
hx : f x ≠ x ∧ ∀ ⦃y : α⦄, f y ≠ y → SameCycle f x y
h1 : f (f x) = x
⊢ Perm.sign (swap x (f x) * (swap x (f x) * f)) = -(-1) ^ card (support f)

Next tactic:
have h : swap x (f x) * f = 1 := by
          simp only [mul_def, one_def]
          rw [hf.eq_swap_of_apply_apply_eq_self hx.1 h1, swap_apply_left, swap_swap]
theorem IsCycle.sign {f : Perm α} (hf : IsCycle f) : sign f = -(-1) ^ f.support.card :=
  let ⟨x, hx⟩ := hf
  calc
    Perm.sign f = Perm.sign (swap x (f x) * (swap x (f x) * f)) := by
      {rw [← mul_assoc, mul_def, mul_def, swap_swap, trans_refl]}
    _ = -(-1) ^ f.support.card :=
      if h1 : f (f x) = x then by
        have h : swap x (f x) * f = 1 := by
          

Proof state:
ι : Type u_1
α : Type u_2
β : Type u_3
f✝ g : Perm α
x✝ y : α
inst✝¹ : DecidableEq α
inst✝ : Fintype α
f : Perm α
hf : IsCycle f
x : α
hx : f x ≠ x ∧ ∀ ⦃y : α⦄, f y ≠ y → SameCycle f x y
h1 : f (f x) = x
⊢ swap x (f x) * f = 1

Next tactic:
simp only [mul_def, one_def]
theorem IsCycle.sign {f : Perm α} (hf : IsCycle f) : sign f = -(-1) ^ f.support.card :=
  let ⟨x, hx⟩ := hf
  calc
    Perm.sign f = Perm.sign (swap x (f x) * (swap x (f x) * f)) := by
      {rw [← mul_assoc, mul_def, mul_def, swap_swap, trans_refl]}
    _ = -(-1) ^ f.support.card :=
      if h1 : f (f x) = x then by
        have h : swap x (f x) * f = 1 := by
          simp only [mul_def, one_def]
          

Proof state:
ι : Type u_1
α : Type u_2
β : Type u_3
f✝ g : Perm α
x✝ y : α
inst✝¹ : DecidableEq α
inst✝ : Fintype α
f : Perm α
hf : IsCycle f
x : α
hx : f x ≠ x ∧ ∀ ⦃y : α⦄, f y ≠ y → SameCycle f x y
h1 : f (f x) = x
⊢ f.trans (swap x (f x)) = Equiv.refl α

Next tactic:
rw [hf.eq_swap_of_apply_apply_eq_self hx.1 h1, swap_apply_left, swap_swap]
theorem IsCycle.sign {f : Perm α} (hf : IsCycle f) : sign f = -(-1) ^ f.support.card :=
  let ⟨x, hx⟩ := hf
  calc
    Perm.sign f = Perm.sign (swap x (f x) * (swap x (f x) * f)) := by
      {rw [← mul_assoc, mul_def, mul_def, swap_swap, trans_refl]}
    _ = -(-1) ^ f.support.card :=
      if h1 : f (f x) = x then by
        have h : swap x (f x) * f = 1 := by
          simp only [mul_def, one_def]
          rw [hf.eq_swap_of_apply_apply_eq_self hx.1 h1, swap_apply_left, swap_swap]
        

Proof state:
ι : Type u_1
α : Type u_2
β : Type u_3
f✝ g : Perm α
x✝ y : α
inst✝¹ : DecidableEq α
inst✝ : Fintype α
f : Perm α
hf : IsCycle f
x : α
hx : f x ≠ x ∧ ∀ ⦃y : α⦄, f y ≠ y → SameCycle f x y
h1 : f (f x) = x
h : swap x (f x) * f = 1
⊢ Perm.sign (swap x (f x) * (swap x (f x) * f)) = -(-1) ^ card (support f)

Next tactic:
rw [sign_mul, sign_swap hx.1.symm, h, sign_one,
          hf.eq_swap_of_apply_apply_eq_self hx.1 h1, card_support_swap hx.1.symm]
theorem IsCycle.sign {f : Perm α} (hf : IsCycle f) : sign f = -(-1) ^ f.support.card :=
  let ⟨x, hx⟩ := hf
  calc
    Perm.sign f = Perm.sign (swap x (f x) * (swap x (f x) * f)) := by
      {rw [← mul_assoc, mul_def, mul_def, swap_swap, trans_refl]}
    _ = -(-1) ^ f.support.card :=
      if h1 : f (f x) = x then by
        have h : swap x (f x) * f = 1 := by
          simp only [mul_def, one_def]
          rw [hf.eq_swap_of_apply_apply_eq_self hx.1 h1, swap_apply_left, swap_swap]
        rw [sign_mul, sign_swap hx.1.symm, h, sign_one,
          hf.eq_swap_of_apply_apply_eq_self hx.1 h1, card_support_swap hx.1.symm]
        

Proof state:
ι : Type u_1
α : Type u_2
β : Type u_3
f✝ g : Perm α
x✝ y : α
inst✝¹ : DecidableEq α
inst✝ : Fintype α
f : Perm α
hf : IsCycle f
x : α
hx : f x ≠ x ∧ ∀ ⦃y : α⦄, f y ≠ y → SameCycle f x y
h1 : f (f x) = x
h : swap x (f x) * f = 1
⊢ -1 * 1 = -(-1) ^ 2

Next tactic:
rfl
theorem IsCycle.sign {f : Perm α} (hf : IsCycle f) : sign f = -(-1) ^ f.support.card :=
  let ⟨x, hx⟩ := hf
  calc
    Perm.sign f = Perm.sign (swap x (f x) * (swap x (f x) * f)) := by
      {rw [← mul_assoc, mul_def, mul_def, swap_swap, trans_refl]}
    _ = -(-1) ^ f.support.card :=
      if h1 : f (f x) = x then by
        have h : swap x (f x) * f = 1 := by
          simp only [mul_def, one_def]
          rw [hf.eq_swap_of_apply_apply_eq_self hx.1 h1, swap_apply_left, swap_swap]
        rw [sign_mul, sign_swap hx.1.symm, h, sign_one,
          hf.eq_swap_of_apply_apply_eq_self hx.1 h1, card_support_swap hx.1.symm]
        rfl
      else by
        

Proof state:
ι : Type u_1
α : Type u_2
β : Type u_3
f✝ g : Perm α
x✝ y : α
inst✝¹ : DecidableEq α
inst✝ : Fintype α
f : Perm α
hf : IsCycle f
x : α
hx : f x ≠ x ∧ ∀ ⦃y : α⦄, f y ≠ y → SameCycle f x y
h1 : ¬f (f x) = x
⊢ Perm.sign (swap x (f x) * (swap x (f x) * f)) = -(-1) ^ card (support f)

Next tactic:
have h : card (support (swap x (f x) * f)) + 1 = card (support f) := by
          rw [← insert_erase (mem_support.2 hx.1), support_swap_mul_eq _ _ h1,
            card_insert_of_not_mem (not_mem_erase _ _), sdiff_singleton_eq_erase]
theorem IsCycle.sign {f : Perm α} (hf : IsCycle f) : sign f = -(-1) ^ f.support.card :=
  let ⟨x, hx⟩ := hf
  calc
    Perm.sign f = Perm.sign (swap x (f x) * (swap x (f x) * f)) := by
      {rw [← mul_assoc, mul_def, mul_def, swap_swap, trans_refl]}
    _ = -(-1) ^ f.support.card :=
      if h1 : f (f x) = x then by
        have h : swap x (f x) * f = 1 := by
          simp only [mul_def, one_def]
          rw [hf.eq_swap_of_apply_apply_eq_self hx.1 h1, swap_apply_left, swap_swap]
        rw [sign_mul, sign_swap hx.1.symm, h, sign_one,
          hf.eq_swap_of_apply_apply_eq_self hx.1 h1, card_support_swap hx.1.symm]
        rfl
      else by
        have h : card (support (swap x (f x) * f)) + 1 = card (support f) := by
          

Proof state:
ι : Type u_1
α : Type u_2
β : Type u_3
f✝ g : Perm α
x✝ y : α
inst✝¹ : DecidableEq α
inst✝ : Fintype α
f : Perm α
hf : IsCycle f
x : α
hx : f x ≠ x ∧ ∀ ⦃y : α⦄, f y ≠ y → SameCycle f x y
h1 : ¬f (f x) = x
⊢ card (support (swap x (f x) * f)) + 1 = card (support f)

Next tactic:
rw [← insert_erase (mem_support.2 hx.1), support_swap_mul_eq _ _ h1,
            card_insert_of_not_mem (not_mem_erase _ _), sdiff_singleton_eq_erase]
theorem IsCycle.sign {f : Perm α} (hf : IsCycle f) : sign f = -(-1) ^ f.support.card :=
  let ⟨x, hx⟩ := hf
  calc
    Perm.sign f = Perm.sign (swap x (f x) * (swap x (f x) * f)) := by
      {rw [← mul_assoc, mul_def, mul_def, swap_swap, trans_refl]}
    _ = -(-1) ^ f.support.card :=
      if h1 : f (f x) = x then by
        have h : swap x (f x) * f = 1 := by
          simp only [mul_def, one_def]
          rw [hf.eq_swap_of_apply_apply_eq_self hx.1 h1, swap_apply_left, swap_swap]
        rw [sign_mul, sign_swap hx.1.symm, h, sign_one,
          hf.eq_swap_of_apply_apply_eq_self hx.1 h1, card_support_swap hx.1.symm]
        rfl
      else by
        have h : card (support (swap x (f x) * f)) + 1 = card (support f) := by
          rw [← insert_erase (mem_support.2 hx.1), support_swap_mul_eq _ _ h1,
            card_insert_of_not_mem (not_mem_erase _ _), sdiff_singleton_eq_erase]
        

Proof state:
ι : Type u_1
α : Type u_2
β : Type u_3
f✝ g : Perm α
x✝ y : α
inst✝¹ : DecidableEq α
inst✝ : Fintype α
f : Perm α
hf : IsCycle f
x : α
hx : f x ≠ x ∧ ∀ ⦃y : α⦄, f y ≠ y → SameCycle f x y
h1 : ¬f (f x) = x
h : card (support (swap x (f x) * f)) + 1 = card (support f)
⊢ Perm.sign (swap x (f x) * (swap x (f x) * f)) = -(-1) ^ card (support f)

Next tactic:
have : card (support (swap x (f x) * f)) < card (support f) :=
          card_support_swap_mul hx.1
theorem IsCycle.sign {f : Perm α} (hf : IsCycle f) : sign f = -(-1) ^ f.support.card :=
  let ⟨x, hx⟩ := hf
  calc
    Perm.sign f = Perm.sign (swap x (f x) * (swap x (f x) * f)) := by
      {rw [← mul_assoc, mul_def, mul_def, swap_swap, trans_refl]}
    _ = -(-1) ^ f.support.card :=
      if h1 : f (f x) = x then by
        have h : swap x (f x) * f = 1 := by
          simp only [mul_def, one_def]
          rw [hf.eq_swap_of_apply_apply_eq_self hx.1 h1, swap_apply_left, swap_swap]
        rw [sign_mul, sign_swap hx.1.symm, h, sign_one,
          hf.eq_swap_of_apply_apply_eq_self hx.1 h1, card_support_swap hx.1.symm]
        rfl
      else by
        have h : card (support (swap x (f x) * f)) + 1 = card (support f) := by
          rw [← insert_erase (mem_support.2 hx.1), support_swap_mul_eq _ _ h1,
            card_insert_of_not_mem (not_mem_erase _ _), sdiff_singleton_eq_erase]
        have : card (support (swap x (f x) * f)) < card (support f) :=
          card_support_swap_mul hx.1
        

Proof state:
ι : Type u_1
α : Type u_2
β : Type u_3
f✝ g : Perm α
x✝ y : α
inst✝¹ : DecidableEq α
inst✝ : Fintype α
f : Perm α
hf : IsCycle f
x : α
hx : f x ≠ x ∧ ∀ ⦃y : α⦄, f y ≠ y → SameCycle f x y
h1 : ¬f (f x) = x
h : card (support (swap x (f x) * f)) + 1 = card (support f)
this : card (support (swap x (f x) * f)) < card (support f)
⊢ Perm.sign (swap x (f x) * (swap x (f x) * f)) = -(-1) ^ card (support f)

Next tactic:
rw [sign_mul, sign_swap hx.1.symm, (hf.swap_mul hx.1 h1).sign, ← h]
theorem IsCycle.sign {f : Perm α} (hf : IsCycle f) : sign f = -(-1) ^ f.support.card :=
  let ⟨x, hx⟩ := hf
  calc
    Perm.sign f = Perm.sign (swap x (f x) * (swap x (f x) * f)) := by
      {rw [← mul_assoc, mul_def, mul_def, swap_swap, trans_refl]}
    _ = -(-1) ^ f.support.card :=
      if h1 : f (f x) = x then by
        have h : swap x (f x) * f = 1 := by
          simp only [mul_def, one_def]
          rw [hf.eq_swap_of_apply_apply_eq_self hx.1 h1, swap_apply_left, swap_swap]
        rw [sign_mul, sign_swap hx.1.symm, h, sign_one,
          hf.eq_swap_of_apply_apply_eq_self hx.1 h1, card_support_swap hx.1.symm]
        rfl
      else by
        have h : card (support (swap x (f x) * f)) + 1 = card (support f) := by
          rw [← insert_erase (mem_support.2 hx.1), support_swap_mul_eq _ _ h1,
            card_insert_of_not_mem (not_mem_erase _ _), sdiff_singleton_eq_erase]
        have : card (support (swap x (f x) * f)) < card (support f) :=
          card_support_swap_mul hx.1
        rw [sign_mul, sign_swap hx.1.symm, (hf.swap_mul hx.1 h1).sign, ← h]
        

Proof state:
ι : Type u_1
α : Type u_2
β : Type u_3
f✝ g : Perm α
x✝ y : α
inst✝¹ : DecidableEq α
inst✝ : Fintype α
f : Perm α
hf : IsCycle f
x : α
hx : f x ≠ x ∧ ∀ ⦃y : α⦄, f y ≠ y → SameCycle f x y
h1 : ¬f (f x) = x
h : card (support (swap x (f x) * f)) + 1 = card (support f)
this : card (support (swap x (f x) * f)) < card (support f)
⊢ -1 * -(-1) ^ card (support (swap x (f x) * f)) = -(-1) ^ (card (support (swap x (f x) * f)) + 1)

Next tactic:
simp only [mul_neg, neg_mul, one_mul, neg_neg, pow_add, pow_one, mul_one]
theorem IsCycle.of_pow {n : ℕ} (h1 : IsCycle (f ^ n)) (h2 : f.support ⊆ (f ^ n).support) :
    IsCycle f := by
  

Proof state:
ι : Type u_1
α : Type u_2
β : Type u_3
f g : Perm α
x y : α
inst✝¹ : DecidableEq α
inst✝ : Fintype α
n : ℕ
h1 : IsCycle (f ^ n)
h2 : support f ⊆ support (f ^ n)
⊢ IsCycle f

Next tactic:
have key : ∀ x : α, (f ^ n) x ≠ x ↔ f x ≠ x := by
    simp_rw [← mem_support, ← Finset.ext_iff]
    exact (support_pow_le _ n).antisymm h2
theorem IsCycle.of_pow {n : ℕ} (h1 : IsCycle (f ^ n)) (h2 : f.support ⊆ (f ^ n).support) :
    IsCycle f := by
  have key : ∀ x : α, (f ^ n) x ≠ x ↔ f x ≠ x := by
    

Proof state:
ι : Type u_1
α : Type u_2
β : Type u_3
f g : Perm α
x y : α
inst✝¹ : DecidableEq α
inst✝ : Fintype α
n : ℕ
h1 : IsCycle (f ^ n)
h2 : support f ⊆ support (f ^ n)
⊢ ∀ (x : α), (f ^ n) x ≠ x ↔ f x ≠ x

Next tactic:
simp_rw [← mem_support, ← Finset.ext_iff]
theorem IsCycle.of_pow {n : ℕ} (h1 : IsCycle (f ^ n)) (h2 : f.support ⊆ (f ^ n).support) :
    IsCycle f := by
  have key : ∀ x : α, (f ^ n) x ≠ x ↔ f x ≠ x := by
    simp_rw [← mem_support, ← Finset.ext_iff]
    

Proof state:
ι : Type u_1
α : Type u_2
β : Type u_3
f g : Perm α
x y : α
inst✝¹ : DecidableEq α
inst✝ : Fintype α
n : ℕ
h1 : IsCycle (f ^ n)
h2 : support f ⊆ support (f ^ n)
⊢ support (f ^ n) = support f

Next tactic:
exact (support_pow_le _ n).antisymm h2
theorem IsCycle.of_pow {n : ℕ} (h1 : IsCycle (f ^ n)) (h2 : f.support ⊆ (f ^ n).support) :
    IsCycle f := by
  have key : ∀ x : α, (f ^ n) x ≠ x ↔ f x ≠ x := by
    simp_rw [← mem_support, ← Finset.ext_iff]
    exact (support_pow_le _ n).antisymm h2
  

Proof state:
ι : Type u_1
α : Type u_2
β : Type u_3
f g : Perm α
x y : α
inst✝¹ : DecidableEq α
inst✝ : Fintype α
n : ℕ
h1 : IsCycle (f ^ n)
h2 : support f ⊆ support (f ^ n)
key : ∀ (x : α), (f ^ n) x ≠ x ↔ f x ≠ x
⊢ IsCycle f

Next tactic:
obtain ⟨x, hx1, hx2⟩ := h1
theorem IsCycle.of_pow {n : ℕ} (h1 : IsCycle (f ^ n)) (h2 : f.support ⊆ (f ^ n).support) :
    IsCycle f := by
  have key : ∀ x : α, (f ^ n) x ≠ x ↔ f x ≠ x := by
    simp_rw [← mem_support, ← Finset.ext_iff]
    exact (support_pow_le _ n).antisymm h2
  obtain ⟨x, hx1, hx2⟩ := h1
  

Proof state:
case intro.intro
ι : Type u_1
α : Type u_2
β : Type u_3
f g : Perm α
x✝ y : α
inst✝¹ : DecidableEq α
inst✝ : Fintype α
n : ℕ
h2 : support f ⊆ support (f ^ n)
key : ∀ (x : α), (f ^ n) x ≠ x ↔ f x ≠ x
x : α
hx1 : (f ^ n) x ≠ x
hx2 : ∀ ⦃y : α⦄, (f ^ n) y ≠ y → SameCycle (f ^ n) x y
⊢ IsCycle f

Next tactic:
refine' ⟨x, (key x).mp hx1, fun y hy => _⟩
theorem IsCycle.of_pow {n : ℕ} (h1 : IsCycle (f ^ n)) (h2 : f.support ⊆ (f ^ n).support) :
    IsCycle f := by
  have key : ∀ x : α, (f ^ n) x ≠ x ↔ f x ≠ x := by
    simp_rw [← mem_support, ← Finset.ext_iff]
    exact (support_pow_le _ n).antisymm h2
  obtain ⟨x, hx1, hx2⟩ := h1
  refine' ⟨x, (key x).mp hx1, fun y hy => _⟩
  

Proof state:
case intro.intro
ι : Type u_1
α : Type u_2
β : Type u_3
f g : Perm α
x✝ y✝ : α
inst✝¹ : DecidableEq α
inst✝ : Fintype α
n : ℕ
h2 : support f ⊆ support (f ^ n)
key : ∀ (x : α), (f ^ n) x ≠ x ↔ f x ≠ x
x : α
hx1 : (f ^ n) x ≠ x
hx2 : ∀ ⦃y : α⦄, (f ^ n) y ≠ y → SameCycle (f ^ n) x y
y : α
hy : f y ≠ y
⊢ SameCycle f x y

Next tactic:
cases' hx2 ((key y).mpr hy) with i _
theorem IsCycle.of_pow {n : ℕ} (h1 : IsCycle (f ^ n)) (h2 : f.support ⊆ (f ^ n).support) :
    IsCycle f := by
  have key : ∀ x : α, (f ^ n) x ≠ x ↔ f x ≠ x := by
    simp_rw [← mem_support, ← Finset.ext_iff]
    exact (support_pow_le _ n).antisymm h2
  obtain ⟨x, hx1, hx2⟩ := h1
  refine' ⟨x, (key x).mp hx1, fun y hy => _⟩
  cases' hx2 ((key y).mpr hy) with i _
  

Proof state:
case intro.intro.intro
ι : Type u_1
α : Type u_2
β : Type u_3
f g : Perm α
x✝ y✝ : α
inst✝¹ : DecidableEq α
inst✝ : Fintype α
n : ℕ
h2 : support f ⊆ support (f ^ n)
key : ∀ (x : α), (f ^ n) x ≠ x ↔ f x ≠ x
x : α
hx1 : (f ^ n) x ≠ x
hx2 : ∀ ⦃y : α⦄, (f ^ n) y ≠ y → SameCycle (f ^ n) x y
y : α
hy : f y ≠ y
i : ℤ
h✝ : ((f ^ n) ^ i) x = y
⊢ SameCycle f x y

Next tactic:
exact ⟨n * i, by rwa [zpow_mul]⟩
theorem IsCycle.of_pow {n : ℕ} (h1 : IsCycle (f ^ n)) (h2 : f.support ⊆ (f ^ n).support) :
    IsCycle f := by
  have key : ∀ x : α, (f ^ n) x ≠ x ↔ f x ≠ x := by
    simp_rw [← mem_support, ← Finset.ext_iff]
    exact (support_pow_le _ n).antisymm h2
  obtain ⟨x, hx1, hx2⟩ := h1
  refine' ⟨x, (key x).mp hx1, fun y hy => _⟩
  cases' hx2 ((key y).mpr hy) with i _
  exact ⟨n * i, by 

Proof state:
ι : Type u_1
α : Type u_2
β : Type u_3
f g : Perm α
x✝ y✝ : α
inst✝¹ : DecidableEq α
inst✝ : Fintype α
n : ℕ
h2 : support f ⊆ support (f ^ n)
key : ∀ (x : α), (f ^ n) x ≠ x ↔ f x ≠ x
x : α
hx1 : (f ^ n) x ≠ x
hx2 : ∀ ⦃y : α⦄, (f ^ n) y ≠ y → SameCycle (f ^ n) x y
y : α
hy : f y ≠ y
i : ℤ
h✝ : ((f ^ n) ^ i) x = y
⊢ (f ^ (↑n * i)) x = y

Next tactic:
rwa [zpow_mul]
theorem IsCycle.of_zpow {n : ℤ} (h1 : IsCycle (f ^ n)) (h2 : f.support ⊆ (f ^ n).support) :
    IsCycle f := by
  

Proof state:
ι : Type u_1
α : Type u_2
β : Type u_3
f g : Perm α
x y : α
inst✝¹ : DecidableEq α
inst✝ : Fintype α
n : ℤ
h1 : IsCycle (f ^ n)
h2 : support f ⊆ support (f ^ n)
⊢ IsCycle f

Next tactic:
cases n
theorem IsCycle.of_zpow {n : ℤ} (h1 : IsCycle (f ^ n)) (h2 : f.support ⊆ (f ^ n).support) :
    IsCycle f := by
  cases n
  · 

Proof state:
case ofNat
ι : Type u_1
α : Type u_2
β : Type u_3
f g : Perm α
x y : α
inst✝¹ : DecidableEq α
inst✝ : Fintype α
a✝ : ℕ
h1 : IsCycle (f ^ Int.ofNat a✝)
h2 : support f ⊆ support (f ^ Int.ofNat a✝)
⊢ IsCycle f

Next tactic:
exact h1.of_pow h2
theorem IsCycle.of_zpow {n : ℤ} (h1 : IsCycle (f ^ n)) (h2 : f.support ⊆ (f ^ n).support) :
    IsCycle f := by
  cases n
  · exact h1.of_pow h2
  · 

Proof state:
case negSucc
ι : Type u_1
α : Type u_2
β : Type u_3
f g : Perm α
x y : α
inst✝¹ : DecidableEq α
inst✝ : Fintype α
a✝ : ℕ
h1 : IsCycle (f ^ Int.negSucc a✝)
h2 : support f ⊆ support (f ^ Int.negSucc a✝)
⊢ IsCycle f

Next tactic:
simp only [le_eq_subset, zpow_negSucc, Perm.support_inv] at h1 h2
theorem IsCycle.of_zpow {n : ℤ} (h1 : IsCycle (f ^ n)) (h2 : f.support ⊆ (f ^ n).support) :
    IsCycle f := by
  cases n
  · exact h1.of_pow h2
  · simp only [le_eq_subset, zpow_negSucc, Perm.support_inv] at h1 h2
    

Proof state:
case negSucc
ι : Type u_1
α : Type u_2
β : Type u_3
f g : Perm α
x y : α
inst✝¹ : DecidableEq α
inst✝ : Fintype α
a✝ : ℕ
h1 : IsCycle (f ^ (a✝ + 1))⁻¹
h2 : support f ⊆ support (f ^ (a✝ + 1))
⊢ IsCycle f

Next tactic:
exact (inv_inv (f ^ _) ▸ h1.inv).of_pow h2
/-- Unlike `support_congr`, which assumes that `∀ (x ∈ g.support), f x = g x)`, here
we have the weaker assumption that `∀ (x ∈ f.support), f x = g x`. -/
theorem IsCycle.support_congr (hf : IsCycle f) (hg : IsCycle g) (h : f.support ⊆ g.support)
    (h' : ∀ x ∈ f.support, f x = g x) : f = g := by
  

Proof state:
ι : Type u_1
α : Type u_2
β : Type u_3
f g : Perm α
x y : α
inst✝¹ : DecidableEq α
inst✝ : Fintype α
hf : IsCycle f
hg : IsCycle g
h : support f ⊆ support g
h' : ∀ x ∈ support f, f x = g x
⊢ f = g

Next tactic:
have : f.support = g.support := by
    refine' le_antisymm h _
    intro z hz
    obtain ⟨x, hx, _⟩ := id hf
    have hx' : g x ≠ x := by rwa [← h' x (mem_support.mpr hx)]
    obtain ⟨m, hm⟩ := hg.exists_pow_eq hx' (mem_support.mp hz)
    have h'' : ∀ x ∈ f.support ∩ g.support, f x = g x := by
      intro x hx
      exact h' x (mem_of_mem_inter_left hx)
    rwa [← hm, ←
      pow_eq_on_of_mem_support h'' _ x
        (mem_inter_of_mem (mem_support.mpr hx) (mem_support.mpr hx')),
      pow_apply_mem_support, mem_support]
/-- Unlike `support_congr`, which assumes that `∀ (x ∈ g.support), f x = g x)`, here
we have the weaker assumption that `∀ (x ∈ f.support), f x = g x`. -/
theorem IsCycle.support_congr (hf : IsCycle f) (hg : IsCycle g) (h : f.support ⊆ g.support)
    (h' : ∀ x ∈ f.support, f x = g x) : f = g := by
  have : f.support = g.support := by
    

Proof state:
ι : Type u_1
α : Type u_2
β : Type u_3
f g : Perm α
x y : α
inst✝¹ : DecidableEq α
inst✝ : Fintype α
hf : IsCycle f
hg : IsCycle g
h : support f ⊆ support g
h' : ∀ x ∈ support f, f x = g x
⊢ support f = support g

Next tactic:
refine' le_antisymm h _
/-- Unlike `support_congr`, which assumes that `∀ (x ∈ g.support), f x = g x)`, here
we have the weaker assumption that `∀ (x ∈ f.support), f x = g x`. -/
theorem IsCycle.support_congr (hf : IsCycle f) (hg : IsCycle g) (h : f.support ⊆ g.support)
    (h' : ∀ x ∈ f.support, f x = g x) : f = g := by
  have : f.support = g.support := by
    refine' le_antisymm h _
    

Proof state:
ι : Type u_1
α : Type u_2
β : Type u_3
f g : Perm α
x y : α
inst✝¹ : DecidableEq α
inst✝ : Fintype α
hf : IsCycle f
hg : IsCycle g
h : support f ⊆ support g
h' : ∀ x ∈ support f, f x = g x
⊢ support g ≤ support f

Next tactic:
intro z hz