我知道这个问题早先已被提出,但答案偏离了主要问题。
这是一个检查Haskell中是否存在元素的方法
elem’ x (y : ys) = if x == y then True else elem’ x ys
我感到困惑的是,在Haskell (y : ys)
中,这会将y添加到y,因此该函数如何确实检查元素是否存在?因为我没有看到任何循环,除了递归调用将y
传递给ys
。
请赐教。
答案 0 :(得分:4)
我没有看到任何循环,除了递归调用将相同的y传递给ys
递归部分将列表的 tail 传递给elem'
函数,而不是相同的列表。因此,一旦它到达列表的末尾,剩下的唯一尾部是空列表[]
,它应该以这样的另一个函数模式终止:
elem' _ [] = False
修改:进一步澄清您的评论
你可以像这样描绘递归调用:
-- assuming elem' is defined as:
elem' _ [] = False
elem' x (y : ys) = if x == y then True else elem' x ys
-- calling elem' trying to find 6 in [1..5]
elem' 6 (1 : [2, 3, 4, 5]) = if 6 == 1 then True else elem' 6 [2, 3, 4, 5]
elem' 6 (2 : [3, 4, 5]) = if 6 == 2 then True else elem' 6 [3, 4, 5]
elem' 6 (3 : [4, 5]) = if 6 == 3 then True else elem' 6 [4, 5]
elem' 6 (4 : [5]) = if 6 == 4 then True else elem' 6 [5]
elem' 6 (5 : []) = if 6 == 5 then True else elem' 6 []
elem' 6 [] = False
答案 1 :(得分:0)
我感到困惑的是,在Haskell(y:ys)中,这会将y添加到ys
不,它不是,pattern matching
功能,它实际上将列表的第一个值绑定到y
,其余部分绑定到ys
。
因此,当您进行递归调用elem’ x ys
时,您正在评估列表的其余部分。
这称为tail recursion pattern