【问题标题】:Why does list comprehension not filter out duplicates?为什么列表推导不过滤掉重复项?
【发布时间】:2012-07-15 09:19:02
【问题描述】:

我有以下问题的解决方法。该解决方法将是一个 for 循环,其中包含一个包含在输出中的测试,如下所示:

#!/usr/bin/env python

def rem_dup(dup_list):
    reduced_list = []
    for val in dup_list:
        if val in reduced_list:
            continue
        else:
            reduced_list.append(val)

    return reduced_list

我问以下问题,因为我很好奇是否有列表理解解决方案。

给定以下数据:

reduced_vals = []
vals = [1, 2, 3, 3, 2, 2, 4, 5, 5, 0, 0]

为什么

reduced_vals = = [x for x in vals if x not in reduced_vals]

生成相同的列表?

>>> reduced_vals
[1, 2, 3, 3, 2, 2, 4, 5, 5, 0, 0]

我认为这与检查输出 (reduced_vals) 作为分配给列表的一部分有关。我很好奇,但确切的原因。

谢谢。

【问题讨论】:

  • 您可以使用this 回答非常接近。

标签: python list filter duplicates list-comprehension


【解决方案1】:

在这一行中:[x for x in vals if x not in reduced_vals]reduced_vals 中没有一个值不是,因为reduced_vals 是空列表[]。换句话说,没有任何内容被过滤,vals 中的所有元素都被返回。

如果你试试这个:

[x for x in vals if x in reduced_vals]

结果是空列表[],因为所有不是reduced_vals(它是空的)。我相信您对过滤部分在列表理解中的工作方式感到困惑:您看,过滤器只选择那些使条件为True 的值,但它不会防止重复值。

现在,如果您需要过滤掉重复项,那么列表推导式就不是适合这项工作的工具。为此,请使用集合 - 虽然它不一定会保留原始列表的顺序,但它会保证元素是唯一的:

vals = [1, 2, 3, 3, 2, 2, 4, 5, 5, 0, 0]
list(set(vals))
> [0, 1, 2, 3, 4, 5]

【讨论】:

    【解决方案2】:

    因为reduced_vals 在评估列表理解期间没有改变。

    【讨论】:

      【解决方案3】:

      您正在针对一个空列表进行测试。

      首先对表达式进行完整计算,然后将其分配为 reduced_vals 的新值,因此在计算完整列表表达式之前,该值一直为空。

      换句话说,表达式[x for x in vals if x not in reduced_vals] 是单独执行的。如果您以稍微修改的方式查看代码可能会有所帮助:

      temp_var = [x for x in vals if x not in reduced_vals]
      reduced_vals = temp_var
      del temp_var
      

      上面是直接将列表表达式的结果分配给reduced_vals的道德等价物,但我通过使用第二个变量更清楚地分开分配结果。

      【讨论】:

        【解决方案4】:

        因为列表推导式中的元素在整个列表构建完成之前不会分配给reduced_vals。如果您想完成这项工作,请使用带有 .append()for 循环。

        【讨论】:

        • 这已经是原始代码中发生的事情(没有 OP 的“解决方法”)
        【解决方案5】:

        列表推导式创建一个新列表,而reduced_vals 在列表推导式评估期间始终指向空列表。

        Python 中赋值的语义是:计算右侧并将结果对象绑定到左侧的名称。对裸名的赋值从不改变任何对象。

        顺便说一句,您应该使用set()collections.OrderedDict.fromkeys() 以有效的方式删除重复项(取决于您是否需要保留顺序)。

        【讨论】:

        • 如何包含集合?我只是想;它是进口的;但我得到了一个错误>>> collections.OrderedDict.fromkeys(color) Traceback (last recent call last): File "", line 1, in NameError: name 'collections' is not defined I'm使用 Python 2.7.x
        • @octopusgrabbus: import collections
        • >>> 导入集合 >>> collections.OrderedDict.fromkeys(color) Traceback(最近一次调用最后):文件“”,第 1 行,在 中 AttributeError:'module ' 对象没有属性 'OrderedDict'
        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2013-07-27
        • 2018-11-01
        • 1970-01-01
        • 1970-01-01
        • 2015-08-25
        • 2020-01-16
        • 1970-01-01
        相关资源
        最近更新 更多