我在编写一个从元组中的列表中删除元素的函数时遇到了问题。
问题是,我希望函数返回元组。但是,使用delete
中的Data.List
函数会给我一个列表。
代码:
-- type Value = Int
type Cell = (Int, [Int])
type Board = [Cell]
----------- your solution goes here --------------
-- solvem :: Board -> Board
-- solvem bd = ???
deleteCandidate :: Int -> Cell -> Cell
deleteCandidate cand c1 = delete cand (snd c1) -- This gives me trouble
updateNeighbors :: Cell -> Cell -> Cell
updateNeighbors c1 c2 | isNeighbor c1 c2 = deleteCandidate (head (snd c1)) c2
| otherwise = c2
由于Haskell中的数据是不可变的,我如何在deleteCandidate
函数中返回元组?我需要重建一个细胞吗?
答案 0 :(得分:6)
简单地模式匹配元组以提取两个部分,对其中一个进行操作,然后将它们重新组合成一个新的元组:
deleteCandidate :: Int -> Cell -> Cell
deleteCandidate cand (x, xs) = (x, delete cand xs)
或者,由于(a,)
有一个Functor
实例,您可以编写
deleteCandidate :: Int -> Cell -> Cell
deleteCandidate cand = fmap (delete cand)
或者,更短的是,您也可以忽略显式的cand
参数,并将deleteCandidate表示为一个简单的函数组合:
deleteCandidate :: Int -> Cell -> Cell
deleteCandidate = fmap . delete
就个人而言,我最喜欢第二个版本,因为我发现很难想到这个组合是如何工作的,以及它与(fmap delete)
的区别。