【问题标题】:Double elements in a list if values are over certain threshold如果值超过某个阈值,则列表中的双元素
【发布时间】:2014-11-12 04:31:10
【问题描述】:

例如,尝试将列表中大于 5 的元素加倍。

将列表中的每个元素加倍我会这样做

doubleAll n = [2*x| x <-n]

现在我想使用列表推导将列表中大于 5 的所有元素加倍。 所以如果我这样做

doubleAll n = [2*x| x <-n, x>5]

我的列表 [1,2,3,4,5] 将导致 [10]。但我希望我的列表显示 [1,2,3,4,10]

谁能解释我做错了什么以及如何解决?

【问题讨论】:

  • 一个简单的修复是doubleAll n = [if x &gt; 5 then 2*x else x | x &lt;-n]
  • 您做错的是,如果条件为假,则在列表推导中放置一个布尔条件只会跳过该元素,而不是像您预期的那样包含未更改的元素。
  • 现在看到这有很大帮助。因为我是haskell的新手,所以我不熟悉语法。如果你能把这个写成答案,我会接受的:)谢谢。

标签: haskell functional-programming


【解决方案1】:

[2*x| x &lt;-n, x&gt;5] 的解释是:

  1. n 中取出下一个元素并将其命名为x
  2. 如果x&gt;5,则继续,否则转到步骤1
  3. 返回值2*x 作为列表的下一个元素。
  4. 重复

由此可见x&gt;5 过滤掉了n 的元素。表达式等价于:

map (\x -> 2*x) ( filter (\x -> x>5) n )

正如Arthur 提到的,你想要这样的东西:

[ if x > 5 then 2*x else x | x <- n ]

它的解释是:

  1. n 的下一个值并将其命名为x
  2. 返回值 if x &gt; 5 then 2*x else x 作为列表的下一个值。

【讨论】:

    【解决方案2】:

    如果您不使用列表推导并使用 mapfilter 操作,这更容易理解:

    -- Apply a function to every element of the list.
    map :: (a -> b) -> [a] -> [b]
    
    -- Throw out list elements that don't pass the test.
    filter :: (a -> Bool) -> [a] -> [a]
    

    您原来的doubleAll 是这样的:

    -- Multiply every element of the list by two.
    doubleAll xs = map (*2) xs
    

    只有在x &gt; 5 时才加倍的版本是这样的:

    -- Apply the `step` function to every element of the list.  This step function 
    -- multiplies by two if x >= 5, otherwise it just returns its argument.
    doubleAll xs = map step xs
        where step x | x >= 5    = 2*x
                     | otherwise = x
    

    您编写的列表理解版本的问题在于它等效于:

    -- Filter out list elements that are smaller than 5, then double the remaining ones.
    doubleAll xs = map (*2) (filter (>=5) xs)
    

    产生您想要的结果的列表理解解决方案将改为:

    doubleAll xs = [if x >= 5 then x*2 else x | x <- xs]
    

    作为一个更笼统的评论,我总是建议新手远离列表推导并学习更通用且不那么神奇的高阶列表函数。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2014-08-05
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2017-10-16
      • 1970-01-01
      • 2015-07-21
      • 2021-12-17
      相关资源
      最近更新 更多