从列表中删除元组(Haskell)

时间:2015-03-19 00:45:52

标签: list haskell tuples list-comprehension

我想编写一个函数,将像这样的元组列表作为参数:

remove'  [ ("a", True), ("b", False), ("c", False), ("d", True) ]

我想返回一个以False作为第二个值的元组列表,所以我希望我的函数返回

[ ("b", False), ("c", False) ]

这是我到目前为止所拥有的,但它不会加载到GHCi中。谁能帮我吗?谢谢

remove' :: [(a,b)] -> [(a,b)]
remove' [(a,b)] = [ c | c <- [(a,b)], c `notElem` True ]

3 个答案:

答案 0 :(得分:4)

由于你想匹配元组的第二个元素,你需要从元组中选择第二个元素并将其与False进行比较

remove' :: [(a, Bool)] -> [(a, Bool)]
remove' xs = [c | c <- xs, snd c == False]

snd函数将从每个元组中获取第二个元素,并将它们与False进行比较。只有匹配时,它们才会被收集在结果列表中。

由于第二个元素是布尔值,您可以使用not这样的函数

[c | c <- xs, (not . snd) c]

我们可以像这样的点符号表达相同的

[c | c <- xs, not(snd(c))]

注意:在您的计划中,您有

remove' [(a,b)] = ...

这意味着,只有在使用大小为1的元组列表调用remove时才会执行它。您可以像这样检查

remove' :: [(a, Bool)] -> [(a, Bool)]
remove' [(a, b)] = [(a, b)]

remove' [ ("a", True), ("b", False), ("c", False), ("d", True) ]

将打印

Non-exhaustive patterns in function remove'

这意味着您在函数定义中指定的模式未涵盖所有可能的输入。由于我们需要处理任意长度的元组列表,我们在xs中接受它并在列表理解中使用它。

答案 1 :(得分:1)

我很惊讶没有人说过

remove' = filter (not . snd)

答案 2 :(得分:0)

你只需要过滤并选择lambda中的第二项:

filter (\x -> (snd x) == False) [("a", False), ("b", True)]

响应:

[("a",False)]