枚举Python中按两个字段排序的列表

时间:2019-03-08 15:52:13

标签: python sorting enumerate

我有一个这样的数组:
字段4是1,2,3的平均值,字段5是1,2,3的最小值。

unittest.cfg

已按字段4然后按字段5排序。
我希望列举此列表,以创建一种“等级”或“讲台”。

enumerate() 不起作用,因为如您所见,某些字段绑定在字段4和5上,因此它们的“等级”应该相同。
例如,第一个值应类似于:

[['name0', 24, 19, 25, 22.67, 19],
 ['name1', 25, 19, 25, 23.0, 19],
 ['name2', 25, 19, 25, 23.0, 19],
 ['name3', 24, 22, 23, 23.0, 22],
 ['name4', 27, 19, 25, 23.67, 19],
 ['name5', 27, 19, 25, 23.67, 19],
 ['name6', 28, 19, 26, 24.33, 19],
 ['name7', 28, 19, 26, 24.33, 19],
 ['name8', 28, 19, 26, 24.33, 19],
 ['name9', 26, 22, 27, 25.0, 22],
 ['name10', 27, 23, 25, 25.0, 23],
 ['name11', 30, 19, 27, 25.33, 19],
 ['name12', 24, 31, 28, 27.67, 24],
 ['name13', 28, 27, 28, 27.67, 27],
 ['name14', 27, 29, 27, 27.67, 27],
 ['name15', 29, 26, 29, 28.0, 26],
 ['name16', 29, 26, 30, 28.33, 26],
 ['name17', 30, 31, 26, 29.0, 26],
 ['name18', 33, 27, 30, 30.0, 27],
 ['name19', 29, 31, 30, 30.0, 29],
 ['name20', 30, 36, 31, 32.33, 30],
 ['name21', 36, 30, 32, 32.67, 30],
 ['name22', 38, 33, 36, 35.67, 33],
 ['name23', 30, 27, 99, 52.0, 27],
 ['name24', 99, 27, 32, 52.67, 27],
 ['name25', 37, 99, 36, 57.33, 36]]

无法找到一种干净的方法来解决这个问题。 感谢您的帮助。

4 个答案:

答案 0 :(得分:1)

假定列表已排序,则可以使用恰当命名的groupbyitemgetter按子列表的第4个和第5个元素对子列表进行分组。在enumerate返回的迭代器上使用groupby

from itertools import groupby
from operator import itemgetter

# data = [['name0', ...
[ [str(i+1)] + l for i, (k, g) in enumerate(groupby(data, key=itemgetter(4, 5))) for l in g ]

输出:

[
    ['1', 'name0', 24, 19, 25, 22.67, 19],
    ['2', 'name1', 25, 19, 25, 23.0, 19],
    ['2', 'name2', 25, 19, 25, 23.0, 19],
    ['3', 'name3', 24, 22, 23, 23.0, 22],
    ['4', 'name4', 27, 19, 25, 23.67, 19],
    ['4', 'name5', 27, 19, 25, 23.67, 19],
    ['5', 'name6', 28, 19, 26, 24.33, 19],
    ['5', 'name7', 28, 19, 26, 24.33, 19],
    ['5', 'name8', 28, 19, 26, 24.33, 19],
    ['6', 'name9', 26, 22, 27, 25.0, 22],
    ['7', 'name10', 27, 23, 25, 25.0, 23],
    ['8', 'name11', 30, 19, 27, 25.33, 19],
    ['9', 'name12', 24, 31, 28, 27.67, 24],
    ['10', 'name13', 28, 27, 28, 27.67, 27],
    ['10', 'name14', 27, 29, 27, 27.67, 27],
    ['11', 'name15', 29, 26, 29, 28.0, 26],
    ['12', 'name16', 29, 26, 30, 28.33, 26],
    ['13', 'name17', 30, 31, 26, 29.0, 26],
    ['14', 'name18', 33, 27, 30, 30.0, 27],
    ['15', 'name19', 29, 31, 30, 30.0, 29],
    ['16', 'name20', 30, 36, 31, 32.33, 30],
    ['17', 'name21', 36, 30, 32, 32.67, 30],
    ['18', 'name22', 38, 33, 36, 35.67, 33],
    ['19', 'name23', 30, 27, 99, 52.0, 27],
    ['20', 'name24', 99, 27, 32, 52.67, 27],
    ['21', 'name25', 37, 99, 36, 57.33, 36]
]

答案 1 :(得分:0)

i = 1开始并遍历它们并分配等级,如果下一行不同,则仅递增i += 1

答案 2 :(得分:0)

使用Pandasdense rank

import pandas as pd

