如果所有项都大于1,我需要返回一个布尔值True,否则返回False。这是我的尝试......
greaterOne :: Ord a=>a->Bool
greaterOne x = x > 1
checkLis :: Ord a=>[a]->Bool
checkLis [] = True
checkLis (x:xs)
| greaterOne x = checkLis xs
| otherwise = False
这是我得到的错误,我一直在努力修复它,但无济于事......
Could not deduce (Num a) arising from the literal ‘1’
from the context (Ord a)
bound by the type signature for greaterOne :: Ord a => a -> Bool
at pract.hs:23:15-28
Possible fix:
add (Num a) to the context of
the type signature for greaterOne :: Ord a => a -> Bool
In the second argument of ‘(>)’, namely ‘1’
In the expression: x > 1
In an equation for ‘greaterOne’: greaterOne x = x > 1
答案 0 :(得分:5)
暂时考虑一下这个表达式,
x > 1
我们确信1
是一个数字,我们需要将其与x
进行比较并返回结果。但我们不知道x
的类型。如果x
实际上是一个字符串怎么办?然后表达式将失败。但是Haskell的类型系统很强大,它会感觉到这里的混乱,并要求你手动修复它。它甚至为你提供了一个提示,
Possible fix:
add (Num a) to the context of
the type signature for greaterOne :: Ord a => a -> Bool
因此,您需要做的就是明确指定a
是类Num
的实例,如GHC建议的那样
checkLis :: Ord a => Num a => [a] -> Bool
checkLis [] = True
......
greaterOne :: Ord a => Num a => a -> Bool
greaterOne x = x > 1
现在,我们说,a
不仅仅是有序数据类型,而且实际上是类Num
。
您实际上可以使用内置函数all
来执行此操作。
> all greaterOne [2, 2, 3]
True
> all greaterOne [1, 2, 3]
False
all
函数检查函数是否作为第一个参数传递,对列表中的每个元素求值为True
。
我们实际上可以只用部分表达式来做同样的事情,比如这个
Prelude> all (> 1) [2, 2, 3]
True
Prelude> all (> 1) [1, 2, 3]
False