我们有一个使用场景,需要通过删除重复项来联接一行中的所有列值。数据存储在Pandas的DataFrame中。
例如,考虑以下具有列A、B、C的DataFrame df:
我想添加一个新的列,将A、B和C连接起来,并按照顺序去除重复项。输出的结果应如下所示:
请注意,列数是动态的。目前我正在使用以下命令进行操作:
A B C
X1 AX X1
X2 X2 X1
X3 X3 X3
X4 XX XX
我想添加一个新的列,将A、B和C连接起来,并按照顺序去除重复项。输出的结果应如下所示:
A B C Newcol
X1 AX X1 X1_AX
X2 X2 X1 X2_X1
X3 X3 X3 X3
X4 XX XX X4_XX
请注意,列数是动态的。目前我正在使用以下命令进行操作:
df.apply(lambda x: '-'.join(x.dropna().astype(str).drop_duplicates()),axis=1)
但是这个方法非常慢,对于我的数据需要大约150秒的时间。 但是由于数据框通常只有2列的情况占90%,因此我在代码中加入了一个if语句,并对只有2列的情况运行以下命令:
t1=pd.Series(np.where(df.iloc[:,0].dropna().astype(str) != df.iloc[:,1].dropna().astype(str), df.iloc[:,0].dropna().astype(str)+"-"+df.iloc[:,1].dropna().astype(str),df.iloc[:,1].dropna().astype(str)))
需要花费约55.3毫秒的时间
甚至可以
t1=df.iloc[:,0].dropna().astype(str).where(df.iloc[:,0].dropna().astype(str) == df.iloc[:,1].dropna().astype(str), df.iloc[:,0].dropna().astype(str)+"-"+df.iloc[:,1].dropna().astype(str))
两个操作的时间几乎相同(55毫秒对比150秒),但问题在于它仅适用于2列。我想创建一个通用语句,以便它可以处理n个列。我尝试使用reduce,但当我尝试使用3列时出现错误。
reduce((lambda x,y:pd.Series(np.where(df.iloc[:,x].dropna().astype(str) != df.iloc[:,y].dropna().astype(str), df.iloc[:,x].dropna().astype(str)+"-"+df.iloc[:,y].dropna().astype(str),df.iloc[:,y].dropna().astype(str)))),list(range(df.shape[1])))
类型错误:'str'和'int'的实例之间不支持'>='
请注意,df实际上是一个多核并行任务的一部分。因此,如果建议不包括并行性,那将是很好的。