使用另一个列表作为"过滤器"对python中的dicts列表进行排序?

Som*_*DOS 2 python dictionary

b = [{'id': 'a'}, {'id': 'c'}, {'id': 'b'}, {'id': 'e'}]
Run Code Online (Sandbox Code Playgroud)

我需要这个成为:

b = [{'id': 'a'}, {'id': 'c'}, {'id': 'e'}, {'id': 'b'}]
Run Code Online (Sandbox Code Playgroud)

此新订单由另一个列表定义.

my_filter = ['a', 'c', 'e', 'b']
Run Code Online (Sandbox Code Playgroud)

......正如您所看到的,带有dicts的列表现在具有一系列在my_filter变量上显示的ID .

我能够重新安排这个但是使用了一堆fors而且效率不高.你知道更好的方法吗?我已经知道如何按字典的值对字典列表进行排序,但我需要这个顺序由另一个列表定义.

编辑:my_filter被命名filter,我改变了Dave Kirby的推荐,因为它是内置的.由于某些答案仍然存在filter于其中,因此,如果您在其中一些答案中看到此编辑部分,则应避免混淆filter.

Ign*_*ams 7

>>> sorted(b, key=lambda x: filter.index(x['id']))
[{'id': 'a'}, {'id': 'c'}, {'id': 'e'}, {'id': 'b'}]
Run Code Online (Sandbox Code Playgroud)


Kei*_*ens 5

请记住,Ignacio的解决方案相当于执行您想要避免的嵌套for循环.即它是n ^ 2.更有效的解决方案如下:

>>> filterdict = dict((k,i) for i,k in enumerate(filter))
>>> sorted(b, key=lambda x: filterdict[x['id']])
[{'id': 'a'}, {'id': 'c'}, {'id': 'e'}, {'id': 'b'}]
Run Code Online (Sandbox Code Playgroud)

要么:

>>> b.sort(key=lambda x: filterdict[x['id']])
>>> b
[{'id': 'a'}, {'id': 'c'}, {'id': 'e'}, {'id': 'b'}]
Run Code Online (Sandbox Code Playgroud)

就地排序.

编辑: antonakos的解决方案是最好的(2n),如果你的id是唯一的(这可能是一个安全的假设,但你没有指定,所以我不想假设).这是一种稍微简短的写作方式,以防有助于使其更清晰:

>>> d = dict((i['id'], i) for i in b)
>>> [d[key] for key in filter]
[{'id': 'a'}, {'id': 'c'}, {'id': 'e'}, {'id': 'b'}]
Run Code Online (Sandbox Code Playgroud)