Python:筛选列表中具有唯一id值的对象
我有一个Python对象列表,如:Python:筛选列表中具有唯一id值的对象,python,list,filtering,Python,List,Filtering,我有一个Python对象列表,如: my_list = [ SomeObject(id="hello", name="world"), SomeObject(id="hello", name="world"), SomeObject(id="foo", name="bar"), ] 现在我想要一个新列表,它只包含具有唯一id值的对象,因此预期的列表将是
my_list = [
SomeObject(id="hello", name="world"),
SomeObject(id="hello", name="world"),
SomeObject(id="foo", name="bar"),
]
现在我想要一个新列表,它只包含具有唯一id
值的对象,因此预期的列表将是:
expected_list = [
SomeObject(id="hello", name="world"),
SomeObject(id="foo", name="bar"),
]
Python中有没有一种方法可以执行这样的列表过滤
更新:
我最后要做的是创建两个列表,
unique\u id\u list=[]
,和unique\u object\u list=[]
。对于循环:如果object.id
不在unique\u id\u列表中
,则将id追加到unique\u id\u列表中的项目中。否则什么也不做。请参考“最正确的方法”(投票答案)。将ID添加到集合中,然后删除非唯一的列表成员:
def some_object(id="bar", name="baz"):
return id, name
my_list = [
some_object(id="hello", name="world"),
some_object(id="hello", name="world"),
some_object(id="foo", name="bar"),
]
print(my_list)
ids = set()
for obj in my_list:
if (id := obj[0]) in ids:
del my_list[my_list.index(obj)]
ids.add(obj[0])
print(my_list)
返回:
[('hello', 'world'), ('hello', 'world'), ('foo', 'bar')]
[('hello', 'world'), ('foo', 'bar')]
循环遍历my_列表中的每个元素,对照预期_列表中的所有元素进行检查:如果其中任何元素与ID匹配,则不要将其添加到列表中
def删除重复项(总列表):
预期的_列表=[]
in_expected_list=False
对于总清单中的i:
对于预期_列表中的j:
如果j.id==i.id:
in_expected_list=True
如果不在\u预期\u列表中:
预期的_列表。追加(i)
in_expected_list=False
返回预期的\u列表
最干净的方法是,如果您能够自己定义SomeObject
类,那么通过定义使SomeObject
唯一的方法,并指定允许唯一性比较的\uuuueq\uuuuu
、\une\uuuuuuu和\uuhash\uuuu
方法<代码>\uuuu str\uuuuu
刚刚添加,以便我们可以使用值打印它,而不是打印,例如
将打印出筛选列表中的项目:
<SomeObject id=hello name=world>
<SomeObject id=foo name=bar>
您可以使用itertools.groupby
如下所示:
class SomeObject:
def __init__(self, **kwargs):
self.__dict__.update(kwargs)
my_list = [
SomeObject(id="hello", name="world"),
SomeObject(id="foo", name="bar"),
SomeObject(id="hello", name="world")
]
from itertools import groupby
sort_function = lambda obj: obj.id
my_list = [list(item)[0]
for key, item in groupby(sorted(my_list, key=sort_function), key=sort_function)]
print(my_list)
没有,但是写一个很简单。关于你的更新:-你可能会受益于使用set
而不是list
,因为O(1)
lookup而不是O(n)
,但这并不完全有效;询问者只需要唯一的id值,此方法也会筛选唯一的名称。感谢您的回答。2级for循环有点太多了。我最后要做的是创建两个列表,unique_id_list=[]和unique_object_list=[]。for loop:如果object.id不在unique\u id\u列表中,请将该id附加到unique\u id\u列表中的unique\u object\u列表项中。否则什么都不做,一点问题都没有!
<SomeObject id=hello name=world>
<SomeObject id=foo name=bar>
class SomeObject:
def __init__(self, **kwargs):
self.__dict__.update(kwargs)
my_list = [
SomeObject(id="hello", name="world"),
SomeObject(id="foo", name="bar"),
SomeObject(id="hello", name="world")
]
from itertools import groupby
sort_function = lambda obj: obj.id
my_list = [list(item)[0]
for key, item in groupby(sorted(my_list, key=sort_function), key=sort_function)]
print(my_list)