如何比较数字子列表中的第一项,如果重复,比较第二项并选择第二项最小的子列表?

Posted

技术标签:

【中文标题】如何比较数字子列表中的第一项,如果重复,比较第二项并选择第二项最小的子列表?【英文标题】:How to compare first item in sublist of numbers, if repeated, compare the second item and pick the sublist with the smallest second item? 【发布时间】:2020-10-24 22:51:46 【问题描述】:

我有一个带有数字的列表(LIST_long),我需要编写一个列表(LIST_short),其中包含每个第一项(氨基酸的序列号)只有一个具有最小第二项(距离)的子列表:

LIST_long = [['1', '50.9'], ['1', '9.0'], ['1', '10.2'], ['1', '2.0'], ['2', '50.1'], ['2', '8.8'],...]

LIST_short = [['1', '2.0'], ['2', '8.8'],...]

我在 Python 3.6 中编写了这样的代码:

import itertools

LIST_long = [['1', '50.9'], ['1', '9.0'], ['1', '10.2'], ['1', '2.0'], ['2', '50.1'], ['2', '8.8'],...]
LIST_short = []
LIST_long = sorted(LIST_long, key=lambda x:(x[0], x[1]))

for x, y in itertools.groupby(LIST_long, lambda x: x[0]):
    LIST_short.append(list(y)[0])
print(LIST_short)

输出:

LIST_short = [['1', '10.2'], ['2', '50.1'],...]

而不是:

LIST_short = [['1', '2.0'], ['2', '8.8'], ...]

但是以这种方式附加['1', '10.2']而不是['1', '2.0'],因为据我了解,不是第二项的编号而是逐位比较,1在2之前; 5 之前 8 等等....

我将非常感谢有关此问题的帮助。 期待建议。

【问题讨论】:

【参考方案1】:

您可以使用字典来获取结果,将子列表的第一项存储为字典的键,并对应地添加第二项作为列表中的值,然后获取列表的最小值,您就得到了需要的结果。

LIST_long = [['1', '50.9'], ['1', '9.0'], ['1', '10.2'], ['1', '2.0'], ['2', '50.1'], ['2', '8.8']]

from collections import defaultdict as dd

x = dd(list)

for i in LIST_long:
    x[i[0]]+=[float(i[1])]

LIST_sort = []

for k, v in x.items():
    LIST_sort.append([k, str(min(v))])

print(LIST_sort)

输出

[['1', '2.0'], ['2', '8.8']]

【讨论】:

谢谢@sahasrara62 你的问题也很好解决【参考方案2】:

您的代码完美运行,您只需将x[1] 更改为float(x[1])

import itertools

LIST_long = [['1', '50.9'], ['1', '9.0'], ['1', '10.2'], ['1', '2.0'], ['2', '50.1'], ['2', '8.8'],...]
LIST_short = []
LIST_long = sorted(LIST_long, key=lambda x:(x[0], float(x[1])))    # <<-- here

for x, y in itertools.groupby(LIST_long, lambda x: x[0]):
    LIST_short.append(list(y)[0])
print(LIST_short)

结果:

>>> LIST_short
[['1', '2.0'], ['2', '8.8']]
>>> 

问题是,您将第二个元素作为字符串进行比较,而您应该将它们转换为 float 值进行比较。

【讨论】:

【参考方案3】:

以下应该这样做:

LIST_long = [['1', '50.9'], ['1', '9.0'], ['1', '10.2'], ['1', '2.0'], ['2', '50.1'], ['2', '8.8']]
LIST_short = dict()

for id, value in LIST_long:
    if id not in LIST_short or float(value) < float(LIST_short[id]):
        LIST_short[id] = value

LIST_short = [[x, y] for x, y in LIST_short.items()]

【讨论】:

你的代码输出:LIST_short -&gt;&gt; [['1', '10.2'], ['2', '50.1']],这是错误的。

以上是关于如何比较数字子列表中的第一项,如果重复,比较第二项并选择第二项最小的子列表?的主要内容,如果未能解决你的问题,请参考以下文章

Markdown快速学习效果展示页

js面试常考之数组冒泡排序

用数据框的行值替换子列表中的第二项

冒泡排序与快速排序数组越界?

第一次使用markdown

手写冒泡排序