所以我创建了两种整数表示:
data ZZ : Type where
PZ : Nat -> ZZ
Zero : ZZ
NZ : Nat -> ZZ
-- Represent an integer as a difference of two Nats.
data NatNat = NN Nat Nat
和两个转换函数:
toNatNat : ZZ -> NatNat
toNatNat (PZ k) = NN (S k) Z
toNatNat Zero = NN Z Z
toNatNat (NZ k) = NN Z (S k)
toZZ : NatNat -> ZZ
toZZ (NN pos neg) with (cmp pos neg)
toZZ (NN (n + S d) n) | CmpGT d = PZ d
toZZ (NN z z) | CmpEQ = Zero
toZZ (NN p (p + S d)) | CmpLT d = NZ d
请注意,那PZ Z
代表+1
,而不是0
。
现在我证明这些表示是同构的:
import Control.Isomorphism
toNatNatToZZId : (z : NatNat) -> toNatNat (toZZ z) = z
toNatNatToZZId (NN k j) with (cmp k j)
toNatNatToZZId (NN (S d) Z) | CmpGT d = Refl
toNatNatToZZId (NN Z Z) | CmpEQ = Refl
toNatNatToZZId (NN Z (S d)) | CmpLT d = Refl
toZZToNatNatId : (z : ZZ) -> toZZ (toNatNat z) = z
toZZToNatNatId (PZ k) = Refl
toZZToNatNatId Zero = Refl
toZZToNatNatId (NZ k) = Refl
zzIsoNatNat : Iso ZZ NatNat
zzIsoNatNat = MkIso toNatNat toZZ toNatNatToZZId toZZToNatNatId
令我惊讶的是,伊德里斯礼貌地点点头表示同意。
所以诚然,这正是我想要的,尽管我对我现在可以证明的事实感到有点不安NN 0 3 = NN 6 9
:
*Data/Verified/Z> the (NN 0 3 = NN 6 9) $ toNatNatToZZId (NN 6 9)
with block in Data.Verified.Z.toNatNatToZZId 6 9 (CmpGT 2) : NN 0 3 = NN 6 9
这似乎不对。毕竟,NN 0 3
在结构上与NN 6 9
. 那么伊德里斯到底是从哪里确信他们是一样的呢?这是一种预期的行为(我可以想象它是),如果是这样,它究竟是如何工作的?