我正试图找出一种方法,只通过Pandas选择满足我的正则表达式的行。我的实际数据集data.csv有一列(标题没有标记)和数百万行。前四行看起来像:
5;4Z13H;;L
5;346;4567;;O
5;342;4563;;P
5;3LPH14;4567;;O
我写了以下正则表达式
([1-9][A-Z](.*?);|[A-Z][A-Z](.*?);|[A-Z][1-9](.*?);)
将识别第1行的4Z13H;
和第4行的3LPH14;
。基本上我希望pandas过滤我的数据并选择第1行和第4行。
所以我想要的输出是
5;4Z13H;;L
5;3LPH14;4567;;O
然后,我想将过滤器行的子集保存到新的csv,filteredData.csv中。到目前为止我只有这个:
import pandas as pd
import numpy as np
import sys
import re
sys.stdout=open("filteredData.csv","w")
def Process(filename, chunksize):
for chunk in pd.read_csv(filename, chunksize=chunksize):
df[0] = df[0].re.compile(r"([1-9][A-Z]|[A-Z][A-Z]|[A-Z][1-9])(.*?);")
sys.stdout.close()
if __name__ == "__main__":
Process('data.csv', 10 ** 4)
我仍然是python的新手,所以上面的代码有一些语法问题(我还在试图弄清楚如何使用pandas chunksize)。但是主要问题是通过正则表达式过滤行。我非常感谢任何人的建议
答案 0 :(得分:2)
一种方法是将csv作为pandas dataframe读取,然后使用str.contains创建一个掩码列
df['mask'] = df[0].str.contains('(\d+[A-Z]+\d+)') #0 is the column name
df = (df[df['mask'] == True]).drop('mask', axis = 1)
如果您愿意,您可以获得所需的数据帧,您可以使用df = df.reset_index()重置索引
0
0 5;4Z13H;;L
3 5;3LPH14;4567;;O
其次是首先阅读csv并创建仅包含已过滤行的编辑文件,然后读取已过滤的csv以创建数据帧
with open('filteredData.csv', 'r') as f_in:
with open('filteredData_edit.csv', 'w') as f_outfile:
f_out = csv.writer(f_outfile)
for line in f_in:
line = line.strip()
row = []
if bool(re.search("(\d+[A-Z]+\d+)", line)):
row.append(line)
f_out.writerow(row)
df = pd.read_csv('filteredData_edit.csv', header = None)
你得到了
0
0 5;4Z13H;;L
1 5;3LPH14;4567;;O
根据我的经验,我更喜欢第二种方法,因为在创建数据帧之前过滤掉不需要的行会更有效。