2015-02-23 62 views
1

我有一个k元素的元组列表。我想对元素0,元素1等等进行排序,等等。我GOOGLE了,但我仍然无法弄清楚如何做到这一点。会是这样的吗?具有多个条件的元组排序列表

list.sort(key = lambda x : (x[0], x[1], ...., x[k-1]) 

特别是,我想使用不同的标准进行排序,例如,在元素0上递减,在元素1上递增等等。

+2

'list.sort()'应该就足够了。 – vaultah 2015-02-23 07:26:46

+0

建议:使用list.sort()。尝试排序简单元素列表,然后按第一个元素列出元组,然后按第二个元素列出元组列表。结合你的知识。 – dmitri 2015-02-23 07:29:47

回答

1

由于python's sort is stable for versions after 2.2(或perhaps 2.3),我能想到的最简单的实现是通过一系列的index, reverse_value元组的sort串行重复:

# Specify the index, and whether reverse should be True/False 
sort_spec = ((0, True), (1, False), (2, False), (3, True)) 

# Sort repeatedly from last tuple to the first, to have final output be 
# sorted by first tuple, and ties sorted by second tuple etc 
for index, reverse_value in sort_spec[::-1]: 
    list_of_tuples.sort(key = lambda x: x[index], reverse=reverse_value) 

这样做多次通过,因此在恒定时间成本方面效率可能很低,但就渐进复杂性而言仍然是O(nlogn)。

如果索引的排序顺序真正为0, 1... n-1, n,如果您的示例中显示了n大小的元组列表,那么您只需要一个True和False序列来表示您是否需要reverse,并且您可以使用enumerate添加索引。

sort_spec = (True, False, False, True) 
for index, reverse_value in list(enumerate(sort_spec))[::-1]: 
    list_of_tuples.sort(key = lambda x: x[index], reverse=reverse_value) 

尽管原始代码允许通过任何顺序的索引进行排序的灵活性。顺便提一下,这个“排序顺序”方法在Python Sorting HOWTO中推荐使用,只需稍作修改即可。

编辑 如果您没有作为排序依据一些指标升序和降序别人的要求,然后

from operator import itemgetter 
list_of_tuples.sort(key = itemgetter(1, 3, 5)) 

将指数1进行排序,然后联系将被索引3排序,并通过索引5进一步关联。但是,改变每个索引的升序/降序在一遍中是非平凡的。

0

所以我假设你想排序tuple_0升序,然后tuple_1降序,等等。有点冗长,但是这是你可能会寻找:

ctr = 0 
for i in range(list_of_tuples): 
    if ctr%2 == 0: 
     list_of_tuples[0] = sorted(list_of_tuples[0]) 
    else: 
     list_of_tuples[0] = sorted(list_of_tuples[0], reverse=True) 
    ctr+=1 

print list_of_tuples 
+0

'为ctr,我在枚举(范围(list_of_tuples))'可能会更好 – 2015-02-23 10:05:20

1
list.sort(key = lambda x : (x[0], x[1], ...., x[k-1]) 

这实际上是使用元组作为自己的排序键。换句话说,与没有参数调用sort()相同。

如果我假设你简化了问题,并且实际的元素实际上不是按你想排序的顺序(例如,最后一个值的优先级最高),你可以使用相同的技术,但重新排序的关键基于优先级的部分:

list.sort(key = lambda x : (x[k-1], x[1], ...., x[0]) 

在一般情况下,这是一个非常方便的技巧,即使是在像C++等语言(如果你使用的库):如果要排序的列表对象由几个不同优先级的成员组成,您可以按照优先级顺序构造一个包含所有相关成员的元组来构造排序键。

最后的诀窍(这是一个脱离主题,但它可能在某种程度上帮助你):当使用不支持“按键排序”思想的库时,通常可以通过构建获得相同的效果一个包含排序键的列表。因此,您不需要对Obj列表进行排序,而是可以构建一个元组列表:(ObjSortKey, Obj)。另外,只要将对象插入到有序集合中就行,如果它们的排序键是唯一的。 (排序关键字将是指数,在这种情况下)。