[英]Haskell Deriving Mechanism for Agda
我想知道Agda中是否有類似於Haskell deriving Eq
子句的東西---那么我下面也有一個相關的問題。
例如,假設我有玩具語言的類型,
data Type : Set where
Nat : Type
Prp : Type
然后我可以通過模式匹配和Cc Ca
實現可判定的相等性,
_≟ₜ_ : Decidable {A = Type} _≡_
Nat ≟ₜ Nat = yes refl
Nat ≟ₜ Prp = no (λ ())
Prp ≟ₜ Nat = no (λ ())
Prp ≟ₜ Prp = yes refl
我很好奇這是否可以機械化或自動化,以某種方式類似於在Haskell中完成的方式:
data Type = Nat | Prp deriving Eq
謝謝!
雖然我們討論類型的主題,但我想實現我的正式類型為Agda類型:Nat只是自然數,而Prp是小命題。
⟦_⟧Type : Type → Set ?
⟦ Nat ⟧Type = ℕ
⟦ Prp ⟧Type = Set
可悲的是,這不起作用。 我嘗試通過提升解決這個問題但失敗了,因為我對如何使用水平提升沒有任何線索。 任何幫助表示贊賞!
上述函數的一個示例用法是,
record InterpretedFunctionSymbol : Set where
field
arity : ℕ
src tgt : Type
reify : Vec ⟦ src ⟧Type arity → ⟦ tgt ⟧Type
謝謝你讓我感到羞恥!
“數據類型的宇宙學 ”中的“7.3.2。數據類型的派生操作”一章顯示了如何使用描述推導操作。 雖然,派生的Eq
在那里相當弱。
基本思想是使用一些一階編碼表示數據類型,即根據某些通用數據類型,並定義對此數據類型的操作,因此根據它編碼的所有內容都可以由這些通用操作處理。 我在這里詳細介紹了這種機器的簡單版本。
如果你有一個封閉的宇宙,你可以得到一個更強的Eq
。 使用類似於描述的方法(應該同樣具有表現力,但我沒有檢查)和封閉的宇宙我在這里定義了通用show
,它允許例如在命名構造函數后打印元組的向量:
instance
named-vec : {A : Type} -> Named (vec-cs A)
named-vec = record { names = "nil" ∷ "cons" ∷ [] }
test₂ : show (Vec (nat & nat) 3 ∋ (7 , 8) ∷ᵥ (9 , 10) ∷ᵥ (11 , 12) ∷ᵥ []ᵥ)
≡ "(cons 2 (7 , 8) (cons 1 (9 , 10) (cons 0 (11 , 12) nil)))"
test₂ = prefl
其中Vec
是根據類似於Desc
數據類型定義的。 Eq
案例應該類似,但更復雜。
以下是Lift
使用方法:
⟦_⟧Type : Type → Set₁
⟦ Nat ⟧Type = Lift ℕ
⟦ Prp ⟧Type = Set
ex₁ : ∀ A -> ⟦ A ⟧Type
ex₁ Nat = lift 0
ex₁ Prp = ℕ
ex₂ : ∀ A -> ⟦ A ⟧Type -> Maybe ℕ
ex₂ Nat n = just (lower n) -- or (ex₂ Nat (lift n) = just n)
ex₂ Prp t = nothing
如果A : Set α
然后Lift A : Set (α ⊔ ℓ)
任何ℓ
。 所以,當你有ℕ : Set
和Set : Set₁
,要解除ℕ
從Set
到Set₁
,這是剛剛Lift ℕ
-在簡單的情況下,你不需要提供ℓ
明確。
要構建包含在Lift
中的數據類型的元素,請使用lift
(如在lift 0
)。 要使這個元素恢復原狀,你可以使用lower
元素,因此lift
和lower
是相互反轉的。 注意雖然lift (lower x)
不一定與x
在同一個宇宙中,因為lift (lower x)
“刷新” ℓ
。
更新 :現在show
鏈接已斷開(我應該使用永久鏈接)。 但是現在有一個更好的例子: 整個庫為常規Agda數據類型派生Eq
。
有關在Agda中“派生Eq”的實際實現,您可以在https://github.com/UlfNorell/agda-prelude上查看Ulf的agda-prelude。 特別是,模塊Tactic.Deriving.Eq包含用於為一般類(簡單和索引)數據類型自動生成可判定等式的代碼。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.