合并两个具有布尔掩码的Python列表

2024-09-26 22:09:16 发布

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

我有一个简单的python列表和一个布尔掩码。首先,根据掩码将该列表分为两个列表,然后我想将这两个列表合并回原始列表,而不复制/清空这两个列表(这排除了使用.pop().copy())。简单到可以用pandas、np或冗长的代码实现。但是,我需要在列表中实现它;不可能有额外的库(像itertools这样的库就可以了)。你知道吗

问题:如何将两个列表用一个遮罩干净地组合在一起,没有混乱,没有np/pandas/etc?你知道吗

最小示例:

# some data
x = [1.0,2.0,3.0,4.0]
print('original list: {}'.format(x))
# a boolean mask
mask = [True,False,False,True]
print('boolean mask: {}'.format(mask))
# splitting based on the mask is easy enough
xt = [xx for (xx,m) in zip(x,mask) if m]
xf = [xx for (xx,m) in zip(x,mask) if not(m)]
print('true mask of x: {}'.format(xt))
print('false mask of x: {}'.format(xf))

# --output--
# original list: [1.0, 2.0, 3.0, 4.0]
# boolean mask: [True, False, False, True]
# true mask of x: [1.0, 4.0]
# false mask of x: [2.0, 3.0]

现在把它们结合起来;我要解决的问题。这里有三种方法有效,但不合格(第一种是笨重的,第二种使用np,第三种是清空xtxf):

# Method 1: desired performance, but long-winded
i=0
j=0
x_merge=[]
for m in mask:
    if m: 
        x_merge.append(xt[i])
        i += 1
    else:
        x_merge.append(xf[j])
        j += 1
print('merging back together (clunky): {}'.format(x_merge))

# Method 2: in numpy it's not hard either
import numpy as np
x_merge2 = np.zeros(len(xt)+len(xf))
x_merge2[mask]=xt
x_merge2[[not(m) for m in mask]]=xf
print('merging back together (np): {}'.format(x_merge2))

# Method 3: clean, but empties xt and xf, which I can't do; copy/pop also no good
x_merge3 = [xt.pop(0) if m else xf.pop(0) for m in mask]
print('merging back together (pop): {}'.format(x_merge3))

# --output--
# merging back together (clunky): [1.0, 2.0, 3.0, 4.0]
# merging back together (np): [1. 2. 3. 4.]
# merging back together (pop): [1.0, 2.0, 3.0, 4.0]

这感觉很简单,但如果没有copy/poppdnp或类似的东西(这是基于周围代码中的类型约束的真正需求;我不能将其转换回列表或类似的东西),这会有点棘手。有人能告诉我怎么做吗?你知道吗

编辑:我在发帖前搜索过了(没有运气),但答案是肯定的:Merge two or more lists with given order of merging。你知道吗


Tags: ofintrueformat列表fornpback
1条回答
网友
1楼 · 发布于 2024-09-26 22:09:16

方法3,但使用标准迭代器而不是弹出。你知道吗

xti, xfi= iter(xt), iter(xf)
merged = [next(xti) if m else next(xfi) for m in mask]

xti.next()将起作用,但仅适用于python2)

相关问题 更多 >

    热门问题