l3lab/ntp-mathlib huggingface dataset:
/-- A recursor for pairs of lists. To have `C l₁ l₂` for all `l₁`, `l₂`, it suffices to have it for
`l₂ = []` and to be able to pour the elements of `l₁` into `l₂`. -/
def permutationsAux.rec {C : List α → List α → Sort v} (H0 : ∀ is, C [] is)
    (H1 : ∀ t ts is, C ts (t :: is) → C is [] → C (t :: ts) is) : ∀ l₁ l₂, C l₁ l₂
  | [], is => H0 is
  | t :: ts, is =>
      H1 t ts is (permutationsAux.rec H0 H1 ts (t :: is)) (permutationsAux.rec H0 H1 is [])
  termination_by _ ts is => (length ts + length is, length ts)
  decreasing_by 

Proof state:
α : Type u_1
t : α
ts is : List α
⊢ (invImage (fun a => PSigma.casesOn a fun ts snd => (length ts + length snd, length ts))
        Prod.instWellFoundedRelationProd).1
    { fst := ts, snd := t :: is } { fst := t :: ts, snd := is }

Next tactic:
simp_wf
/-- A recursor for pairs of lists. To have `C l₁ l₂` for all `l₁`, `l₂`, it suffices to have it for
`l₂ = []` and to be able to pour the elements of `l₁` into `l₂`. -/
def permutationsAux.rec {C : List α → List α → Sort v} (H0 : ∀ is, C [] is)
    (H1 : ∀ t ts is, C ts (t :: is) → C is [] → C (t :: ts) is) : ∀ l₁ l₂, C l₁ l₂
  | [], is => H0 is
  | t :: ts, is =>
      H1 t ts is (permutationsAux.rec H0 H1 ts (t :: is)) (permutationsAux.rec H0 H1 is [])
  termination_by _ ts is => (length ts + length is, length ts)
  decreasing_by simp_wf; 

Proof state:
α : Type u_1
t : α
ts is : List α
⊢ Prod.Lex (fun a₁ a₂ => a₁ < a₂) (fun a₁ a₂ => a₁ < a₂) (length ts + succ (length is), length ts)
    (succ (length ts) + length is, succ (length ts))

Next tactic:
simp [Nat.succ_add]
/-- A recursor for pairs of lists. To have `C l₁ l₂` for all `l₁`, `l₂`, it suffices to have it for
`l₂ = []` and to be able to pour the elements of `l₁` into `l₂`. -/
def permutationsAux.rec {C : List α → List α → Sort v} (H0 : ∀ is, C [] is)
    (H1 : ∀ t ts is, C ts (t :: is) → C is [] → C (t :: ts) is) : ∀ l₁ l₂, C l₁ l₂
  | [], is => H0 is
  | t :: ts, is =>
      H1 t ts is (permutationsAux.rec H0 H1 ts (t :: is)) (permutationsAux.rec H0 H1 is [])
  termination_by _ ts is => (length ts + length is, length ts)
  decreasing_by simp_wf; simp [Nat.succ_add]; 

Proof state:
α : Type u_1
t : α
ts is : List α
⊢ Prod.Lex (fun a₁ a₂ => a₁ < a₂) (fun a₁ a₂ => a₁ < a₂) (length ts + succ (length is), length ts)
    (succ (length ts + length is), succ (length ts))

Next tactic:
decreasing_tactic
/-- A recursor for pairs of lists. To have `C l₁ l₂` for all `l₁`, `l₂`, it suffices to have it for
`l₂ = []` and to be able to pour the elements of `l₁` into `l₂`. -/
def permutationsAux.rec {C : List α → List α → Sort v} (H0 : ∀ is, C [] is)
    (H1 : ∀ t ts is, C ts (t :: is) → C is [] → C (t :: ts) is) : ∀ l₁ l₂, C l₁ l₂
  | [], is => H0 is
  | t :: ts, is =>
      H1 t ts is (permutationsAux.rec H0 H1 ts (t :: is)) (permutationsAux.rec H0 H1 is [])
  termination_by _ ts is => (length ts + length is, length ts)
  decreasing_by 

Proof state:
α : Type u_1
t : α
ts is : List α
⊢ (invImage (fun a => PSigma.casesOn a fun ts snd => (length ts + length snd, length ts))
        Prod.instWellFoundedRelationProd).1
    { fst := is, snd := [] } { fst := t :: ts, snd := is }

