Haskell:还有其他类似“_”的东西可以用来表示你不关心价值是什么吗?

时间:2011-10-23 22:05:11

标签: haskell operators ghci

所以我写了一个hexapawn游戏,我试图创建一个函数,如果董事会处于获胜状态,则返回True,此时看起来像这样:

checkWin :: BoardState -> Bool
checkWin b1@(blackPieces,whitePieces,turn,size,win)
  |(length blackPieces) == 0 = True
  |(length whitePieces) == 0 = True
  |length (generateMoves b1) == 0 = True
  |otherwise = False

所以如果没有黑色或白色碎片或没有人可以移动但是如果一个对手的棋子到达棋盘的末端(另一种赢得六声道的方式)则不起作用。变量 blackPieces whitePieces 是坐标列表,即[(1,1),(2,1),(3,1)]这些棋子在哪里 size n的电路板(如果白色转动则为真)

我很想将这些条件添加到方法中,但编译器不喜欢它。

  |(_,1) `elem` whitePieces = True
  |(_,size) `elem` blackPieces = True

还有其他方式可以说“ whitePieces 中是否有任何元组是第二个元素是1(即到达了电路板的另一侧)。”

提前致谢有用的评论。

3 个答案:

答案 0 :(得分:7)

所以我们想要一个函数,它接收一些[a]的列表,一个谓词(a->Bool)的谓词,并返回一个Bool。快速查看Hoogle,然后我们回来

any :: (a -> Bool) -> [a] -> Bool
Applied to a predicate and a list, any determines if any element of
the list satisfies the predicate. For the result to be False, the list must be finite

所以

 (_,1) `elem` whitePieces 

变为

 any (\(_, x) -> x == 1) whitePieces

或(正如eternalmatt提醒我的那样)

any (==1) ( map snd whitePieces )

等等


顺便说一下,检查的最佳方法是列表为空是通过模式匹配或null函数。长度== 0方法将遍历所有链表,如果列表是无限的,甚至可能进入无限循环。

答案 1 :(得分:2)

您可以使用filter

not $ null (filter wincond whitePieces)
    where wincond x = snd x == 1

如果带有第二个条目True的{​​{1}}列表不是空列表(whitePieces

,则此表达式为1

或者您可以使用[]

map

此表达式:首先检查or (map (\x -> snd x == size) blackPieces) 的元素是否具有等于blackPieces的第二个条目,并提供sizeTrues的列表({{1} })然后函数Falses给出[Bool],如果其中任何一个是or

答案 2 :(得分:2)

编译器不喜欢的原因是因为_仅适用于模式匹配。下划线表示“我可以将这部分数据绑定到变量名称,但我不需要。”

您尝试使用它的方式不同:您基本上说“是否存在 x(x,1)whitePieces的元素? “

你能看出区别吗?另请参阅Haskell 2010 > Expressions # Patter Matching