我是 Haskell 的新手。我写了这段代码:
deleteDuplicates :: [a] -> [a]
deleteDuplicates [] = []
deleteDuplicates (x:xs)
| x == (head xs) = x : (deleteDuplicates (tail xs))
| otherwise = x : (head xs) : (deleteDuplicates (tail xs))
这个错误是什么意思,为什么会发生?我是不是不小心比较了两种不同的类型?
set2.hs:10:3:
Could not deduce (Eq a) from the context ()
arising from a use of `==' at set2.hs:10:3-16
Possible fix:
add (Eq a) to the context of
the type signature for `deleteDuplicates'
In the expression: x == (head xs)
In a stmt of a pattern guard for
the definition of `deleteDuplicates':
x == (head xs)
In the definition of `deleteDuplicates':
deleteDuplicates (x : xs)
| x == (head xs) = x : (deleteDuplicates (tail xs))
| otherwise = x : (head xs) : (deleteDuplicates (tail xs))
最佳答案
您的类型签名是错误的:
deleteDuplicates :: [a] -> [a]
也就是说你的函数可以处理任何类型的列表,
a
,但事实并非如此!你稍后打电话:x == (head xs)
所以你必须能够比较你的类型是否相等。这意味着签名必须是:
deleteDuplicates :: Eq a => [a] -> [a]
在这种情况下,最好删除您的显式类型签名,在 GHCi 中加载函数并发现解释器认为它应该具有的类型(通过
:t deleteDuplicates
)。更多错误
此外,您对
head
的使用有一个坏主意。 head
是一个偏函数,当 xs == []
时会失败.我建议你扩展模式匹配:deleteDuplicates (x1:x2:xs)
| x1 == x2 = ...
| otherwise = x1 : deleteDuplicates (x2:xs)
还要注意对
otherwise
的修复案件。您跳过了 x2,但是如果 x2 匹配列表中的下一个元素呢?类似 [1,2,2,3]
会发现 1 /= 2
然后递归会得到列表 [2,3]
- 哎呀!
关于haskell - 无法从上下文中推导出 (Eq a) (...),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/5806930/