@@ -49,6 +49,49 @@ def encodeBool : Bool → Fin 2
4949 | false => rfl
5050 | true => rfl
5151
52+ /-- Encode a character value as a `Fin` type. -/
53+ @[pp_nodot] def encodeChar (c : Char) : Fin 1112064 :=
54+ have : c.toNat < 1114112 := by
55+ match c.valid with
56+ | .inl h => apply Nat.lt_trans h; decide
57+ | .inr h => exact h.right
58+ if _ : c.toNat < 55296 then
59+ ⟨c.toNat, by omega⟩
60+ else
61+ ⟨c.toNat - 2048 , by omega⟩
62+
63+ /-- Decode a character value as a `Fin` type. -/
64+ def decodeChar (i : Fin 1112064 ) : Char :=
65+ if h : i.val < 55296 then
66+ Char.ofNatAux i.val (by omega)
67+ else
68+ Char.ofNatAux (i.val + 2048 ) (by omega)
69+
70+ @[simp] theorem encodeChar_decodeChar (x) : encodeChar (decodeChar x) = x := by
71+ simp only [decodeChar]
72+ split
73+ · simp [encodeChar, Char.ofNatAux, Char.toNat, UInt32.toNat]; intro; omega
74+ · simp [encodeChar, Char.ofNatAux, Char.toNat, UInt32.toNat]; intro; omega
75+
76+ @[simp] theorem decodeChar_encodeChar (x) : decodeChar (encodeChar x) = x := by
77+ ext
78+ simp [decodeChar, encodeChar]
79+ split
80+ · next h =>
81+ simp only [Char.toNat] at h
82+ simp [decodeChar, Char.ofNatAux, Char.toNat, dif_pos h]; rfl
83+ · next h =>
84+ have h0 : 57344 ≤ x.toNat ∧ x.toNat < 1114112 := by
85+ match x.valid with
86+ | .inl h => contradiction
87+ | .inr h =>
88+ constructor
89+ · exact Nat.add_one_le_of_lt h.left
90+ · exact h.right
91+ have h1 : ¬ x.toNat - 2048 < 55296 := by omega
92+ have h2 : 2048 ≤ x.toNat := by omega
93+ simp [dif_neg h1, Char.ofNatAux, Nat.sub_add_cancel h2]; rfl
94+
5295/-- Decode an optional `Fin` types. -/
5396def encodeOption : Option (Fin n) → Fin (n+1 )
5497 | none => 0
0 commit comments