Python列表推导式:如何将唯一元素添加到列表中?

3

我试图编写更简单的代码将唯一元素添加到Python列表中。 我有一个包含字典列表的数据集,并尝试迭代字典内的列表。

为什么这不起作用? 它添加了所有项,包括重复项,而不是添加唯一项。

unique_items = []
unique_items = [item for d in data for item in d['items'] if item not in unique_items]

与更长的形式相比,以下是有效的:

unique_items = []
for d in data:
    for item in d['items']:
        if (item not in unique_items):
            unique_items.append(item)

有没有一种使用列表推导式使这个工作正常的方法,或者我只能使用双重循环?我希望保留这个顺序。
这是字典列表:
[{"items":["apple", "banana"]}, {"items":["banana", "strawberry"]}, {"items":["blueberry", "kiwi", "apple"]}]

输出应该为 ["apple", "banana", "strawberry", "blueberry", "kiwi"]

我注意到在另一篇文章中有人提出了类似的问题:Python list comprehension, with unique items,但我想知道是否还有其他方法可以做到这一点,而不是使用OrderedDict或者那是最好的方法。


请提供更多信息:您的字典列表对于任何提供帮助的人都非常有用。 - Abdou
使用集合更好,它会自动去除所有重复项。 - Copperfield
你想保持排序吗? - niemmi
是的,顺序很重要。 - user3226932
1
在这种情况下,另一个问题中的响应是最简单的方法。如果您真的想要替代方案,请查看OrderedSet recipe - niemmi
3个回答

3

all_items在列表推导式中并不会被持续覆盖,因此你一直在空列表中查找东西。

我会这样做:

data = [1, 2, 3, 4, 5, 6, 1, 2, 3, 4, 1, 2, 3, 4,]

items = []
_ = [items.append(d) for d in data if d not in items]
print(items)

我得到:

[1, 2, 3, 4, 5, 6]

但是,有更有效的方法来实现这一点。

有哪些更有效率的方法来完成这个任务? - user3226932
像在其他答案中提到的那样,setnumpy.unique 等等。 - Paul H

2

为什么不直接使用 set

例如 -

>>> data = {1: {'items': [1, 2, 3, 4, 5]}, 2: {'items': [1, 2, 3, 4, 5]}}
>>> {val for item in data for val in data[item]['items']}
>>> {1, 2, 3, 4, 5}

如果你想要一个列表:
>>> list(repeat above)
>>> [1, 2, 3, 4, 5]

为了表示一个集合,你不仅可以使用花括号{},还可以使用set关键字,因为对于一些人来说,花括号可能过于晦涩。

以下是语法链接。


值得注意的是,这种方法不像问题中的示例代码或https://dev59.com/FWnWa4cB1Zd3GeqPwxWE的答案那样保留顺序。 - niemmi

1
最简单的方法是使用OrderedDict
from collections import OrderedDict
from itertools import chain

l = [{"items":["apple", "banana"]}, {"items":["banana", "strawberry"]}, {"items":["blueberry", "kiwi", "apple"]}]
OrderedDict.fromkeys(chain.from_iterable(d['items'] for d in l)).keys() # ['apple', 'banana', 'strawberry', 'blueberry', 'kiwi']

如果你想要替代方案,请查看基于OrderedSetrecipepackage的内容。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接