我想在一个名为'new_col'的新列中分配一个csv,就像其他列的值的字符串一样。
目前,我的工作如下:
df['new_col'] = (df['a'].map(str) + ',' + df['b'].map(str))
这工作得很好,但我希望它能够自治。我想向函数提供一个列列表,然后让它执行字符串。
我当然可以如下遍历列表:
lstColumns = ['a','b']
lstItems = []
for item in lstColumns:
lstItems.append(df[item])
szChain = (',').join(lstItems)
但这很丑陋,我可能会在具有更多列的数据帧上使用它。
那么有什么方法可以简化吗?
答案 0 :(得分:0)
您可以使用以下内容:
df['new_col'] = df[df.columns].apply(
lambda x: ','.join(x.dropna().astype(str)),
axis=1
)
答案 1 :(得分:0)
向数据框逐行(轴= 1)应用功能。 该函数映射到字符串并以“,”
连接cols = ["a", "b"]
df.apply(lambda x: ", ".join(map(str, x[cols])), axis=1)
答案 2 :(得分:0)
您可以使用@Anshul Jindal提出的版本,但是还有另一种选择,它的输出差异很大,如果数据中有nan
,则可能会有用。
import io
df = pd.DataFrame({'a': ['a', 'b', np.nan],
'b': [np.nan, 'e', 'f'],
'c': ['g', 'h', 'i'],
'd': ['j', np.nan, 'l']})
cols = ['a', 'b' ,'d']
# another approach, using temporary text buffer
with io.StringIO() as output:
df[cols].to_csv(output, sep=',', index=False, header=False)
output.seek(0)
df = df.assign(new_col=output.readlines())
df.new_col = df.new_col.str.strip()
# approach proposed earlier
df = df.assign(new_col_2 = df[cols].apply(
lambda x: ','.join(x.dropna().astype(str)),
axis=1
))
print(df)
a b c d new_col new_col_2
0 a NaN g j a,,j a,j
1 b e h NaN b,e, b,e
2 NaN f i l ,f,l f,l
加上非常令人惊讶的方法时机:
import io
import timeit
df = pd.DataFrame({'a': ['a', 'b', np.nan],
'b': [np.nan, 'e', 'f'],
'c': ['g', 'h', 'i'],
'd': ['j', np.nan, 'l']})
cols = ['a', 'b' ,'d']
def buffer_approach(df, cols_to_merge):
with io.StringIO() as output:
df[cols_to_merge].to_csv(output, sep=',', index=False, header=False)
output.seek(0)
df = df.assign(new_col=output.readlines())
df.new_col = df.new_col.str.strip()
return df
def pandas_approach(df, cols_to_merge):
df = df.assign(new_col = df[cols_to_merge].apply(
lambda x: ','.join(x.dropna().astype(str)),
axis=1
))
return df
print(timeit.repeat("buffer_approach(df, cols)", globals=globals(), repeat=5, number=1000))
print(timeit.repeat("pandas_approach(df, cols)", globals=globals(), repeat=5, number=1000))
[2.5745794447138906, 2.556944037321955, 2.5482078031636775, 2.2512022089213133, 2.0038619451224804]
[3.6452969149686396, 3.326099018100649, 3.5136850751005113, 3.9479835461825132, 3.4149401267059147]
答案 3 :(得分:-1)
也许我不能正确理解您的问题,但是如果您有很多专栏,可以这样做:
cols_a = ['a1', 'a2', 'a3']
cols_b = ['b1', 'b2', 'b3']
cols_res = ['res1', 'res2', 'res3']
df = pd.DataFrame({i:[i, i] for i in (cols_a+cols_b+ cols_res)})
print(df)
a1 a2 a3 b1 b2 b3 res1 res2 res3
0 a1 a2 a3 b1 b2 b3 res1 res2 res3
1 a1 a2 a3 b1 b2 b3 res1 res2 res3
df[cols_res] = (df[cols_a].astype(str).values + ',' + df[cols_b].astype(str).values)
print(df)
a1 a2 a3 b1 b2 b3 res1 res2 res3
0 a1 a2 a3 b1 b2 b3 a1,b1 a2,b2 a3,b3
1 a1 a2 a3 b1 b2 b3 a1,b1 a2,b2 a3,b3