python3排序对象列表由attr相同的值

时间:2017-07-07 17:59:28

标签: python python-3.x sorting

我的排序方法有问题。

这是我在列表中包含的对象: 地址类,具有城市属性

我的列表看起来像(简化):

[Address('Paris'), Address('Denver'), Address('Paris'), Address('Test'), Address('Denver')]

在这个例子中,我有两个重复的城市:巴黎和丹佛,

我希望得到如下结果:

[Address('Devenr'), Address('Denver'), Address('Paris'), Address('Paris'), Address('Test')]

按重复次数排序,如果是相同的数字,则按字母数字顺序排序。

我试过了:

self.dictionnary.sort(key=lambda address: len([x for x in self.dictionnary if address.city == x.city]))

通过这项工作......

任何人都可以帮助我吗?

提前谢谢!

2 个答案:

答案 0 :(得分:1)

import collections
counts = collections.Counter(address.city for address in self.dictionnary)
self.dictionnary.sort(key=lambda address: (-counts[address.city], address.city))

通过使用Counter在单独的步骤中计算重复项,每次需要新密钥时,可以节省扫描列表的开销。这可能会对长列表的运行时间产生很大影响。然后密钥成为一个元组;通过取计数的负数,较大的计数将在排序顺序中排在第一位。元组的第二部分,城市名称本身,只有在计数相等时才会被考虑。

答案 1 :(得分:1)

问题在于巴黎和丹佛都有2个计数器,因此它们不会被排序。

如果你将字符串添加到排序中,那么词汇就会被修改,它应该可以正常工作

示例:

from collections import Counter

l = ['a', 'b', 'a', 'b', 'c']
c = Counter(l)
l.sort(key=lambda x : -c[x])
# l is unchanged
l.sort(key=lambda x : (-c[x],x))
# l is ['a', 'a', 'b', 'b', 'c']

编辑:Mark的解决方案使用的计数器比每次重新计数要好得多。我要偷那个想法