Next tactic:
simp_wf
/-- A recursor for pairs of lists. To have `C l₁ l₂` for all `l₁`, `l₂`, it suffices to have it for
`l₂ = []` and to be able to pour the elements of `l₁` into `l₂`. -/
def permutationsAux.rec {C : List α → List α → Sort v} (H0 : ∀ is, C [] is)
    (H1 : ∀ t ts is, C ts (t :: is) → C is [] → C (t :: ts) is) : ∀ l₁ l₂, C l₁ l₂
  | [], is => H0 is
  | t :: ts, is =>
      H1 t ts is (permutationsAux.rec H0 H1 ts (t :: is)) (permutationsAux.rec H0 H1 is [])
  termination_by _ ts is => (length ts + length is, length ts)
  decreasing_by simp_wf; 

Proof state:
α : Type u_1
t : α
ts is : List α
⊢ Prod.Lex (fun a₁ a₂ => a₁ < a₂) (fun a₁ a₂ => a₁ < a₂) (length is, length is)
    (succ (length ts) + length is, succ (length ts))

Next tactic:
simp [Nat.succ_add]
/-- A recursor for pairs of lists. To have `C l₁ l₂` for all `l₁`, `l₂`, it suffices to have it for
`l₂ = []` and to be able to pour the elements of `l₁` into `l₂`. -/
def permutationsAux.rec {C : List α → List α → Sort v} (H0 : ∀ is, C [] is)
    (H1 : ∀ t ts is, C ts (t :: is) → C is [] → C (t :: ts) is) : ∀ l₁ l₂, C l₁ l₂
  | [], is => H0 is
  | t :: ts, is =>
      H1 t ts is (permutationsAux.rec H0 H1 ts (t :: is)) (permutationsAux.rec H0 H1 is [])
  termination_by _ ts is => (length ts + length is, length ts)
  decreasing_by simp_wf; simp [Nat.succ_add]; 

Proof state:
α : Type u_1
t : α
ts is : List α
⊢ Prod.Lex (fun a₁ a₂ => a₁ < a₂) (fun a₁ a₂ => a₁ < a₂) (length is, length is)
    (succ (length ts + length is), succ (length ts))

Next tactic:
decreasing_tactic
instance decidableChain [DecidableRel R] (a : α) (l : List α) :
    Decidable (Chain R a l) := by
  

Proof state:
α : Type u_1
β : Type u_2
γ : Type u_3
δ : Type u_4
ε : Type u_5
ζ : Type u_6
R : α → α → Prop
inst✝ : DecidableRel R
a : α
l : List α
⊢ Decidable (Chain R a l)

Next tactic:
induction l generalizing a with
  | nil => simp only [List.Chain.nil]; infer_instance
  | cons a as ih => haveI := ih; simp only [List.chain_cons]; infer_instance
instance decidableChain [DecidableRel R] (a : α) (l : List α) :
    Decidable (Chain R a l) := by
  induction l generalizing a with
  

Proof state:
case nil
α : Type u_1
β : Type u_2
γ : Type u_3
δ : Type u_4
ε : Type u_5
ζ : Type u_6
R : α → α → Prop
inst✝ : DecidableRel R
a : α
⊢ Decidable (Chain R a [])

Next tactic:
| nil => simp only [List.Chain.nil]; infer_instance
instance decidableChain [DecidableRel R] (a : α) (l : List α) :
    Decidable (Chain R a l) := by
  induction l generalizing a with
  | nil => 

Proof state:
case nil
α : Type u_1
β : Type u_2
γ : Type u_3
δ : Type u_4
ε : Type u_5
ζ : Type u_6
R : α → α → Prop
inst✝ : DecidableRel R
a : α
⊢ Decidable (Chain R a [])

Next tactic:
simp only [List.Chain.nil]
instance decidableChain [DecidableRel R] (a : α) (l : List α) :
    Decidable (Chain R a l) := by
  induction l generalizing a with
  | nil => simp only [List.Chain.nil]; 

Proof state:
case nil
α : Type u_1
β : Type u_2
γ : Type u_3
δ : Type u_4
ε : Type u_5
ζ : Type u_6
R : α → α → Prop
inst✝ : DecidableRel R
a : α
⊢ Decidable True

