-- Mathlib/Data/PFunctor/Multivariate/Basic.lean
theorem liftP_iff {α : TypeVec n} (p : ∀ ⦃i⦄, α i → Prop) (x : P α) :
    LiftP p x ↔ ∃ a f, x = ⟨a, f⟩ ∧ ∀ i j, p (f i j)

Proof state:
case mp.intro
n : ℕ
P : MvPFunctor.{u} n
α : TypeVec.{u} n
p : ⦃i : Fin2 n⦄ → α i → Prop
x : ↑P α
y : ↑P fun i => Subtype p
hy : (fun i => Subtype.val) <$$> y = x
⊢ ∃ a f, x = ⟨a, f⟩ ∧ ∀ (i : Fin2 n) (j : P.B a i), p (f i j)

Tactic:
rcases h : y with ⟨a, f⟩

Result:
case mp.intro.mk
n : ℕ
P : MvPFunctor.{u} n
α : TypeVec.{u} n
p : ⦃i : Fin2 n⦄ → α i → Prop
x : ↑P α
y : ↑P fun i => Subtype p
hy : (fun i => Subtype.val) <$$> y = x
a : P.A
f : P.B a ⟹ fun i => Subtype p
h : y = ⟨a, f⟩
⊢ ∃ a f, x = ⟨a, f⟩ ∧ ∀ (i : Fin2 n) (j : P.B a i), p (f i j)

Proof state:
case mp.intro.mk
n : ℕ
P : MvPFunctor.{u} n
α : TypeVec.{u} n
p : ⦃i : Fin2 n⦄ → α i → Prop
x : ↑P α
y : ↑P fun i => Subtype p
hy : (fun i => Subtype.val) <$$> y = x
a : P.A
f : P.B a ⟹ fun i => Subtype p
h : y = ⟨a, f⟩
⊢ x = ⟨a, fun i j => ↑(f i j)⟩

Tactic:
rw [← hy, h, map_eq]

Result:
case mp.intro.mk
n : ℕ
P : MvPFunctor.{u} n
α : TypeVec.{u} n
p : ⦃i : Fin2 n⦄ → α i → Prop
x : ↑P α
y : ↑P fun i => Subtype p
hy : (fun i => Subtype.val) <$$> y = x
a : P.A
f : P.B a ⟹ fun i => Subtype p
h : y = ⟨a, f⟩
⊢ ⟨a, (fun i => Subtype.val) ⊚ f⟩ = ⟨a, fun i j => ↑(f i j)⟩

Proof state:
n : ℕ
P : MvPFunctor.{u} n
α : TypeVec.{u} n
p : ⦃i : Fin2 n⦄ → α i → Prop
x : ↑P α
⊢ LiftP p x ↔ ∃ a f, x = ⟨a, f⟩ ∧ ∀ (i : Fin2 n) (j : P.B a i), p (f i j)

Tactic:
constructor

Result:
case mp
n : ℕ
P : MvPFunctor.{u} n
α : TypeVec.{u} n
p : ⦃i : Fin2 n⦄ → α i → Prop
x : ↑P α
⊢ LiftP p x → ∃ a f, x = ⟨a, f⟩ ∧ ∀ (i : Fin2 n) (j : P.B a i), p (f i j)

case mpr
n : ℕ
P : MvPFunctor.{u} n
α : TypeVec.{u} n
p : ⦃i : Fin2 n⦄ → α i → Prop
x : ↑P α
⊢ (∃ a f, x = ⟨a, f⟩ ∧ ∀ (i : Fin2 n) (j : P.B a i), p (f i j)) → LiftP p x

Proof state:
case mp.intro.mk
n : ℕ
P : MvPFunctor.{u} n
α : TypeVec.{u} n
p : ⦃i : Fin2 n⦄ → α i → Prop
x : ↑P α
y : ↑P fun i => Subtype p
hy : (fun i => Subtype.val) <$$> y = x
a : P.A
f : P.B a ⟹ fun i => Subtype p
h : y = ⟨a, f⟩
⊢ ∃ a f, x = ⟨a, f⟩ ∧ ∀ (i : Fin2 n) (j : P.B a i), p (f i j)

Tactic:
refine ⟨a, fun i j => (f i j).val, ?_, fun i j => (f i j).property⟩

Result:
case mp.intro.mk
n : ℕ
P : MvPFunctor.{u} n
α : TypeVec.{u} n
p : ⦃i : Fin2 n⦄ → α i → Prop
x : ↑P α
y : ↑P fun i => Subtype p
hy : (fun i => Subtype.val) <$$> y = x
a : P.A
f : P.B a ⟹ fun i => Subtype p
h : y = ⟨a, f⟩
⊢ x = ⟨a, fun i j => ↑(f i j)⟩

