我有以下数据框
col1 col2
0 str9 val1
1 str8 val2
2 str4 val3
3 str2 val4
4 unknown1 asdvstr1df
5 random1 teststr2test
以及以下列表
strings = ['str1', 'str2', 'str3', 'str4']
如果第二列中字符串中任何一点与给定列表字符串匹配,我想替换第1列中的值。
注意:col2可以在字符串中包含列表'string'的值,也可以在任一端。
目前我正在使用一个丑陋且缓慢的嵌套循环:
import pandas as pd
data_file = pd.DataFrame(data = ([['str9', 'val1'], ['str8', 'val2'], ['str4','val3'] , ['str2', 'val4'] , ['unknown', 'asdvstr1df'] , ['unknown', 'teststr2test']] ), columns = (['col1', 'col2']), dtype = str)
strings = ['str1', 'str2', 'str3', 'str4']
for value in range(data_file.shape[0]):
for text in strings:
if (str(data_file.col2[value]).find(text) != -1):
data_file.loc[value, 'col1'] = text
我不确定如何改进这个缓慢的过程。如何让这个运行速度比当前的O(nm)时间快(n是data_file的大小,m是名为字符串的列表的大小)?
输出应为:
col1 col2
0 str9 val1
1 str8 val2
2 str4 val3
3 str2 val4
4 str1 asdvstr1df
5 str2 teststr2test
答案 0 :(得分:5)
IIUC,
x = '(' + '|'.join(strings)+ ')'
df.assign(col1 = df.col2.str.extract(x, expand=False).combine_first(df.col1))
输出:
col1 col2
0 str9 val1
1 str8 val2
2 str4 val3
3 str2 val4
4 str1 asdvstr1df
5 str2 teststr2test
答案 1 :(得分:3)
您可以replace
regex
d1=dict(zip(strings,[1,2,3,4]))
d2=dict(zip([1,2,3,4],strings))
df.loc[df.col1=='unknown','col1']=df.col2.replace(d1,regex=True).replace(d2)
df
Out[970]:
col1 col2
0 str9 val1
1 str8 val2
2 str4 val3
3 str2 val4
4 str1 asdvstr1df
5 str2 teststr2test
答案 2 :(得分:1)
试试这个:
data_file["col1"] = data_file["col2"].apply(lambda y:strings[[True if x in y
else False for x in strings ].index(True)] if any([True if x in y else False
for x in strings ]) else y)
print(data_file)
输出:
col1 col2
0 val1 val1
1 val2 val2
2 val3 val3
3 val4 val4
4 str1 asdvstr1df
5 str2 teststr2test