Haskell守卫表达解释

时间:2016-09-17 11:30:28

标签: haskell

comp shows if two words are lexicographically equal or smaller 

import Data.Char
class MyComp a where
   comp :: a -> a -> Bool
instance MyComp Char where
   comp num1 num2 = (ord num1) <= (ord num2)       -- ord :: Char -> Int


instance MyComp a => MyComp [a] where
   comp [] _ = True
   comp _ [] = False
   comp (x:xs) (y:ys)
    | comp x y && comp y x = comp xs ys
    | comp x y = True
    | otherwise = False

上面的代码对我来说有点神秘。有人可以向我解释警卫的情况吗?他们为什么要查看comp x ycomp y x是否属实。不应该

| comp x y = comp xs ys
| otherwise = False

诀窍?

2 个答案:

答案 0 :(得分:2)

Sheets("TABLAK").Select Sheets.Add Dim ujfulneve As String ujfulneve = Sheets("MENU").Range("B2").Value Sheets(ActiveSheet).Name = ufjulneve 基本上是一个扩展的小于或等于函数。

您有疑问的代码是将类型comp中的小于或等于的定义扩展为类型a。它通过传统的词典排序定义来实现这一点。

现在,由于[a]MyComp之间没有正式关系,因此您无法真正询问Eq - 而是询问x == y和{{}的唯一方式根据{{​​1}},{1}}是相等的,你会在那里进行双重测试。

这个双重测试是为了处理这种情况:

x

现在,这应该是错误的,因为y应该在comp之前排序。但要做到这一点,你需要检查超出第一个字母。这就是你要问的代码正在做什么 - 它是在初始字母相等的情况下检查第二个(和后续)字母。

但是你并不总是检查后续的字母!那个案子怎么样:

"abcd" `comp` "aacd"

显然,即使"aacd"为真且"abcd"为假,也应如此。

答案 1 :(得分:1)

MyComp的定义可以看出,comp x y等同于x <= y。现在,定义instance MyComp a => MyComp [a]意味着如果为类型a的值定义了小于或等于的关系,那么它也为类型[a]的值定义,大概使用lexicographical order

字典顺序的工作方式是,如果要比较两个列表,首先要比较第一个列表的第一个元素和第二个列表的第一个元素。如果它们不同,那么您将使用该比较的结果作为两个列表的比较结果。如果另一方面它们是相等的,那么你看两个列表中的第二个元素,依此类推。这就是上面的代码尝试做的事情:comp x y && comp y x就像说x <= y && y <= x,这相当于说x等于y。如果发生了。然后根据字典顺序,你必须丢弃这两个元素并查看两个列表的其余部分。