按多个属性对列表进行排序?
我有一个列表清单:
[[12, 'tall', 'blue', 1],
[2, 'short', 'red', 9],
[4, 'tall', 'blue', 13]]
如果我想按一个元素排序,说高/短元素,我可以通过s = sorted(s, key = itemgetter(1))
。
如果我想根据高/短和颜色进行排序,我可以进行两次排序,每个元素排序一次,但有没有更快的方法?
一个键可以是一个返回元组的函数:
s = sorted(s, key = lambda x: (x[1], x[2]))
或者你可以使用itemgetter
(这是更快,并避免Python函数调用)实现相同:
import operator
s = sorted(s, key = operator.itemgetter(1, 2))
并注意,在这里你可以使用sort
而不是使用sorted
然后重新分配:
s.sort(key = operator.itemgetter(1, 2))
我不确定这是否是最pythonic的方法...我有一个元组列表,需要按降序整数值排序第一个和按字母顺序排序第二个。 这需要颠倒整数排序而不是按字母排序。 这是我的解决方案:(在考试中随时随地,我甚至不知道你可以'嵌套'排序函数)
a = [('Al', 2),('Bill', 1),('Carol', 2), ('Abel', 3), ('Zeke', 2), ('Chris', 1)]
b = sorted(sorted(a, key = lambda x : x[0]), key = lambda x : x[1], reverse = True)
print(b)
[('Abel', 3), ('Al', 2), ('Carol', 2), ('Zeke', 2), ('Bill', 1), ('Chris', 1)]
看起来你可以使用list
而不是tuple
。 当你抓取属性而不是列表/元组的'魔术索引'时,这变得更加重要。
在我的情况下,我想按类的多个属性进行排序,其中传入的键是字符串。 我需要在不同地方进行不同的排序,并且我希望客户端与之交互的父类具有通用的默认排序方式; 只有当我真的需要时才必须重写'排序键',但也可以将它们存储为类可以共享的列表
所以首先我定义了一个辅助方法
def attr_sort(self, attrs=['someAttributeString']:
'''helper to sort by the attributes named by strings of attrs in order'''
return lambda k: [ getattr(k, attr) for attr in attrs ]
然后使用它
# would defined elsewhere but showing here for consiseness
self.SortListA = ['attrA', 'attrB']
self.SortListB = ['attrC', 'attrA']
records = .... #list of my objects to sort
records.sort(key=self.attr_sort(attrs=self.SortListA))
# perhaps later nearby or in another function
more_records = .... #another list
more_records.sort(key=self.attr_sort(attrs=self.SortListB))
这将使用生成的lambda函数按object.attrA
对列表进行排序,然后使用object.attrB
假定object
具有与提供的字符串名称相对应的getter。 而第二种情况将被排序object.attrC
然后object.attrA
。
这也使得你可能会将外部排序选择暴露给消费者,单元测试,或者让他们告诉你他们希望如何在你的api中进行一些操作来完成排序,只需要给你一个列表而不是将它们耦合到您的后端实现。
链接地址: http://www.djcxy.com/p/70755.html上一篇: Sort a list by multiple attributes?
下一篇: Processing credit cards in React/Node using only open source tech