首页 > 解决方案 > 根据元组中的两个项目对列表进行排序 - Python

问题描述

我将感谢一些帮助来修复我的代码并获得正确的结果。

假设我的列表(列表中的元组)可能有 3 个输出,例如:

list1 = [('a', 3.30, '' ,'' ), ('b', 3.20, '' , '' ), ......]

list2 = [('a', 3.30, 2.90, '' ), ('b', 3.20, 2.95, '' ), ........]

list3 = [('a', 3.30, 2.90, '' ), ('b', 3.20, '' , ''), ........]

我的清单总是在 [1] 位置标价,有时在 [2] 位置标价。我想根据所有价格对我的清单进行排序。我下面的代码适用于示例 list1 和示例 list2。

from operator import itemgetter
sort_list = sorted(list, key=itemgetter(1))
sort_list = sorted(sort_list, key=itemgetter(2))
print(sort_list)

但是 forlist3不能很好地工作,因为它识别出 [2] 的空单元格并首先短路。如果有的话,我想忽略空单元格的价格。所以打印输出list3应该是

('a', 3.30, 2.90, '' ), ('b', 3.20, '' , '').

因为,2.90 < 3.20我忽略了空白

谢谢

标签: pythonpython-3.x

解决方案


以书面形式回答问题:

使用 的key函数lambda tup: [x for x in tup[2:0:-1] if not isinstance(x, str)]。不必费心进行两次排序,这会一次对两个值进行排序:

list3 = [('a', 3.30, 2.90, '' ), ('b', 3.20, '' , '')]
sort_list = sorted(list3 , key=lambda tup: [x for x in tup[2:0:-1] if not isinstance(x, str)])
print(sort_list)

输出:

[('a', 3.3, 2.9, ''), ('b', 3.2, '', '')]

以这里的函数为例key,它按顺序切出索引 2 和 1。当其中一个是 astr时,它会省略它,否则它将保留它作为密钥的一部分。所以('a', 3.3, 2.9, '')产生 的key[2.9, 3.3],而('b', 3.2, '', '')产生单独的key值。[3.2]

我会警告您,这会使维护您的代码的任何人感到困惑;在普通代码中,您无条件地将位置 n 与位置 n 进行比较,您不会遇到位置 n 不存在于一个元素中的情况,从而导致您将位置 n 与另一个元素中的位置 n-1 进行比较。

另请注意,Python 不允许您使用逗号作为小数点。如果所需的值是十分之三又十分之二,那么您想要的文字是3.20(或等价于3.2),而不是3,20等价于3,2);前者是预期的数值,后者是tuple两个ints 中的一个(3并且20作为不相关的值)。您可能认为3,20有效,但这只是因为您将小数部分填充为零,因此在比较tuples 时,它首先比较整数部分,然后是小数部分(由于被填充,比较正确)。如果你曾经比较3,33,20,你会得到不正确的排序,因为 while3.3大于3.20(后面的零无关紧要),3,3小于3,20(因为3s 相等,并且20大于3)。如果需要十进制精度,请使用decimal.Decimal类型,但如果这是玩具代码,请使用float; 使用 a tupleof two ints 通常比任何其他选项更容易出错。


推荐阅读