1

嘿伙计们,我希望能够替换元组列表中的元组。这是我的想法:

let lst = [("john",3), ("greg",3), ("tom",2), ("rob",7), ("jason",4), ("tev",7)]

我希望能够从列表中删除任何元组,例如(“rob”,7),然后用新的元组(“ain”,3)替换它。最后,我的最终列表将如下所示:

lst = [("john",3), ("greg",3), ("tom",2), ("ain",3), ("jason",4), ("tev",7)]

感谢您提前提供帮助。

4

4 回答 4

9

这是不可能的。Haskell 是一种纯函数式语言,因此一旦变量具有值,它就会永久保持该值。

但是,您可以轻松地从旧列表中计算出新列表

map (\ x -> if x == ("rob",7) then ("ain",3) else x) lst
于 2012-05-06T21:30:48.983 回答
0
replaceTuple :: [(String, Int)] -> (String, Int) -> (String, Int) -> [(String, Int)]
replaceTuple tups old new = map check tups where
    check tup | tup == old = new
              | otherwise  = tup


main = print $ replaceTuple [("john",3), ("greg",3), ("tom",2), ("rob",7), ("jason",4), ("tev",7)] ("tev", 7) ("newperson", 9001)

这将(正如您从类型注释中看到的那样)仅适用于(String,Int)列表,这就是您所拥有的。但是,您可以定义一个更通用的替换函数,其类型签名为replace :: Eq b => [b] -> b -> b -> [b]. b必须是Eq类型类的实例,因为我们正在比较元素,这就是“Eq b => ...”的意思。

于 2012-05-06T21:35:37.743 回答
0

以下是您可以执行的操作:

import qualified Data.Map.Lazy as Map

lst = Map.fromList [("john",3), ("greg",3), ("tom",2), ("rob",7), ("jason",4), ("tev",7)]

lst2 = Map.insert "ain" 3 $ Map.delete "rob" lst

如果您使用的是解释型 Haskell,则过程基本相同:

Prelude> import qualified Data.Map.Lazy as Map
Prelude Data.Map.Lazy> let lst = Map.fromList [("john",3), ("greg",3), ("tom",2), ("rob",7),     ("jason",4), ("tev",7)]
Prelude Data.Map.Lazy> lst
fromList [("greg",3),("jason",4),("john",3),("rob",7),("tev",7),("tom",2)]
Prelude Data.Map.Lazy> let lst2 = Map.insert "ain" 3 $ Map.delete "rob" lst
Prelude Data.Map.Lazy> lst2
fromList [("ain",3),("greg",3),("jason",4),("john",3),("tev",7),("tom",2)]

请注意,“ain”不一定与“rob”在地图中的“位置”相同。然而,地图不像列表那样有排序的概念。

于 2012-05-06T23:37:54.887 回答
0

span当您想在列表中进行编辑时,我通常发现最简单的方法是使用orbreak或将列表分解splitAt,进行更改,然后将其粘合在一起++。所以在这种情况下,我会这样做:

case break (\ (key,val) -> key == "rob") lst of
  (_, []) -> error "key not found! :("
  (xs, _ : ys) -> xs ++ ("ain", 3) : ys

请注意,如果您使用Data.Sequence,那么有一个函数update可以完全按照您的意愿进行操作,而且速度更快。

于 2012-05-07T10:35:47.727 回答