问题描述
因此,我一直在尝试在 Idris 中以一种新的数据类型对二叉搜索树(而不仅仅是二叉树)的属性进行编码。
如果只使用数据类型(例如在 repl 中)来创建新树,它似乎工作得相当好。
这是目前的数据类型,它接收一个类型和那个类型的Maybe,基本上就是这棵树的最大值。函数 isLMaybe 和 isGMaybe 用于检查子树的值是否大于或小于根值。
isLMaybe: Ord a => Maybe a -> a -> Bool
isLMaybe nothing _ = True
isLMaybe (Just x) y = x < y
isGMaybe: Ord a => Maybe a -> a -> Bool
isGMaybe nothing _ = True
isGMaybe (Just x) y = x > y
data BST: (x: Type) -> Maybe x -> Type where
EmptyBST: Ord a => BST a nothing
NodeBST: Ord a => (l: BST a b) -> (v: a) -> (r: BST a c) -> {auto leftValues: So (isLMaybe b v)} -> {auto rightValues: So (isGMaybe c v)} -> BST a (Just v)
问题是,一旦我尝试创建一个插入函数,如下所示,它会抛出以下错误:
insertTest : (a: Type,c: Maybe a,d: Maybe a) => (x: a) -> BST a c -> BST a d
insertTest x EmptyBST = NodeBST EmptyBST x EmptyBST
insertTest x (NodeBST l v r) = case lessEqualGreater x v of
L => NodeBST (insertTest x l) v r
E => NodeBST l v r
G => NodeBST l v (insertTest x r)
N => NodeBST l v r
When checking right hand side of insertTest with expected type
BST a d
Type mismatch between
BST a (Just x) (Type of NodeBST EmptyBST x EmptyBST)
and
BST a d (Expected type)
Specifically:
Type mismatch between
Just x
and
d
我不明白为什么它认为 d
不是 Maybe a
的实例,因为在我得到错误之后,我试图将它明确地放入函数中,但我仍然得到同样的错误.
解决方法
您提供的类型签名并不代表您的想法。
insertTest : (a: Type,c: Maybe a,d: Maybe a) => (x: a) -> BST a c -> BST a d
此函数必须能够为 d
的任何可能值生成一个值。不只是Just x
。如果使用 insertTest
调用 {d=Nothing}
会发生什么?也许看看依赖对?