Next tactic:
infer_instance
instance decidableChain [DecidableRel R] (a : α) (l : List α) :
    Decidable (Chain R a l) := by
  induction l generalizing a with
  | nil => simp only [List.Chain.nil]; infer_instance
  

Proof state:
case cons
α : Type u_1
β : Type u_2
γ : Type u_3
δ : Type u_4
ε : Type u_5
ζ : Type u_6
R : α → α → Prop
inst✝ : DecidableRel R
a✝ : α
as : List α
ih : (a : α) → Decidable (Chain R a as)
a : α
⊢ Decidable (Chain R a (a✝ :: as))

Next tactic:
| cons a as ih => haveI := ih; simp only [List.chain_cons]; infer_instance
instance decidableChain [DecidableRel R] (a : α) (l : List α) :
    Decidable (Chain R a l) := by
  induction l generalizing a with
  | nil => simp only [List.Chain.nil]; infer_instance
  | cons a as ih => 

Proof state:
case cons
α : Type u_1
β : Type u_2
γ : Type u_3
δ : Type u_4
ε : Type u_5
ζ : Type u_6
R : α → α → Prop
inst✝ : DecidableRel R
a✝ : α
as : List α
ih : (a : α) → Decidable (Chain R a as)
a : α
⊢ Decidable (Chain R a (a✝ :: as))

Next tactic:
haveI := ih
instance decidableChain [DecidableRel R] (a : α) (l : List α) :
    Decidable (Chain R a l) := by
  induction l generalizing a with
  | nil => simp only [List.Chain.nil]; infer_instance
  | cons a as ih => haveI := ih; 

Proof state:
case cons
α : Type u_1
β : Type u_2
γ : Type u_3
δ : Type u_4
ε : Type u_5
ζ : Type u_6
R : α → α → Prop
inst✝ : DecidableRel R
a✝ : α
as : List α
ih : (a : α) → Decidable (Chain R a as)
a : α
this : (a : α) → Decidable (Chain R a as)
⊢ Decidable (Chain R a (a✝ :: as))

Next tactic:
simp only [List.chain_cons]
instance decidableChain [DecidableRel R] (a : α) (l : List α) :
    Decidable (Chain R a l) := by
  induction l generalizing a with
  | nil => simp only [List.Chain.nil]; infer_instance
  | cons a as ih => haveI := ih; simp only [List.chain_cons]; 

Proof state:
case cons
α : Type u_1
β : Type u_2
γ : Type u_3
δ : Type u_4
ε : Type u_5
ζ : Type u_6
R : α → α → Prop
inst✝ : DecidableRel R
a✝ : α
as : List α
ih : (a : α) → Decidable (Chain R a as)
a : α
this : (a : α) → Decidable (Chain R a as)
⊢ Decidable (R a a✝ ∧ Chain R a✝ as)

Next tactic:
infer_instance
instance decidableChain' [DecidableRel R] (l : List α) : Decidable (Chain' R l) := by
  

Proof state:
α : Type u_1
β : Type u_2
γ : Type u_3
δ : Type u_4
ε : Type u_5
ζ : Type u_6
R : α → α → Prop
inst✝ : DecidableRel R
l : List α
⊢ Decidable (Chain' R l)

Next tactic:
cases l
instance decidableChain' [DecidableRel R] (l : List α) : Decidable (Chain' R l) := by
  cases l <;> 