Proof state:
case mp.intro.mk
n : ℕ
P : MvPFunctor.{u} n
α : TypeVec.{u} n
p : ⦃i : Fin2 n⦄ → α i → Prop
x : ↑P α
y : ↑P fun i => Subtype p
hy : (fun i => Subtype.val) <$$> y = x
a : P.A
f : P.B a ⟹ fun i => Subtype p
h : y = ⟨a, f⟩
⊢ ⟨a, (fun i => Subtype.val) ⊚ f⟩ = ⟨a, fun i j => ↑(f i j)⟩

Tactic:
rfl

Result:
no goals

Proof state:
case mpr
n : ℕ
P : MvPFunctor.{u} n
α : TypeVec.{u} n
p : ⦃i : Fin2 n⦄ → α i → Prop
x : ↑P α
⊢ (∃ a f, x = ⟨a, f⟩ ∧ ∀ (i : Fin2 n) (j : P.B a i), p (f i j)) → LiftP p x

Tactic:
rintro ⟨a, f, xeq, pf⟩

Result:
case mpr.intro.intro.intro
n : ℕ
P : MvPFunctor.{u} n
α : TypeVec.{u} n
p : ⦃i : Fin2 n⦄ → α i → Prop
x : ↑P α
a : P.A
f : P.B a ⟹ α
xeq : x = ⟨a, f⟩
pf : ∀ (i : Fin2 n) (j : P.B a i), p (f i j)
⊢ LiftP p x

Proof state:
case mpr.intro.intro.intro
n : ℕ
P : MvPFunctor.{u} n
α : TypeVec.{u} n
p : ⦃i : Fin2 n⦄ → α i → Prop
x : ↑P α
a : P.A
f : P.B a ⟹ α
xeq : x = ⟨a, f⟩
pf : ∀ (i : Fin2 n) (j : P.B a i), p (f i j)
⊢ LiftP p x

Tactic:
use ⟨a, fun i j => ⟨f i j, pf i j⟩⟩

Result:
case h
n : ℕ
P : MvPFunctor.{u} n
α : TypeVec.{u} n
p : ⦃i : Fin2 n⦄ → α i → Prop
x : ↑P α
a : P.A
f : P.B a ⟹ α
xeq : x = ⟨a, f⟩
pf : ∀ (i : Fin2 n) (j : P.B a i), p (f i j)
⊢ (fun i => Subtype.val) <$$> ⟨a, fun i j => ⟨f i j, ⋯⟩⟩ = x

Proof state:
case h
n : ℕ
P : MvPFunctor.{u} n
α : TypeVec.{u} n
p : ⦃i : Fin2 n⦄ → α i → Prop
x : ↑P α
a : P.A
f : P.B a ⟹ α
xeq : x = ⟨a, f⟩
pf : ∀ (i : Fin2 n) (j : P.B a i), p (f i j)
⊢ (fun i => Subtype.val) <$$> ⟨a, fun i j => ⟨f i j, ⋯⟩⟩ = ⟨a, f⟩

Tactic:
rfl

Result:
no goals

Proof state:
case mp
n : ℕ
P : MvPFunctor.{u} n
α : TypeVec.{u} n
p : ⦃i : Fin2 n⦄ → α i → Prop
x : ↑P α
⊢ LiftP p x → ∃ a f, x = ⟨a, f⟩ ∧ ∀ (i : Fin2 n) (j : P.B a i), p (f i j)

Tactic:
rintro ⟨y, hy⟩

Result:
case mp.intro
n : ℕ
P : MvPFunctor.{u} n
α : TypeVec.{u} n
p : ⦃i : Fin2 n⦄ → α i → Prop
x : ↑P α
y : ↑P fun i => Subtype p
hy : (fun i => Subtype.val) <$$> y = x
⊢ ∃ a f, x = ⟨a, f⟩ ∧ ∀ (i : Fin2 n) (j : P.B a i), p (f i j)

Proof state:
case h
n : ℕ
P : MvPFunctor.{u} n
α : TypeVec.{u} n
p : ⦃i : Fin2 n⦄ → α i → Prop
x : ↑P α
a : P.A
f : P.B a ⟹ α
xeq : x = ⟨a, f⟩
pf : ∀ (i : Fin2 n) (j : P.B a i), p (f i j)
⊢ (fun i => Subtype.val) <$$> ⟨a, fun i j => ⟨f i j, ⋯⟩⟩ = x

Tactic:
rw [xeq]

Result:
case h
n : ℕ
P : MvPFunctor.{u} n
α : TypeVec.{u} n
p : ⦃i : Fin2 n⦄ → α i → Prop
x : ↑P α
a : P.A
f : P.B a ⟹ α
xeq : x = ⟨a, f⟩
pf : ∀ (i : Fin2 n) (j : P.B a i), p (f i j)
⊢ (fun i => Subtype.val) <$$> ⟨a, fun i j => ⟨f i j, ⋯⟩⟩ = ⟨a, f⟩