Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/python/329.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Python 使用列表理解根据使用其他列表的条件替换重复项_Python_List Comprehension - Fatal编程技术网

Python 使用列表理解根据使用其他列表的条件替换重复项

Python 使用列表理解根据使用其他列表的条件替换重复项,python,list-comprehension,Python,List Comprehension,用一个例子来说明可能更容易 A = [1, 1, 1, 1, 2, 2, 2, 2, 3, 3, 3, 3] B = [0.1, 0.2, 0.3, 0.4, 0.01, 0.02, 0.03, 0.04, 0.001, 0.001, 0.0003, 0.0003] 我有上面的两张清单 A中的每个元素都会重复几次。每个元素的多重性可以不同(并且它们不必像这里那样排序) B包含与A相同数量的元素。我想将A中每个重复元素中的最小元素分配给列表C(其中最小值来自B列表中的相应值。因此,对于前4个元素

用一个例子来说明可能更容易

A = [1, 1, 1, 1, 2, 2, 2, 2, 3, 3, 3, 3]
B = [0.1, 0.2, 0.3, 0.4, 0.01, 0.02, 0.03, 0.04, 0.001, 0.001, 0.0003, 0.0003]
我有上面的两张清单

A中的每个元素都会重复几次。每个元素的多重性可以不同(并且它们不必像这里那样排序)

B包含与A相同数量的元素。我想将A中每个重复元素中的最小元素分配给列表C(其中最小值来自B列表中的相应值。因此,对于前4个元素,它将是0.1,对于接下来的4个元素,它在本例中是0.01,对于最后4个元素,它是0.0003的重复值,并且对于每个重复元素都是如此)

我想获得以下列表

C = [0.1, 0.1, 0.1, 0.1, 0.01, 0.01, 0.01, 0.01, 0.0003, 0.0003, 0.0003, 0.0003]
由于我正在使用的代码已经广泛使用列表理解,所以我希望使用相同的方法

这可能吗

这样做明智吗

我熟悉一些简单的情况,比如

C = A[B < 0.0005]

但是,对于如何在此处继续操作,您还没有明确的想法。

您可以使用以下方法:

>>> A = [1, 1, 1, 1, 2, 2, 2, 2, 3, 3, 3, 3]
>>> B = [0.1, 0.2, 0.3, 0.4, 0.01, 0.02, 0.03, 0.04, 0.001, 0.001, 0.0003, 0.0003]
>>> AB = zip(A, B)
>>> AB_sorted = sorted(AB, key=lambda i: (i[0], -i[1]))
>>> AB_dict = dict(AB_sorted)
>>> C = [AB_dict[i] for i in A]
>>> C
[0.1, 0.1, 0.1, 0.1, 0.01, 0.01, 0.01, 0.01, 0.0003, 0.0003, 0.0003, 0.0003]

这是因为当您将
元组的
列表
转换为
dict
时,重复的键会被最后一个键覆盖。

如果您想要一行,这是有效的,假设我的注释是正确的解释:

[min([B[j] for j in [ind for ind,x in enumerate(A) if x==y]]) for y in A]
要分解它,最里面的列表理解将遍历
A
中的索引和值,然后下一个列表理解将再次遍历
A
中的所有值(将它们存储在
y
),并用作前面提到的列表的条件。
然后使用此索引列表获取
B
(使用
j
)中的所有元素,最后获取该列表中的
min


enumerate将索引和值分别返回到
ind
x

如果您不介意使用名为
Pandas
的附加Python库,可以执行以下操作:

import pandas as pd
A = [1, 1, 1, 1, 2, 2, 2, 2, 3, 3, 3, 3]
B = [0.1, 0.2, 0.3, 0.4, 0.01, 0.02, 0.03, 0.04, 0.001, 0.001, 0.0003, 0.0003]
df = pd.DataFrame([A, B]).T.rename(columns={0: 'A', 1: 'B'})
req_dict = {key: value for key, value in df.groupby('A')['B'].min().iteritems()}
print(df['A'].replace(req_dict))
输出:

[0.1, 0.1, 0.1, 0.1, 0.01, 0.01, 0.01, 0.01, 0.0003, 0.0003, 0.0003, 0.0003]

是的,一行就可以了

[min(y for x, y in zip(A, B) if z == x) for z in A]
这将生成此列表

[0.1, 0.1, 0.1, 0.1, 0.01, 0.01, 0.01, 0.01, 0.0003, 0.0003, 0.0003, 0.0003]

当你说最小的元素时,你是指最低的索引吗?如果是,我建议你根据最小的值来编辑这个问题。因此,对于前4个元素,它将是
0.1
,对于接下来的4个元素,在本例中它是
0.01
,对于最后4个元素,它是
0.0003
的重复值,你的意思是如果重复项在索引x、y、z、w(在
A
中)中,因此您需要
min(B[[x、y、z、w]])
?工作起来很有魅力。列表理解令人惊讶……非常感谢!我还有其他一些类似的条件需要解决,但我认为这会帮助我自己解决。是的,有时需要很多测试,但如果你一步一步地做,打印出结果列表,并增加复杂性,我发现这会让它更易于管理确实如此。目前,我设法访问了每个最小值的索引。
C=[B.index(min([B[j]表示j in[ind for ind,x in enumerate(A)if x==y]]))表示y in A]
这不是OP所寻找的列表。
[0.1, 0.1, 0.1, 0.1, 0.01, 0.01, 0.01, 0.01, 0.0003, 0.0003, 0.0003, 0.0003]