我有一个包含多个列的DataFrame。有3列包含空白行,或者如果行对应于列变量,则具有随机数字/字母字符串。我想获取这些数据并创建另一个列,其中包含一个字符串,其中包含每行的变量名称。
例如:
raw_data['A']
Out[192]:
0 00Q2400000GUxMjEAL
1 00Q2400000G5QDzEAN
2 NaN
3 NaN
4 NaN
5 NaN
到目前为止,我已尝试编写一个要应用的函数,但它只为每一行返回'xyz'。
def type(row):
if row['A'] is not None:
return 'xyz'
elif row['B'] is not None:
return 'acb'
else:
return 'efg'
raw_data['TUV'] = raw_data.apply(lambda row: type(row), axis = 1)
非常感谢任何帮助。
答案 0 :(得分:1)
使用pd.notnull:
def type(row):
if pd.notnull(row['A']):
return 'xyz'
elif pd.notnull(row['B']):
return 'acb'
else:
return 'efg'
df['TUV'] = df.apply(lambda row: type(row), axis = 1)
更好地编辑以使用pd.notnull
答案 1 :(得分:1)
使用更大的数据集时,apply
可能会很慢
即使只有10,000行,通过简单的索引操作,您也可以在此任务上获得 25x加速。
以下是一些示例数据:
N = 10000
data = {"A": np.random.choice([1, None], size=N),
"B": np.random.choice([1, None], size=N)}
df = pd.DataFrame(data)
df.head()
A B
0 1 1
1 None 1
2 1 1
3 1 1
4 None None
使用基本分配和索引:
%%timeit
df["TUV"] = "efg"
df.loc[df.A.notnull(), "TUV"] = "xyz"
df.loc[df.B.notnull(), "TUV"] = "acb"
# 6.15 ms ± 211 µs per loop (mean ± std. dev. of 7 runs, 100 loops each)
使用apply
:
%%timeit
def type(row):
if pd.notnull(row['A']):
return 'xyz'
elif pd.notnull(row['B']):
return 'acb'
else:
return 'efg'
df['TUV2'] = df.apply(lambda row: type(row), axis = 1)
# 152 ms ± 1.5 ms per loop (mean ± std. dev. of 7 runs, 10 loops each)
df.TUV.equals(df.TUV2) # True