l3lab/ntp-mathlib huggingface dataset:
theorem enum_zero_le {r : α → α → Prop} [IsWellOrder α r] (h0 : 0 < type r) (a : α) :
    ¬r a (enum r 0 h0) := by
  

Proof state:
α : Type u
β : Type u_1
γ : Type u_2
r✝ : α → α → Prop
s : β → β → Prop
t : γ → γ → Prop
r : α → α → Prop
inst✝ : IsWellOrder α r
h0 : 0 < type r
a : α
⊢ ¬r a (enum r 0 h0)

Next tactic:
rw [← enum_typein r a, enum_le_enum r]
theorem enum_zero_le {r : α → α → Prop} [IsWellOrder α r] (h0 : 0 < type r) (a : α) :
    ¬r a (enum r 0 h0) := by
  rw [← enum_typein r a, enum_le_enum r]
  

Proof state:
α : Type u
β : Type u_1
γ : Type u_2
r✝ : α → α → Prop
s : β → β → Prop
t : γ → γ → Prop
r : α → α → Prop
inst✝ : IsWellOrder α r
h0 : 0 < type r
a : α
⊢ 0 ≤ typein r a

Next tactic:
apply Ordinal.zero_le
theorem enum_zero_le' {o : Ordinal} (h0 : 0 < o) (a : o.out.α) :
    @enum o.out.α (· < ·) _ 0 (by 

Proof state:
α : Type u
β : Type u_1
γ : Type u_2
r : α → α → Prop
s : β → β → Prop
t : γ → γ → Prop
o : Ordinal.{?u.185665}
h0 : 0 < o
a : (Quotient.out o).α
⊢ 0 < type fun x x_1 => x < x_1

Next tactic:
rwa [type_lt]
theorem enum_zero_le' {o : Ordinal} (h0 : 0 < o) (a : o.out.α) :
    @enum o.out.α (· < ·) _ 0 (by rwa [type_lt]) ≤ a := by
  

Proof state:
α : Type u
β : Type u_1
γ : Type u_2
r : α → α → Prop
s : β → β → Prop
t : γ → γ → Prop
o : Ordinal.{u_3}
h0 : 0 < o
a : (Quotient.out o).α
⊢ enum (fun x x_1 => x < x_1) 0 (_ : 0 < type fun x x_1 => x < x_1) ≤ a

Next tactic:
rw [← not_lt]
theorem enum_zero_le' {o : Ordinal} (h0 : 0 < o) (a : o.out.α) :
    @enum o.out.α (· < ·) _ 0 (by rwa [type_lt]) ≤ a := by
  rw [← not_lt]
  

Proof state:
α : Type u
β : Type u_1
γ : Type u_2
r : α → α → Prop
s : β → β → Prop
t : γ → γ → Prop
o : Ordinal.{u_3}
h0 : 0 < o
a : (Quotient.out o).α
⊢ ¬a < enum (fun x x_1 => x < x_1) 0 (_ : 0 < type fun x x_1 => x < x_1)

Next tactic:
apply enum_zero_le
theorem le_enum_succ {o : Ordinal} (a : (succ o).out.α) :
    a ≤
      @enum (succ o).out.α (· < ·) _ o
        (by
          

Proof state:
α : Type u
β : Type u_1
γ : Type u_2
r : α → α → Prop
s : β → β → Prop
t : γ → γ → Prop
o : Ordinal.{?u.186849}
a : (Quotient.out (succ o)).α
⊢ o < type fun x x_1 => x < x_1

Next tactic:
rw [type_lt]
theorem le_enum_succ {o : Ordinal} (a : (succ o).out.α) :
    a ≤
      @enum (succ o).out.α (· < ·) _ o
        (by
          rw [type_lt]
          

Proof state:
α : Type u
β : Type u_1
γ : Type u_2
r : α → α → Prop
s : β → β → Prop
t : γ → γ → Prop
o : Ordinal.{?u.186849}
a : (Quotient.out (succ o)).α
⊢ o < succ o

Next tactic:
exact lt_succ o
theorem le_enum_succ {o : Ordinal} (a : (succ o).out.α) :
    a ≤
      @enum (succ o).out.α (· < ·) _ o
        (by
          rw [type_lt]
          exact lt_succ o) := by
  

Proof state:
α : Type u
β : Type u_1
γ : Type u_2
r : α → α → Prop
s : β → β → Prop
t : γ → γ → Prop
o : Ordinal.{u_3}
a : (Quotient.out (succ o)).α
⊢ a ≤ enum (fun x x_1 => x < x_1) o (_ : o < type fun x x_1 => x < x_1)

Next tactic:
rw [← @enum_typein _ (· < ·) (isWellOrder_out_lt _) a, enum_le_enum', ← lt_succ_iff]
theorem le_enum_succ {o : Ordinal} (a : (succ o).out.α) :
    a ≤
      @enum (succ o).out.α (· < ·) _ o
        (by
          rw [type_lt]
          exact lt_succ o) := by
  rw [← @enum_typein _ (· < ·) (isWellOrder_out_lt _) a, enum_le_enum', ← lt_succ_iff]
  

Proof state:
α : Type u
β : Type u_1
γ : Type u_2
r : α → α → Prop
s : β → β → Prop
t : γ → γ → Prop
o : Ordinal.{u_3}
a : (Quotient.out (succ o)).α
⊢ typein (fun x x_1 => x < x_1) a < succ o

Next tactic:
apply typein_lt_self
/-- The order isomorphism between ordinals less than `o` and `o.out.α`. -/
@[simps!]
noncomputable def enumIsoOut (o : Ordinal) : Set.Iio o ≃o o.out.α
    where
  toFun x :=
    enum (· < ·) x.1 <| by
      

Proof state:
α : Type u
β : Type u_1
γ : Type u_2
r : α → α → Prop
s : β → β → Prop
t : γ → γ → Prop
o : Ordinal.{?u.192092}
x : ↑(Iio o)
⊢ ↑x < type fun x x_1 => x < x_1

Next tactic:
rw [type_lt]
/-- The order isomorphism between ordinals less than `o` and `o.out.α`. -/
@[simps!]
noncomputable def enumIsoOut (o : Ordinal) : Set.Iio o ≃o o.out.α
    where
  toFun x :=
    enum (· < ·) x.1 <| by
      rw [type_lt]
      

Proof state:
α : Type u
β : Type u_1
γ : Type u_2
r : α → α → Prop
s : β → β → Prop
t : γ → γ → Prop
o : Ordinal.{?u.192092}
x : ↑(Iio o)
⊢ ↑x < o

Next tactic:
exact x.2
/-- The order isomorphism between ordinals less than `o` and `o.out.α`. -/
@[simps!]
noncomputable def enumIsoOut (o : Ordinal) : Set.Iio o ≃o o.out.α
    where
  toFun x :=
    enum (· < ·) x.1 <| by
      rw [type_lt]
      exact x.2
  invFun x := ⟨@typein _ (· < ·) (isWellOrder_out_lt _) x, typein_lt_self x⟩
  left_inv := fun ⟨o', h⟩ => Subtype.ext_val (typein_enum _ _)
  right_inv h := enum_typein _ _
  map_rel_iff' := by
    

Proof state:
α : Type u
β : Type u_1
γ : Type u_2
r : α → α → Prop
s : β → β → Prop
t : γ → γ → Prop
o : Ordinal.{?u.192092}
⊢ ∀ {a b : ↑(Iio o)},
    { toFun := fun x => enum (fun x x_1 => x < x_1) ↑x (_ : ↑x < type fun x x_1 => x < x_1),
            invFun := fun x =>
              { val := typein (fun x x_1 => x < x_1) x, property := (_ : typein (fun x x_1 => x < x_1) x < o) },
            left_inv :=
              (_ :
                ∀ (x : ↑(Iio o)),
                  (fun x =>
                        { val := typein (fun x x_1 => x < x_1) x,
                          property := (_ : typein (fun x x_1 => x < x_1) x < o) })
                      ((fun x => enum (fun x x_1 => x < x_1) ↑x (_ : ↑x < type fun x x_1 => x < x_1)) x) =
                    x),
            right_inv :=
              (_ :
                ∀ (h : (Quotient.out o).α),
                  enum (fun x x_1 => x < x_1) (typein (fun x x_1 => x < x_1) h)
                      (_ : typein (fun x x_1 => x < x_1) h < type fun x x_1 => x < x_1) =
                    h) }
          a ≤
        { toFun := fun x => enum (fun x x_1 => x < x_1) ↑x (_ : ↑x < type fun x x_1 => x < x_1),
            invFun := fun x =>
              { val := typein (fun x x_1 => x < x_1) x, property := (_ : typein (fun x x_1 => x < x_1) x < o) },
            left_inv :=
              (_ :
                ∀ (x : ↑(Iio o)),
                  (fun x =>
                        { val := typein (fun x x_1 => x < x_1) x,
                          property := (_ : typein (fun x x_1 => x < x_1) x < o) })
                      ((fun x => enum (fun x x_1 => x < x_1) ↑x (_ : ↑x < type fun x x_1 => x < x_1)) x) =
                    x),
            right_inv :=
              (_ :
                ∀ (h : (Quotient.out o).α),
                  enum (fun x x_1 => x < x_1) (typein (fun x x_1 => x < x_1) h)
                      (_ : typein (fun x x_1 => x < x_1) h < type fun x x_1 => x < x_1) =
                    h) }
          b ↔
      a ≤ b

Next tactic:
rintro ⟨a, _⟩ ⟨b, _⟩
/-- The order isomorphism between ordinals less than `o` and `o.out.α`. -/
@[simps!]
noncomputable def enumIsoOut (o : Ordinal) : Set.Iio o ≃o o.out.α
    where
  toFun x :=
    enum (· < ·) x.1 <| by
      rw [type_lt]
      exact x.2
  invFun x := ⟨@typein _ (· < ·) (isWellOrder_out_lt _) x, typein_lt_self x⟩
  left_inv := fun ⟨o', h⟩ => Subtype.ext_val (typein_enum _ _)
  right_inv h := enum_typein _ _
  map_rel_iff' := by
    rintro ⟨a, _⟩ ⟨b, _⟩
    

Proof state:
case mk.mk
α : Type u
β : Type u_1
γ : Type u_2
r : α → α → Prop
s : β → β → Prop
t : γ → γ → Prop
o a : Ordinal.{?u.192092}
property✝¹ : a ∈ Iio o
b : Ordinal.{?u.192092}
property✝ : b ∈ Iio o
⊢ { toFun := fun x => enum (fun x x_1 => x < x_1) ↑x (_ : ↑x < type fun x x_1 => x < x_1),
          invFun := fun x =>
            { val := typein (fun x x_1 => x < x_1) x, property := (_ : typein (fun x x_1 => x < x_1) x < o) },
          left_inv :=
            (_ :
              ∀ (x : ↑(Iio o)),
                (fun x =>
                      { val := typein (fun x x_1 => x < x_1) x, property := (_ : typein (fun x x_1 => x < x_1) x < o) })
                    ((fun x => enum (fun x x_1 => x < x_1) ↑x (_ : ↑x < type fun x x_1 => x < x_1)) x) =
                  x),
          right_inv :=
            (_ :
              ∀ (h : (Quotient.out o).α),
                enum (fun x x_1 => x < x_1) (typein (fun x x_1 => x < x_1) h)
                    (_ : typein (fun x x_1 => x < x_1) h < type fun x x_1 => x < x_1) =
                  h) }
        { val := a, property := property✝¹ } ≤
      { toFun := fun x => enum (fun x x_1 => x < x_1) ↑x (_ : ↑x < type fun x x_1 => x < x_1),
          invFun := fun x =>
            { val := typein (fun x x_1 => x < x_1) x, property := (_ : typein (fun x x_1 => x < x_1) x < o) },
          left_inv :=
            (_ :
              ∀ (x : ↑(Iio o)),
                (fun x =>
                      { val := typein (fun x x_1 => x < x_1) x, property := (_ : typein (fun x x_1 => x < x_1) x < o) })
                    ((fun x => enum (fun x x_1 => x < x_1) ↑x (_ : ↑x < type fun x x_1 => x < x_1)) x) =
                  x),
          right_inv :=
            (_ :
              ∀ (h : (Quotient.out o).α),
                enum (fun x x_1 => x < x_1) (typein (fun x x_1 => x < x_1) h)
                    (_ : typein (fun x x_1 => x < x_1) h < type fun x x_1 => x < x_1) =
                  h) }
        { val := b, property := property✝ } ↔
    { val := a, property := property✝¹ } ≤ { val := b, property := property✝ }

Next tactic:
apply enum_le_enum'
theorem enum_zero_eq_bot {o : Ordinal} (ho : 0 < o) :
    enum (· < ·) 0 (by 

Proof state:
α : Type u
β : Type u_1
γ : Type u_2
r : α → α → Prop
s : β → β → Prop
t : γ → γ → Prop
o : Ordinal.{?u.197289}
ho : 0 < o
⊢ 0 < type fun x x_1 => x < x_1

Next tactic:
rwa [type_lt]
/-- Principal segment version of the lift operation on ordinals, embedding `ordinal.{u}` in
  `ordinal.{v}` as a principal segment when `u < v`. -/
def lift.principalSeg : @PrincipalSeg Ordinal.{u} Ordinal.{max (u + 1) v} (· < ·) (· < ·) :=
  ⟨↑lift.initialSeg.{u, max (u + 1) v}, univ.{u, v}, by
    

Proof state:
α : Type u
β : Type u_1
γ : Type u_2
r : α → α → Prop
s : β → β → Prop
t : γ → γ → Prop
⊢ ∀ (b : Ordinal.{max (u + 1) v}), b < univ.{u, v} ↔ ∃ a, initialSeg.toRelEmbedding a = b

Next tactic:
refine' fun b => inductionOn b _
/-- Principal segment version of the lift operation on ordinals, embedding `ordinal.{u}` in
  `ordinal.{v}` as a principal segment when `u < v`. -/
def lift.principalSeg : @PrincipalSeg Ordinal.{u} Ordinal.{max (u + 1) v} (· < ·) (· < ·) :=
  ⟨↑lift.initialSeg.{u, max (u + 1) v}, univ.{u, v}, by
    refine' fun b => inductionOn b _; 

Proof state:
α : Type u
β : Type u_1
γ : Type u_2
r : α → α → Prop
s : β → β → Prop
t : γ → γ → Prop
b : Ordinal.{max (u + 1) v}
⊢ ∀ (α : Type (max (u + 1) v)) (r : α → α → Prop) [inst : IsWellOrder α r],
    type r < univ.{u, v} ↔ ∃ a, initialSeg.toRelEmbedding a = type r

Next tactic:
intro β s _
/-- Principal segment version of the lift operation on ordinals, embedding `ordinal.{u}` in
  `ordinal.{v}` as a principal segment when `u < v`. -/
def lift.principalSeg : @PrincipalSeg Ordinal.{u} Ordinal.{max (u + 1) v} (· < ·) (· < ·) :=
  ⟨↑lift.initialSeg.{u, max (u + 1) v}, univ.{u, v}, by
    refine' fun b => inductionOn b _; intro β s _
    

Proof state:
α : Type u
β✝ : Type u_1
γ : Type u_2
r : α → α → Prop
s✝ : β✝ → β✝ → Prop
t : γ → γ → Prop
b : Ordinal.{max (u + 1) v}
β : Type (max (u + 1) v)
s : β → β → Prop
inst✝ : IsWellOrder β s
⊢ type s < univ.{u, v} ↔ ∃ a, initialSeg.toRelEmbedding a = type s

Next tactic:
rw [univ, ← lift_umax]
/-- Principal segment version of the lift operation on ordinals, embedding `ordinal.{u}` in
  `ordinal.{v}` as a principal segment when `u < v`. -/
def lift.principalSeg : @PrincipalSeg Ordinal.{u} Ordinal.{max (u + 1) v} (· < ·) (· < ·) :=
  ⟨↑lift.initialSeg.{u, max (u + 1) v}, univ.{u, v}, by
    refine' fun b => inductionOn b _; intro β s _
    rw [univ, ← lift_umax]; 

Proof state:
α : Type u
β✝ : Type u_1
γ : Type u_2
r : α → α → Prop
s✝ : β✝ → β✝ → Prop
t : γ → γ → Prop
b : Ordinal.{max (u + 1) v}
β : Type (max (u + 1) v)
s : β → β → Prop
inst✝ : IsWellOrder β s
⊢ type s < lift.{max (u + 1) v, u + 1} (type fun x x_1 => x < x_1) ↔ ∃ a, initialSeg.toRelEmbedding a = type s

Next tactic:
constructor
/-- Principal segment version of the lift operation on ordinals, embedding `ordinal.{u}` in
  `ordinal.{v}` as a principal segment when `u < v`. -/
def lift.principalSeg : @PrincipalSeg Ordinal.{u} Ordinal.{max (u + 1) v} (· < ·) (· < ·) :=
  ⟨↑lift.initialSeg.{u, max (u + 1) v}, univ.{u, v}, by
    refine' fun b => inductionOn b _; intro β s _
    rw [univ, ← lift_umax]; constructor <;> 

Proof state:
case mp
α : Type u
β✝ : Type u_1
γ : Type u_2
r : α → α → Prop
s✝ : β✝ → β✝ → Prop
t : γ → γ → Prop
b : Ordinal.{max (u + 1) v}
β : Type (max (u + 1) v)
s : β → β → Prop
inst✝ : IsWellOrder β s
⊢ type s < lift.{max (u + 1) v, u + 1} (type fun x x_1 => x < x_1) → ∃ a, initialSeg.toRelEmbedding a = type s

Next tactic:
intro h
/-- Principal segment version of the lift operation on ordinals, embedding `ordinal.{u}` in
  `ordinal.{v}` as a principal segment when `u < v`. -/
def lift.principalSeg : @PrincipalSeg Ordinal.{u} Ordinal.{max (u + 1) v} (· < ·) (· < ·) :=
  ⟨↑lift.initialSeg.{u, max (u + 1) v}, univ.{u, v}, by
    refine' fun b => inductionOn b _; intro β s _
    rw [univ, ← lift_umax]; constructor <;> 

Proof state:
case mpr
α : Type u
β✝ : Type u_1
γ : Type u_2
r : α → α → Prop
s✝ : β✝ → β✝ → Prop
t : γ → γ → Prop
b : Ordinal.{max (u + 1) v}
β : Type (max (u + 1) v)
s : β → β → Prop
inst✝ : IsWellOrder β s
⊢ (∃ a, initialSeg.toRelEmbedding a = type s) → type s < lift.{max (u + 1) v, u + 1} (type fun x x_1 => x < x_1)

Next tactic:
intro h
/-- Principal segment version of the lift operation on ordinals, embedding `ordinal.{u}` in
  `ordinal.{v}` as a principal segment when `u < v`. -/
def lift.principalSeg : @PrincipalSeg Ordinal.{u} Ordinal.{max (u + 1) v} (· < ·) (· < ·) :=
  ⟨↑lift.initialSeg.{u, max (u + 1) v}, univ.{u, v}, by
    refine' fun b => inductionOn b _; intro β s _
    rw [univ, ← lift_umax]; constructor <;> intro h
    · 

Proof state:
case mp
α : Type u
β✝ : Type u_1
γ : Type u_2
r : α → α → Prop
s✝ : β✝ → β✝ → Prop
t : γ → γ → Prop
b : Ordinal.{max (u + 1) v}
β : Type (max (u + 1) v)
s : β → β → Prop
inst✝ : IsWellOrder β s
h : type s < lift.{max (u + 1) v, u + 1} (type fun x x_1 => x < x_1)
⊢ ∃ a, initialSeg.toRelEmbedding a = type s

Next tactic:
rw [← lift_id (type s)] at h ⊢
/-- Principal segment version of the lift operation on ordinals, embedding `ordinal.{u}` in
  `ordinal.{v}` as a principal segment when `u < v`. -/
def lift.principalSeg : @PrincipalSeg Ordinal.{u} Ordinal.{max (u + 1) v} (· < ·) (· < ·) :=
  ⟨↑lift.initialSeg.{u, max (u + 1) v}, univ.{u, v}, by
    refine' fun b => inductionOn b _; intro β s _
    rw [univ, ← lift_umax]; constructor <;> intro h
    · rw [← lift_id (type s)] at h ⊢
      

Proof state:
case mp
α : Type u
β✝ : Type u_1
γ : Type u_2
r : α → α → Prop
s✝ : β✝ → β✝ → Prop
t : γ → γ → Prop
b : Ordinal.{max (u + 1) v}
β : Type (max (u + 1) v)
s : β → β → Prop
inst✝ : IsWellOrder β s
h : lift.{max (u + 1) v, max (u + 1) v} (type s) < lift.{max (u + 1) v, u + 1} (type fun x x_1 => x < x_1)
⊢ ∃ a, initialSeg.toRelEmbedding a = lift.{max (u + 1) v, max (u + 1) v} (type s)

Next tactic:
cases' lift_type_lt.{_,_,v}.1 h with f
/-- Principal segment version of the lift operation on ordinals, embedding `ordinal.{u}` in
  `ordinal.{v}` as a principal segment when `u < v`. -/
def lift.principalSeg : @PrincipalSeg Ordinal.{u} Ordinal.{max (u + 1) v} (· < ·) (· < ·) :=
  ⟨↑lift.initialSeg.{u, max (u + 1) v}, univ.{u, v}, by
    refine' fun b => inductionOn b _; intro β s _
    rw [univ, ← lift_umax]; constructor <;> intro h
    · rw [← lift_id (type s)] at h ⊢
      cases' lift_type_lt.{_,_,v}.1 h with f
      

Proof state:
case mp.intro
α : Type u
β✝ : Type u_1
γ : Type u_2
r : α → α → Prop
s✝ : β✝ → β✝ → Prop
t : γ → γ → Prop
b : Ordinal.{max (u + 1) v}
β : Type (max (u + 1) v)
s : β → β → Prop
inst✝ : IsWellOrder β s
h : lift.{max (u + 1) v, max (u + 1) v} (type s) < lift.{max (u + 1) v, u + 1} (type fun x x_1 => x < x_1)
f : s ≺i fun x x_1 => x < x_1
⊢ ∃ a, initialSeg.toRelEmbedding a = lift.{max (u + 1) v, max (u + 1) v} (type s)

Next tactic:
cases' f with f a hf
/-- Principal segment version of the lift operation on ordinals, embedding `ordinal.{u}` in
  `ordinal.{v}` as a principal segment when `u < v`. -/
def lift.principalSeg : @PrincipalSeg Ordinal.{u} Ordinal.{max (u + 1) v} (· < ·) (· < ·) :=
  ⟨↑lift.initialSeg.{u, max (u + 1) v}, univ.{u, v}, by
    refine' fun b => inductionOn b _; intro β s _
    rw [univ, ← lift_umax]; constructor <;> intro h
    · rw [← lift_id (type s)] at h ⊢
      cases' lift_type_lt.{_,_,v}.1 h with f
      cases' f with f a hf
      

Proof state:
case mp.intro.mk
α : Type u
β✝ : Type u_1
γ : Type u_2
r : α → α → Prop
s✝ : β✝ → β✝ → Prop
t : γ → γ → Prop
b : Ordinal.{max (u + 1) v}
β : Type (max (u + 1) v)
s : β → β → Prop
inst✝ : IsWellOrder β s
h : lift.{max (u + 1) v, max (u + 1) v} (type s) < lift.{max (u + 1) v, u + 1} (type fun x x_1 => x < x_1)
f : s ↪r fun x x_1 => x < x_1
a : Ordinal.{u}
hf : ∀ (b : Ordinal.{u}), b < a ↔ ∃ a, f a = b
⊢ ∃ a, initialSeg.toRelEmbedding a = lift.{max (u + 1) v, max (u + 1) v} (type s)

Next tactic:
exists a
/-- Principal segment version of the lift operation on ordinals, embedding `ordinal.{u}` in
  `ordinal.{v}` as a principal segment when `u < v`. -/
def lift.principalSeg : @PrincipalSeg Ordinal.{u} Ordinal.{max (u + 1) v} (· < ·) (· < ·) :=
  ⟨↑lift.initialSeg.{u, max (u + 1) v}, univ.{u, v}, by
    refine' fun b => inductionOn b _; intro β s _
    rw [univ, ← lift_umax]; constructor <;> intro h
    · rw [← lift_id (type s)] at h ⊢
      cases' lift_type_lt.{_,_,v}.1 h with f
      cases' f with f a hf
      exists a
      

Proof state:
case mp.intro.mk
α : Type u
β✝ : Type u_1
γ : Type u_2
r : α → α → Prop
s✝ : β✝ → β✝ → Prop
t : γ → γ → Prop
b : Ordinal.{max (u + 1) v}
β : Type (max (u + 1) v)
s : β → β → Prop
inst✝ : IsWellOrder β s
h : lift.{max (u + 1) v, max (u + 1) v} (type s) < lift.{max (u + 1) v, u + 1} (type fun x x_1 => x < x_1)
f : s ↪r fun x x_1 => x < x_1
a : Ordinal.{u}
hf : ∀ (b : Ordinal.{u}), b < a ↔ ∃ a, f a = b
⊢ initialSeg.toRelEmbedding a = lift.{max (u + 1) v, max (u + 1) v} (type s)

Next tactic:
revert hf
/-- Principal segment version of the lift operation on ordinals, embedding `ordinal.{u}` in
  `ordinal.{v}` as a principal segment when `u < v`. -/
def lift.principalSeg : @PrincipalSeg Ordinal.{u} Ordinal.{max (u + 1) v} (· < ·) (· < ·) :=
  ⟨↑lift.initialSeg.{u, max (u + 1) v}, univ.{u, v}, by
    refine' fun b => inductionOn b _; intro β s _
    rw [univ, ← lift_umax]; constructor <;> intro h
    · rw [← lift_id (type s)] at h ⊢
      cases' lift_type_lt.{_,_,v}.1 h with f
      cases' f with f a hf
      exists a
      revert hf
      -- Porting note: apply inductionOn does not work, refine does
      

Proof state:
case mp.intro.mk
α : Type u
β✝ : Type u_1
γ : Type u_2
r : α → α → Prop
s✝ : β✝ → β✝ → Prop
t : γ → γ → Prop
b : Ordinal.{max (u + 1) v}
β : Type (max (u + 1) v)
s : β → β → Prop
inst✝ : IsWellOrder β s
h : lift.{max (u + 1) v, max (u + 1) v} (type s) < lift.{max (u + 1) v, u + 1} (type fun x x_1 => x < x_1)
f : s ↪r fun x x_1 => x < x_1
a : Ordinal.{u}
⊢ (∀ (b : Ordinal.{u}), b < a ↔ ∃ a, f a = b) →
    initialSeg.toRelEmbedding a = lift.{max (u + 1) v, max (u + 1) v} (type s)

Next tactic:
refine inductionOn a ?_
/-- Principal segment version of the lift operation on ordinals, embedding `ordinal.{u}` in
  `ordinal.{v}` as a principal segment when `u < v`. -/
def lift.principalSeg : @PrincipalSeg Ordinal.{u} Ordinal.{max (u + 1) v} (· < ·) (· < ·) :=
  ⟨↑lift.initialSeg.{u, max (u + 1) v}, univ.{u, v}, by
    refine' fun b => inductionOn b _; intro β s _
    rw [univ, ← lift_umax]; constructor <;> intro h
    · rw [← lift_id (type s)] at h ⊢
      cases' lift_type_lt.{_,_,v}.1 h with f
      cases' f with f a hf
      exists a
      revert hf
      -- Porting note: apply inductionOn does not work, refine does
      refine inductionOn a ?_
      

Proof state:
case mp.intro.mk
α : Type u
β✝ : Type u_1
γ : Type u_2
r : α → α → Prop
s✝ : β✝ → β✝ → Prop
t : γ → γ → Prop
b : Ordinal.{max (u + 1) v}
β : Type (max (u + 1) v)
s : β → β → Prop
inst✝ : IsWellOrder β s
h : lift.{max (u + 1) v, max (u + 1) v} (type s) < lift.{max (u + 1) v, u + 1} (type fun x x_1 => x < x_1)
f : s ↪r fun x x_1 => x < x_1
a : Ordinal.{u}
⊢ ∀ (α : Type u) (r : α → α → Prop) [inst : IsWellOrder α r],
    (∀ (b : Ordinal.{u}), b < type r ↔ ∃ a, f a = b) →
      initialSeg.toRelEmbedding (type r) = lift.{max (u + 1) v, max (u + 1) v} (type s)

Next tactic:
intro α r _ hf
/-- Principal segment version of the lift operation on ordinals, embedding `ordinal.{u}` in
  `ordinal.{v}` as a principal segment when `u < v`. -/
def lift.principalSeg : @PrincipalSeg Ordinal.{u} Ordinal.{max (u + 1) v} (· < ·) (· < ·) :=
  ⟨↑lift.initialSeg.{u, max (u + 1) v}, univ.{u, v}, by
    refine' fun b => inductionOn b _; intro β s _
    rw [univ, ← lift_umax]; constructor <;> intro h
    · rw [← lift_id (type s)] at h ⊢
      cases' lift_type_lt.{_,_,v}.1 h with f
      cases' f with f a hf
      exists a
      revert hf
      -- Porting note: apply inductionOn does not work, refine does
      refine inductionOn a ?_
      intro α r _ hf
      

Proof state:
case mp.intro.mk
α✝ : Type u
β✝ : Type u_1
γ : Type u_2
r✝ : α✝ → α✝ → Prop
s✝ : β✝ → β✝ → Prop
t : γ → γ → Prop
b : Ordinal.{max (u + 1) v}
β : Type (max (u + 1) v)
s : β → β → Prop
inst✝¹ : IsWellOrder β s
h : lift.{max (u + 1) v, max (u + 1) v} (type s) < lift.{max (u + 1) v, u + 1} (type fun x x_1 => x < x_1)
f : s ↪r fun x x_1 => x < x_1
a : Ordinal.{u}
α : Type u
r : α → α → Prop
inst✝ : IsWellOrder α r
hf : ∀ (b : Ordinal.{u}), b < type r ↔ ∃ a, f a = b
⊢ initialSeg.toRelEmbedding (type r) = lift.{max (u + 1) v, max (u + 1) v} (type s)

Next tactic:
refine'
        lift_type_eq.{u, max (u + 1) v, max (u + 1) v}.2
          ⟨(RelIso.ofSurjective (RelEmbedding.ofMonotone _ _) _).symm⟩
/-- Principal segment version of the lift operation on ordinals, embedding `ordinal.{u}` in
  `ordinal.{v}` as a principal segment when `u < v`. -/
def lift.principalSeg : @PrincipalSeg Ordinal.{u} Ordinal.{max (u + 1) v} (· < ·) (· < ·) :=
  ⟨↑lift.initialSeg.{u, max (u + 1) v}, univ.{u, v}, by
    refine' fun b => inductionOn b _; intro β s _
    rw [univ, ← lift_umax]; constructor <;> intro h
    · rw [← lift_id (type s)] at h ⊢
      cases' lift_type_lt.{_,_,v}.1 h with f
      cases' f with f a hf
      exists a
      revert hf
      -- Porting note: apply inductionOn does not work, refine does
      refine inductionOn a ?_
      intro α r _ hf
      refine'
        lift_type_eq.{u, max (u + 1) v, max (u + 1) v}.2
          ⟨(RelIso.ofSurjective (RelEmbedding.ofMonotone _ _) _).symm⟩
      · 

Proof state:
case mp.intro.mk.refine'_1
α✝ : Type u
β✝ : Type u_1
γ : Type u_2
r✝ : α✝ → α✝ → Prop
s✝ : β✝ → β✝ → Prop
t : γ → γ → Prop
b : Ordinal.{max (u + 1) v}
β : Type (max (u + 1) v)
s : β → β → Prop
inst✝¹ : IsWellOrder β s
h : lift.{max (u + 1) v, max (u + 1) v} (type s) < lift.{max (u + 1) v, u + 1} (type fun x x_1 => x < x_1)
f : s ↪r fun x x_1 => x < x_1
a : Ordinal.{u}
α : Type u
r : α → α → Prop
inst✝ : IsWellOrder α r
hf : ∀ (b : Ordinal.{u}), b < type r ↔ ∃ a, f a = b
⊢ β → α

Next tactic:
exact fun b => enum r (f b) ((hf _).2 ⟨_, rfl⟩)