我发现了一个方便的功能:
coerce : ∀ {ℓ} {A B : Set ℓ} → A ≡ B → A → B
coerce refl x = x
定义具有索引类型的函数时。在索引在定义上不相等的情况下,i,e,必须使用引理来显示类型匹配。
zipVec : ∀ {a b n m } {A : Set a} {B : Set b} → Vec A n → Vec B m → Vec (A × B) (n ⊓ m)
zipVec [] _ = []
zipVec {n = n} _ [] = coerce (cong (Vec _) (0≡n⊓0 n)) []
zipVec (x ∷ xs) (y ∷ ys) = (x , y) ∷ zipVec xs ys
注意,但这个例子很容易重写,所以不需要强制:
zipVec : ∀ {a b n m } {A : Set a} {B : Set b} → Vec A n → Vec B m → Vec (A × B) (n ⊓ m)
zipVec [] _ = []
zipVec (_ ∷ _) [] = []
zipVec (x ∷ xs) (y ∷ ys) = (x , y) ∷ zipVec xs ys
有时模式匹配无济于事。
问题:但我想知道,这个功能之类的东西是否已经在agda-stdlib
?对于Agda,有什么类似 hoogle 的东西,或类似 SearchAbout 的东西吗?
答案 0 :(得分:5)
我不认为你的coerce
功能正是如此。然而,它是subst
的一个更通用的函数 - Relation.Binary.PropositionalEquality
(平等的替代属性)的一个特例:
subst : ∀ {a p} {A : Set a} (P : A → Set p) {x y : A}
→ x ≡ y → P x → P y
subst P refl p = p
如果您选择P = id
(来自Data.Function
,或只是写λ x → x
),则会获得:
coerce : ∀ {ℓ} {A B : Set ℓ} → A ≡ B → A → B
coerce = subst id
顺便说一句,您最不可能找到预定义此功能的原因是Agda通过coerce
处理rewrite
这样的问题:
postulate
n⊓0≡0 : ∀ n → n ⊓ 0 ≡ 0
zipVec : ∀ {a b n m} {A : Set a} {B : Set b}
→ Vec A n → Vec B m → Vec (A × B) (n ⊓ m)
zipVec [] _ = []
zipVec {n = n} _ [] rewrite n⊓0≡0 n = []
zipVec (x ∷ xs) (y ∷ ys) = (x , y) ∷ zipVec xs ys
这是一个更复杂的语法糖:
zipVec {n = n} _ [] with n ⊓ 0 | n⊓0≡0 n
... | ._ | refl = []
如果您熟悉with
的工作原理,请尝试弄清楚rewrite
的工作原理;它很有启发性。