从其他lis访问列表值

2024-06-25 22:47:40 发布

您现在位置:Python中文网/ 问答频道 /正文

假设目前我有一个列表:

L = [[1,'JAYCE'],[2,'AMIE'],[3,'JACK'],[4,'STEVE'],[5,'JAYCE']]

我还有一个列表,其中包含按顺序排列的姓名:

sortedNames = ['AMIE','JACK','JAYCE','JAYCE','STEVE']

我想要得到的输出是,基于排序的名称列表,我想要按照排序的顺序(基于sortedNames列表)将ID添加回名称。你知道吗

finalist = [[2,'AMIE'],[3,'JACK'],[1,'JAYCE'],[5,'JAYCE'],[4,'STEVE']]

注意,Jayce出现了两次,所以即使第一次出现的Jayce有5个,然后是1,它也完全好。你知道吗

我一直在想:

L = [[1,'JAYCE'],[2,'AMIE'],[3,'JACK'],[4,'STEVE'],[5,'JAYCE']]
sortedNames = ['AMIE','JACK','JAYCE','JAYCE','STEVE']

finalist = []
for i in sortedNames:
    j = 0
    if i in L[j][1]:
        finalist.append(L[0] + i)
    j+=1

print(finalist)

我得到一个错误,说:

TypeError: can only concatenate list (not "str") to list

我肯定是加错了。你知道吗


Tags: in名称id列表排序顺序liststeve
3条回答

可以使用sorted()函数执行此操作,并使用其key参数查找存储名称的位置:

finalList = sorted(L, key=lambda x: sortedNames.index(x[1]))

结果是:

[[2, 'AMIE'], [3, 'JACK'], [1, 'JAYCE'], [5, 'JAYCE'], [4, 'STEVE']]

因此,只要您的数据表现良好,就可以使用defaultdict将数字分组为DEQUE:

In [14]: from collections import defaultdict, deque

In [15]: grouper = defaultdict(deque)

In [16]: for a,b in L:
    ...:     grouper[b].append(a)
    ...:

然后简单地说:

In [17]: grouper
Out[17]:
defaultdict(collections.deque,
            {'AMIE': deque([2]),
             'JACK': deque([3]),
             'JAYCE': deque([1, 5]),
             'STEVE': deque([4])})

In [18]: [[grouper[x].popleft(), x] for x in sortedNames]
Out[18]: [[2, 'AMIE'], [3, 'JACK'], [1, 'JAYCE'], [5, 'JAYCE'], [4, 'STEVE']]

我意识到在列表中使用pop是一个丑陋的缺点。。。你知道吗

这里有一种只使用dictlist的方法:

In [19]: grouper = {}
    ...: for a,b in L:
    ...:     grouper.setdefault(b, []).append(a)
    ...:

In [20]: grouper = {k:v[::-1] for k, v in grouper.items()}

In [21]: [[grouper[x].pop(), x] for x in sortedNames]
Out[21]: [[2, 'AMIE'], [3, 'JACK'], [1, 'JAYCE'], [5, 'JAYCE'], [4, 'STEVE']]

两种方法都是O(N)。你知道吗

编辑

我刚刚意识到,您真正想要的不是生成排序名称列表,而是直接使用键对L排序:
In [26]: L
Out[26]: [[1, 'JAYCE'], [2, 'AMIE'], [3, 'JACK'], [4, 'STEVE'], [5, 'JAYCE']]

In [27]: from operator import itemgetter

In [28]: sorted(L, key=itemgetter(1))
Out[28]: [[2, 'AMIE'], [3, 'JACK'], [1, 'JAYCE'], [5, 'JAYCE'], [4, 'STEVE']]

您可以通过将每个名称分组到为该名称找到的所有id的列表来创建字典。然后,可以应用next。你知道吗

import itertools
L = [[1,'JAYCE'],[2,'AMIE'],[3,'JACK'],[4,'STEVE'],[5,'JAYCE']]
new_l = {a:iter([c for c, _ in b]) for a, b in itertools.groupby(sorted(L, key=lambda x:x[-1]), key=lambda x:x[-1])}
sortedNames = ['AMIE','JACK','JAYCE','JAYCE','STEVE']
final_data = [[next(new_l[i]), i] for i in sortedNames]

输出:

[[2, 'AMIE'], [3, 'JACK'], [1, 'JAYCE'], [5, 'JAYCE'], [4, 'STEVE']]

编辑:

也可以利用sorted

L = [[1,'JAYCE'],[2,'AMIE'],[3,'JACK'],[4,'STEVE'],[5,'JAYCE']]
sortedNames = ['AMIE','JACK','JAYCE','JAYCE','STEVE']
new_result = sorted(L, key=lambda x:(sortedNames.index(x[-1]), x[0]))

输出:

[[2, 'AMIE'], [3, 'JACK'], [1, 'JAYCE'], [5, 'JAYCE'], [4, 'STEVE']]

相关问题 更多 >