Proof state:
case nil
α : Type u_1
β : Type u_2
γ : Type u_3
δ : Type u_4
ε : Type u_5
ζ : Type u_6
R : α → α → Prop
inst✝ : DecidableRel R
⊢ Decidable (Chain' R [])

Next tactic:
dsimp only [List.Chain']
instance decidableChain' [DecidableRel R] (l : List α) : Decidable (Chain' R l) := by
  cases l <;> 

Proof state:
case cons
α : Type u_1
β : Type u_2
γ : Type u_3
δ : Type u_4
ε : Type u_5
ζ : Type u_6
R : α → α → Prop
inst✝ : DecidableRel R
head✝ : α
tail✝ : List α
⊢ Decidable (Chain' R (head✝ :: tail✝))

Next tactic:
dsimp only [List.Chain']
instance decidableChain' [DecidableRel R] (l : List α) : Decidable (Chain' R l) := by
  cases l <;> dsimp only [List.Chain'] <;> 

Proof state:
case nil
α : Type u_1
β : Type u_2
γ : Type u_3
δ : Type u_4
ε : Type u_5
ζ : Type u_6
R : α → α → Prop
inst✝ : DecidableRel R
⊢ Decidable True

Next tactic:
infer_instance
instance decidableChain' [DecidableRel R] (l : List α) : Decidable (Chain' R l) := by
  cases l <;> dsimp only [List.Chain'] <;> 

Proof state:
case cons
α : Type u_1
β : Type u_2
γ : Type u_3
δ : Type u_4
ε : Type u_5
ζ : Type u_6
R : α → α → Prop
inst✝ : DecidableRel R
head✝ : α
tail✝ : List α
⊢ Decidable (Chain R head✝ tail✝)

Next tactic:
infer_instance
/-- Grade involution, inverting the sign of each basis vector. -/
def involute : CliffordAlgebra Q →ₐ[R] CliffordAlgebra Q :=
  CliffordAlgebra.lift Q ⟨-ι Q, fun m => by 

Proof state:
R : Type u_1
inst✝² : CommRing R
M : Type u_2
inst✝¹ : AddCommGroup M
inst✝ : Module R M
Q : QuadraticForm R M
m : M
⊢ (-ι Q) m * (-ι Q) m = (algebraMap R (CliffordAlgebra Q)) (Q m)

Next tactic:
simp
@[simp]
theorem involute_comp_involute : involute.comp involute = AlgHom.id R (CliffordAlgebra Q) := by
  

Proof state:
R : Type u_1
inst✝² : CommRing R
M : Type u_2
inst✝¹ : AddCommGroup M
inst✝ : Module R M
Q : QuadraticForm R M
⊢ AlgHom.comp involute involute = AlgHom.id R (CliffordAlgebra Q)

Next tactic:
ext
@[simp]
theorem involute_comp_involute : involute.comp involute = AlgHom.id R (CliffordAlgebra Q) := by
  ext; 

Proof state:
case a.h
R : Type u_1
inst✝² : CommRing R
M : Type u_2
inst✝¹ : AddCommGroup M
inst✝ : Module R M
Q : QuadraticForm R M
x✝ : M
⊢ (AlgHom.toLinearMap (AlgHom.comp involute involute) ∘ₗ ι Q) x✝ =
    (AlgHom.toLinearMap (AlgHom.id R (CliffordAlgebra Q)) ∘ₗ ι Q) x✝

Next tactic:
simp
/-- `CliffordAlgebra.reverse` as an `AlgHom` to the opposite algebra -/
def reverseOp : CliffordAlgebra Q →ₐ[R] (CliffordAlgebra Q)ᵐᵒᵖ :=
  CliffordAlgebra.lift Q
    ⟨(MulOpposite.opLinearEquiv R).toLinearMap ∘ₗ ι Q, fun m => unop_injective <| by 

Proof state:
R : Type u_1
inst✝² : CommRing R
M : Type u_2
inst✝¹ : AddCommGroup M
inst✝ : Module R M
Q : QuadraticForm R M
m : M
⊢ unop ((↑(opLinearEquiv R) ∘ₗ ι Q) m * (↑(opLinearEquiv R) ∘ₗ ι Q) m) =
    unop ((algebraMap R (CliffordAlgebra Q)ᵐᵒᵖ) (Q m))

Next tactic:
simp
/-- `CliffordAlgebra.reverseEquiv` as an `AlgEquiv` to the opposite algebra -/
@[simps! apply]
def reverseOpEquiv : CliffordAlgebra Q ≃ₐ[R] (CliffordAlgebra Q)ᵐᵒᵖ :=
  AlgEquiv.ofAlgHom reverseOp (AlgHom.opComm reverseOp)
    (AlgHom.unop.injective <| hom_ext <| LinearMap.ext <| fun _ => by 

Proof state:
R : Type u_1
inst✝² : CommRing R
M : Type u_2
inst✝¹ : AddCommGroup M
inst✝ : Module R M
Q : QuadraticForm R M
x✝ : M
⊢ (AlgHom.toLinearMap (AlgHom.unop (AlgHom.comp reverseOp (AlgHom.opComm reverseOp))) ∘ₗ ι Q) x✝ =
    (AlgHom.toLinearMap (AlgHom.unop (AlgHom.id R (CliffordAlgebra Q)ᵐᵒᵖ)) ∘ₗ ι Q) x✝

Next tactic:
simp
/-- `CliffordAlgebra.reverseEquiv` as an `AlgEquiv` to the opposite algebra -/
@[simps! apply]
def reverseOpEquiv : CliffordAlgebra Q ≃ₐ[R] (CliffordAlgebra Q)ᵐᵒᵖ :=
  AlgEquiv.ofAlgHom reverseOp (AlgHom.opComm reverseOp)
    (AlgHom.unop.injective <| hom_ext <| LinearMap.ext <| fun _ => by simp)
    (hom_ext <| LinearMap.ext <| fun _ => by 

Proof state:
R : Type u_1
inst✝² : CommRing R
M : Type u_2
inst✝¹ : AddCommGroup M
inst✝ : Module R M
Q : QuadraticForm R M
x✝ : M
⊢ (AlgHom.toLinearMap (AlgHom.comp (AlgHom.opComm reverseOp) reverseOp) ∘ₗ ι Q) x✝ =
    (AlgHom.toLinearMap (AlgHom.id R (CliffordAlgebra Q)) ∘ₗ ι Q) x✝

Next tactic:
simp
@[simp]
theorem reverse_ι (m : M) : reverse (ι Q m) = ι Q m := by 

Proof state:
R : Type u_1
inst✝² : CommRing R
M : Type u_2
inst✝¹ : AddCommGroup M
inst✝ : Module R M
Q : QuadraticForm R M
m : M
⊢ reverse ((ι Q) m) = (ι Q) m

Next tactic:
simp [reverse]
theorem reverse_comp_involute :
    reverse.comp involute.toLinearMap =
      (involute.toLinearMap.comp reverse : _ →ₗ[R] CliffordAlgebra Q) := by
  

Proof state:
R : Type u_1
inst✝² : CommRing R
M : Type u_2
inst✝¹ : AddCommGroup M
inst✝ : Module R M
Q : QuadraticForm R M
⊢ reverse ∘ₗ AlgHom.toLinearMap involute = AlgHom.toLinearMap involute ∘ₗ reverse

Next tactic:
ext x
theorem reverse_comp_involute :
    reverse.comp involute.toLinearMap =
      (involute.toLinearMap.comp reverse : _ →ₗ[R] CliffordAlgebra Q) := by
  ext x
  

Proof state:
case h
R : Type u_1
inst✝² : CommRing R
M : Type u_2
inst✝¹ : AddCommGroup M
inst✝ : Module R M
Q : QuadraticForm R M
x : CliffordAlgebra Q
⊢ (reverse ∘ₗ AlgHom.toLinearMap involute) x = (AlgHom.toLinearMap involute ∘ₗ reverse) x

Next tactic:
simp only [LinearMap.comp_apply, AlgHom.toLinearMap_apply]
theorem reverse_comp_involute :
    reverse.comp involute.toLinearMap =
      (involute.toLinearMap.comp reverse : _ →ₗ[R] CliffordAlgebra Q) := by
  ext x
  simp only [LinearMap.comp_apply, AlgHom.toLinearMap_apply]
  

Proof state:
case h
R : Type u_1
inst✝² : CommRing R
M : Type u_2
inst✝¹ : AddCommGroup M
inst✝ : Module R M
Q : QuadraticForm R M
x : CliffordAlgebra Q
⊢ reverse (involute x) = involute (reverse x)

Next tactic:
induction x using CliffordAlgebra.induction
theorem reverse_comp_involute :
    reverse.comp involute.toLinearMap =
      (involute.toLinearMap.comp reverse : _ →ₗ[R] CliffordAlgebra Q) := by
  ext x
  simp only [LinearMap.comp_apply, AlgHom.toLinearMap_apply]
  induction x using CliffordAlgebra.induction
  

Proof state:
case h.h_grade0
R : Type u_1
inst✝² : CommRing R
M : Type u_2
inst✝¹ : AddCommGroup M
inst✝ : Module R M
Q : QuadraticForm R M
r✝ : R
⊢ reverse (involute ((algebraMap R (CliffordAlgebra Q)) r✝)) =
    involute (reverse ((algebraMap R (CliffordAlgebra Q)) r✝))
case h.h_grade1
R : Type u_1
inst✝² : CommRing R
M : Type u_2
inst✝¹ : AddCommGroup M
inst✝ : Module R M
Q : QuadraticForm R M
x✝ : M
⊢ reverse (involute ((ι Q) x✝)) = involute (reverse ((ι Q) x✝))
case h.h_mul
R : Type u_1
inst✝² : CommRing R
M : Type u_2
inst✝¹ : AddCommGroup M
inst✝ : Module R M
Q : QuadraticForm R M
a✝² b✝ : CliffordAlgebra Q
a✝¹ : reverse (involute a✝²) = involute (reverse a✝²)
a✝ : reverse (involute b✝) = involute (reverse b✝)
⊢ reverse (involute (a✝² * b✝)) = involute (reverse (a✝² * b✝))
case h.h_add
R : Type u_1
inst✝² : CommRing R
M : Type u_2
inst✝¹ : AddCommGroup M
inst✝ : Module R M
Q : QuadraticForm R M
a✝² b✝ : CliffordAlgebra Q
a✝¹ : reverse (involute a✝²) = involute (reverse a✝²)
a✝ : reverse (involute b✝) = involute (reverse b✝)
⊢ reverse (involute (a✝² + b✝)) = involute (reverse (a✝² + b✝))

Next tactic:
case h_grade0 => simp
theorem reverse_comp_involute :
    reverse.comp involute.toLinearMap =
      (involute.toLinearMap.comp reverse : _ →ₗ[R] CliffordAlgebra Q) := by
  ext x
  simp only [LinearMap.comp_apply, AlgHom.toLinearMap_apply]
  induction x using CliffordAlgebra.induction
  

Proof state:
R : Type u_1
inst✝² : CommRing R
M : Type u_2
inst✝¹ : AddCommGroup M
inst✝ : Module R M
Q : QuadraticForm R M
r✝ : R
⊢ reverse (involute ((algebraMap R (CliffordAlgebra Q)) r✝)) =
    involute (reverse ((algebraMap R (CliffordAlgebra Q)) r✝))

Next tactic:
case h_grade0 => simp
theorem reverse_comp_involute :
    reverse.comp involute.toLinearMap =
      (involute.toLinearMap.comp reverse : _ →ₗ[R] CliffordAlgebra Q) := by
  ext x
  simp only [LinearMap.comp_apply, AlgHom.toLinearMap_apply]
  induction x using CliffordAlgebra.induction
  case h_grade0 => 

Proof state:
R : Type u_1
inst✝² : CommRing R
M : Type u_2
inst✝¹ : AddCommGroup M
inst✝ : Module R M
Q : QuadraticForm R M
r✝ : R
⊢ reverse (involute ((algebraMap R (CliffordAlgebra Q)) r✝)) =
    involute (reverse ((algebraMap R (CliffordAlgebra Q)) r✝))

Next tactic:
simp
theorem reverse_comp_involute :
    reverse.comp involute.toLinearMap =
      (involute.toLinearMap.comp reverse : _ →ₗ[R] CliffordAlgebra Q) := by
  ext x
  simp only [LinearMap.comp_apply, AlgHom.toLinearMap_apply]
  induction x using CliffordAlgebra.induction
  case h_grade0 => simp
  

Proof state:
case h.h_grade1
R : Type u_1
inst✝² : CommRing R
M : Type u_2
inst✝¹ : AddCommGroup M
inst✝ : Module R M
Q : QuadraticForm R M
x✝ : M
⊢ reverse (involute ((ι Q) x✝)) = involute (reverse ((ι Q) x✝))
case h.h_mul
R : Type u_1
inst✝² : CommRing R
M : Type u_2
inst✝¹ : AddCommGroup M
inst✝ : Module R M
Q : QuadraticForm R M
a✝² b✝ : CliffordAlgebra Q
a✝¹ : reverse (involute a✝²) = involute (reverse a✝²)
a✝ : reverse (involute b✝) = involute (reverse b✝)
⊢ reverse (involute (a✝² * b✝)) = involute (reverse (a✝² * b✝))
case h.h_add
R : Type u_1
inst✝² : CommRing R
M : Type u_2
inst✝¹ : AddCommGroup M
inst✝ : Module R M
Q : QuadraticForm R M
a✝² b✝ : CliffordAlgebra Q
a✝¹ : reverse (involute a✝²) = involute (reverse a✝²)
a✝ : reverse (involute b✝) = involute (reverse b✝)
⊢ reverse (involute (a✝² + b✝)) = involute (reverse (a✝² + b✝))

Next tactic:
case h_grade1 => simp
theorem reverse_comp_involute :
    reverse.comp involute.toLinearMap =
      (involute.toLinearMap.comp reverse : _ →ₗ[R] CliffordAlgebra Q) := by
  ext x
  simp only [LinearMap.comp_apply, AlgHom.toLinearMap_apply]
  induction x using CliffordAlgebra.induction
  case h_grade0 => simp
  

Proof state:
R : Type u_1
inst✝² : CommRing R
M : Type u_2
inst✝¹ : AddCommGroup M
inst✝ : Module R M
Q : QuadraticForm R M
x✝ : M
⊢ reverse (involute ((ι Q) x✝)) = involute (reverse ((ι Q) x✝))

Next tactic:
case h_grade1 => simp
theorem reverse_comp_involute :
    reverse.comp involute.toLinearMap =
      (involute.toLinearMap.comp reverse : _ →ₗ[R] CliffordAlgebra Q) := by
  ext x
  simp only [LinearMap.comp_apply, AlgHom.toLinearMap_apply]
  induction x using CliffordAlgebra.induction
  case h_grade0 => simp
  case h_grade1 => 

Proof state:
R : Type u_1
inst✝² : CommRing R
M : Type u_2
inst✝¹ : AddCommGroup M
inst✝ : Module R M
Q : QuadraticForm R M
x✝ : M
⊢ reverse (involute ((ι Q) x✝)) = involute (reverse ((ι Q) x✝))

Next tactic:
simp
theorem reverse_comp_involute :
    reverse.comp involute.toLinearMap =
      (involute.toLinearMap.comp reverse : _ →ₗ[R] CliffordAlgebra Q) := by
  ext x
  simp only [LinearMap.comp_apply, AlgHom.toLinearMap_apply]
  induction x using CliffordAlgebra.induction
  case h_grade0 => simp
  case h_grade1 => simp
  

Proof state:
case h.h_mul
R : Type u_1
inst✝² : CommRing R
M : Type u_2
inst✝¹ : AddCommGroup M
inst✝ : Module R M
Q : QuadraticForm R M
a✝² b✝ : CliffordAlgebra Q
a✝¹ : reverse (involute a✝²) = involute (reverse a✝²)
a✝ : reverse (involute b✝) = involute (reverse b✝)
⊢ reverse (involute (a✝² * b✝)) = involute (reverse (a✝² * b✝))
case h.h_add
R : Type u_1
inst✝² : CommRing R
M : Type u_2
inst✝¹ : AddCommGroup M
inst✝ : Module R M
Q : QuadraticForm R M
a✝² b✝ : CliffordAlgebra Q
a✝¹ : reverse (involute a✝²) = involute (reverse a✝²)
a✝ : reverse (involute b✝) = involute (reverse b✝)
⊢ reverse (involute (a✝² + b✝)) = involute (reverse (a✝² + b✝))

Next tactic:
case h_mul a b ha hb => simp only [ha, hb, reverse.map_mul, AlgHom.map_mul]
theorem reverse_comp_involute :
    reverse.comp involute.toLinearMap =
      (involute.toLinearMap.comp reverse : _ →ₗ[R] CliffordAlgebra Q) := by
  ext x
  simp only [LinearMap.comp_apply, AlgHom.toLinearMap_apply]
  induction x using CliffordAlgebra.induction
  case h_grade0 => simp
  case h_grade1 => simp
  

Proof state:
R : Type u_1
inst✝² : CommRing R
M : Type u_2
inst✝¹ : AddCommGroup M
inst✝ : Module R M
Q : QuadraticForm R M
a b : CliffordAlgebra Q
ha : reverse (involute a) = involute (reverse a)
hb : reverse (involute b) = involute (reverse b)
⊢ reverse (involute (a * b)) = involute (reverse (a * b))

Next tactic:
case h_mul a b ha hb => simp only [ha, hb, reverse.map_mul, AlgHom.map_mul]
theorem reverse_comp_involute :
    reverse.comp involute.toLinearMap =
      (involute.toLinearMap.comp reverse : _ →ₗ[R] CliffordAlgebra Q) := by
  ext x
  simp only [LinearMap.comp_apply, AlgHom.toLinearMap_apply]
  induction x using CliffordAlgebra.induction
  case h_grade0 => simp
  case h_grade1 => simp
  case h_mul a b ha hb => 

Proof state:
R : Type u_1
inst✝² : CommRing R
M : Type u_2
inst✝¹ : AddCommGroup M
inst✝ : Module R M
Q : QuadraticForm R M
a b : CliffordAlgebra Q
ha : reverse (involute a) = involute (reverse a)
hb : reverse (involute b) = involute (reverse b)
⊢ reverse (involute (a * b)) = involute (reverse (a * b))

Next tactic:
simp only [ha, hb, reverse.map_mul, AlgHom.map_mul]
theorem reverse_comp_involute :
    reverse.comp involute.toLinearMap =
      (involute.toLinearMap.comp reverse : _ →ₗ[R] CliffordAlgebra Q) := by
  ext x
  simp only [LinearMap.comp_apply, AlgHom.toLinearMap_apply]
  induction x using CliffordAlgebra.induction
  case h_grade0 => simp
  case h_grade1 => simp
  case h_mul a b ha hb => simp only [ha, hb, reverse.map_mul, AlgHom.map_mul]
  

Proof state:
case h.h_add
R : Type u_1
inst✝² : CommRing R
M : Type u_2
inst✝¹ : AddCommGroup M
inst✝ : Module R M
Q : QuadraticForm R M
a✝² b✝ : CliffordAlgebra Q
a✝¹ : reverse (involute a✝²) = involute (reverse a✝²)
a✝ : reverse (involute b✝) = involute (reverse b✝)
⊢ reverse (involute (a✝² + b✝)) = involute (reverse (a✝² + b✝))

Next tactic:
case h_add a b ha hb => simp only [ha, hb, reverse.map_add, AlgHom.map_add]
theorem reverse_comp_involute :
    reverse.comp involute.toLinearMap =
      (involute.toLinearMap.comp reverse : _ →ₗ[R] CliffordAlgebra Q) := by
  ext x
  simp only [LinearMap.comp_apply, AlgHom.toLinearMap_apply]
  induction x using CliffordAlgebra.induction
  case h_grade0 => simp
  case h_grade1 => simp
  case h_mul a b ha hb => simp only [ha, hb, reverse.map_mul, AlgHom.map_mul]
  

Proof state:
R : Type u_1
inst✝² : CommRing R
M : Type u_2
inst✝¹ : AddCommGroup M
inst✝ : Module R M
Q : QuadraticForm R M
a b : CliffordAlgebra Q
ha : reverse (involute a) = involute (reverse a)
hb : reverse (involute b) = involute (reverse b)
⊢ reverse (involute (a + b)) = involute (reverse (a + b))

Next tactic:
case h_add a b ha hb => simp only [ha, hb, reverse.map_add, AlgHom.map_add]
theorem reverse_comp_involute :
    reverse.comp involute.toLinearMap =
      (involute.toLinearMap.comp reverse : _ →ₗ[R] CliffordAlgebra Q) := by
  ext x
  simp only [LinearMap.comp_apply, AlgHom.toLinearMap_apply]
  induction x using CliffordAlgebra.induction
  case h_grade0 => simp
  case h_grade1 => simp
  case h_mul a b ha hb => simp only [ha, hb, reverse.map_mul, AlgHom.map_mul]
  case h_add a b ha hb => 

Proof state:
R : Type u_1
inst✝² : CommRing R
M : Type u_2
inst✝¹ : AddCommGroup M
inst✝ : Module R M
Q : QuadraticForm R M
a b : CliffordAlgebra Q
ha : reverse (involute a) = involute (reverse a)
hb : reverse (involute b) = involute (reverse b)
⊢ reverse (involute (a + b)) = involute (reverse (a + b))

Next tactic:
simp only [ha, hb, reverse.map_add, AlgHom.map_add]