df = pd.DataFrame(data = [['name0', 24, 19, 25, 22.67, 19],
 ['name1', 25, 19, 25, 23.0, 19],
 ['name2', 25, 19, 25, 23.0, 19],
 ['name3', 24, 22, 23, 23.0, 22],
 ['name4', 27, 19, 25, 23.67, 19],
 ['name5', 27, 19, 25, 23.67, 19],
 ['name6', 28, 19, 26, 24.33, 19],
 ['name7', 28, 19, 26, 24.33, 19],
 ['name8', 28, 19, 26, 24.33, 19],
 ['name9', 26, 22, 27, 25.0, 22],
 ['name10', 27, 23, 25, 25.0, 23],
 ['name11', 30, 19, 27, 25.33, 19],
 ['name12', 24, 31, 28, 27.67, 24],
 ['name13', 28, 27, 28, 27.67, 27],
 ['name14', 27, 29, 27, 27.67, 27],
 ['name15', 29, 26, 29, 28.0, 26],
 ['name16', 29, 26, 30, 28.33, 26],
 ['name17', 30, 31, 26, 29.0, 26],
 ['name18', 33, 27, 30, 30.0, 27],
 ['name19', 29, 31, 30, 30.0, 29],
 ['name20', 30, 36, 31, 32.33, 30],
 ['name21', 36, 30, 32, 32.67, 30],
 ['name22', 38, 33, 36, 35.67, 33],
 ['name23', 30, 27, 99, 52.0, 27],
 ['name24', 99, 27, 32, 52.67, 27],
 ['name25', 37, 99, 36, 57.33, 36]], columns= ['1', '2', '3', '4', '5', '6'])

df["rank"] = df['5'].rank(method = "dense")
df

>
    1   2   3   4   5   6   rank
0   name0   24  19  25  22.67   19  1.0
1   name1   25  19  25  23.00   19  2.0
2   name2   25  19  25  23.00   19  2.0
3   name3   24  22  23  23.00   22  2.0
4   name4   27  19  25  23.67   19  3.0
5   name5   27  19  25  23.67   19  3.0
6   name6   28  19  26  24.33   19  4.0
7   name7   28  19  26  24.33   19  4.0
8   name8   28  19  26  24.33   19  4.0
9   name9   26  22  27  25.00   22  5.0
10  name10  27  23  25  25.00   23  5.0
11  name11  30  19  27  25.33   19  6.0
12  name12  24  31  28  27.67   24  7.0
13  name13  28  27  28  27.67   27  7.0
14  name14  27  29  27  27.67   27  7.0
15  name15  29  26  29  28.00   26  8.0
16  name16  29  26  30  28.33   26  9.0
17  name17  30  31  26  29.00   26  10.0
18  name18  33  27  30  30.00   27  11.0
19  name19  29  31  30  30.00   29  11.0
20  name20  30  36  31  32.33   30  12.0
21  name21  36  30  32  32.67   30  13.0
22  name22  38  33  36  35.67   33  14.0
23  name23  30  27  99  52.00   27  15.0
24  name24  99  27  32  52.67   27  16.0
25  name25  37  99  36  57.33   36  17.0

如果要列表列表-

df = df.set_index('rank').reset_index()
df.values.tolist()

答案 3 :(得分:0)

您可以在将None值填充到其中一项后,通过将列表与自身之间的位置进行压缩来对相邻项目进行配对,以便您可以遍历经过压缩的对以比较关键字段,如果它们相同,则可以重复使用以前的排名:

for i, ((*_, prev_mean, prev_min), (*_, mean, _min)) in enumerate(zip([(None, None)] + l, l)):
    l[i].insert(0, str(l[i - 1][0] if mean == prev_mean and _min == prev_min else i + 1))

假设列表列表存储为变量l,则l变为:

[['1', 'name0', 24, 19, 25, 22.67, 19],
 ['2', 'name1', 25, 19, 25, 23.0, 19],
 ['2', 'name2', 25, 19, 25, 23.0, 19],
 ['4', 'name3', 24, 22, 23, 23.0, 22],
 ['5', 'name4', 27, 19, 25, 23.67, 19],
 ['5', 'name5', 27, 19, 25, 23.67, 19],
 ['7', 'name6', 28, 19, 26, 24.33, 19],
 ['7', 'name7', 28, 19, 26, 24.33, 19],
 ['7', 'name8', 28, 19, 26, 24.33, 19],
 ['10', 'name9', 26, 22, 27, 25.0, 22],
 ['11', 'name10', 27, 23, 25, 25.0, 23],
 ['12', 'name11', 30, 19, 27, 25.33, 19],
 ['13', 'name12', 24, 31, 28, 27.67, 24],
 ['14', 'name13', 28, 27, 28, 27.67, 27],
 ['14', 'name14', 27, 29, 27, 27.67, 27],
 ['16', 'name15', 29, 26, 29, 28.0, 26],
 ['17', 'name16', 29, 26, 30, 28.33, 26],
 ['18', 'name17', 30, 31, 26, 29.0, 26],
 ['19', 'name18', 33, 27, 30, 30.0, 27],
 ['20', 'name19', 29, 31, 30, 30.0, 29],
 ['21', 'name20', 30, 36, 31, 32.33, 30],
 ['22', 'name21', 36, 30, 32, 32.67, 30],
 ['23', 'name22', 38, 33, 36, 35.67, 33],
 ['24', 'name23', 30, 27, 99, 52.0, 27],
 ['25', 'name24', 99, 27, 32, 52.67, 27],
 ['26', 'name25', 37, 99, 36, 57.33, 36]]