【发布时间】:2016-08-15 14:38:35
【问题描述】:
在Towards Observational Type Theory 的“5. Full OTT”部分的最后,作者展示了如何在 OTT 中定义 coercible-under-constructors 索引数据类型。这个想法基本上是将索引数据类型转换为参数化,如下所示:
data IFin : ℕ -> Set where
zero : ∀ {n} -> IFin (suc n)
suc : ∀ {n} -> IFin n -> IFin (suc n)
data PFin (m : ℕ) : Set where
zero : ∀ {n} -> suc n ≡ m -> PFin m
suc : ∀ {n} -> suc n ≡ m -> PFin n -> PFin m
Conor 在observational type theory (delivery) 的底部也提到了这种技术:
当然,解决方法是做 GADT 人所做的事情,并定义 归纳家庭明确地上升到命题平等。然后的 当然,您可以通过传递性来传输它们。
然而,Haskell 中的类型检查器知道范围内的相等约束,并在类型检查期间实际使用它们。例如。我们可以写
f :: a ~ b => a -> b
f x = x
在类型论中它不起作用,因为在范围内有一个 a ~ b 的证明不足以用这个等式重写:这个证明也必须是 refl,因为在由于终止问题(例如this),错误的假设类型检查变得无法确定。因此,当您在 Haskell 中对 Fin m 进行模式匹配时,m 在每个分支中都会被重写为 suc n,但这在类型论中不会发生,而是留下了 suc n ~ m 的明确证明。在 OTT 中,根本不可能对证明进行模式匹配,因此您既不能假装证明是 refl,也不能真正要求它。只能将证明提供给 coerce 或忽略它。
这使得编写任何涉及索引数据类型的东西变得非常困难。例如。向量的通常三行(包括类型签名)lookup 变成了这个野兽:
vlookupₑ : ∀ {n m a} {α : Level a} {A : Univ α} -> ⟦ n ≅ m ⇒ fin n ⇒ vec A m ⇒ A ⟧
vlookupₑ p (fzeroₑ q) (vconsₑ r x xs) = x
vlookupₑ {n} {m} p (fsucₑ {n′} q i) (vconsₑ {m′} r x xs) =
vlookupₑ (left (suc n′) {m} {suc m′} (trans (suc n′) {n} {m} q p) r) i xs
vlookupₑ {n} {m} p (fzeroₑ {n′} q) (vnilₑ r) =
⊥-elim $ left (suc n′) {m} {0} (trans (suc n′) {n} {m} q p) r
vlookupₑ {n} {m} p (fsucₑ {n′} q i) (vnilₑ r) =
⊥-elim $ left (suc n′) {m} {0} (trans (suc n′) {n} {m} q p) r
vlookup : ∀ {n a} {α : Level a} {A : Univ α} -> Fin n -> Vec A n -> ⟦ A ⟧
vlookup {n} = vlookupₑ (refl n)
可以稍微简化一下,因为如果具有可判定相等的数据类型的两个元素明显相等,那么它们在通常的内涵意义上也是相等的,并且自然数确实具有可判定相等,所以我们可以强制所有方程与其内涵对应物和模式匹配,但这会破坏vlookup 的一些计算属性,并且无论如何都是冗长的。在更复杂的情况下处理无法确定相等性的索引几乎是不可能的。
我的推理正确吗? OTT 中的模式匹配是如何工作的?如果这确实是一个问题,有什么方法可以缓解它?
【问题讨论】:
标签: haskell agda gadt type-theory observational-type-theory