Fon*_*nti 49 python csv pandas
我想读一个非常大的csv(不能在excel中打开并且很容易编辑)但是在第100,000行的某个地方,有一行有一个额外的列导致程序崩溃.这行是错误的,所以我需要一种方法来忽略它是一个额外的列的事实.有大约50列,所以硬编码标题和使用名称或usecols是不可取的.我也可能在其他csv中遇到这个问题,并且想要一个通用的解决方案.遗憾的是,我在read_csv中找不到任何内容.代码就像这样简单:
def loadCSV(filePath):
dataframe = pd.read_csv(filePath, index_col=False, encoding='iso-8859-1', nrows=1000)
datakeys = dataframe.keys();
return dataframe, datakeys
Run Code Online (Sandbox Code Playgroud)
EdC*_*ica 77
传递error_bad_lines=False跳过错误的行:
error_bad_lines:boolean,default具有太多字段的True Lines(例如,带有太多逗号的csv行)默认情况下会引发异常,并且不会返回任何DataFrame.如果为False,那么这些"坏行"将从返回的DataFrame中删除.(仅对C解析器有效)
小智 35
对于像我这样在原件发布之后几年才遇到的人来说,其他答案建议使用error_bad_lines=False和warn_bad_lines=True,但两者在 pandas 中都已被弃用。
相反,使用on_bad_lines = 'warn'可以达到相同的效果来跳过坏数据线。
dataframe = pd.read_csv(filePath, index_col=False, encoding='iso-8859-1', nrows=1000, on_bad_lines = 'warn')
Run Code Online (Sandbox Code Playgroud)
on_bad_lines = 'warn'当遇到坏行时会发出警告并跳过该行。
其他可接受的on_bad_lines值是
Luk*_*kas 18
要获取有关导致错误的行的信息,请尝试使用error_bad_lines=False和 的组合warn_bad_lines=True:
dataframe = pd.read_csv(filePath, index_col=False, encoding='iso-8859-1', nrows=1000,
warn_bad_lines=True, error_bad_lines=False)
Run Code Online (Sandbox Code Playgroud)
error_bad_lines=False跳过导致错误的行并warn_bad_lines=True打印错误详细信息和行号,如下所示:
'Skipping line 3: expected 4 fields, saw 3401\nSkipping line 4: expected 4 fields, saw 30...'
Run Code Online (Sandbox Code Playgroud)
如果您想保存警告消息(即进行一些进一步处理),那么您也可以将其保存到文件中(使用contextlib):
import contextlib
with open(r'D:\Temp\log.txt', 'w') as log:
with contextlib.redirect_stderr(log):
dataframe = pd.read_csv(filePath, index_col=False, encoding='iso-8859-1',
warn_bad_lines=True, error_bad_lines=False)
Run Code Online (Sandbox Code Playgroud)
sit*_*uck 17
首先pandas 1.4.0,read_csv()提供了允许您通过允许分配可调用对象以更加优雅和智能的方式处理这些情况的功能on_bad_lines=。
例如,假设CSV可能导致错误数据错误Expected 4 fields in line 3, saw 5::
C1,C2,C3,C4
10,11,12,13
25,26,27,28,garbage
80,81,82,83
Run Code Online (Sandbox Code Playgroud)
以下 lambda 函数只是忽略错误行中的最后一列(如上面原始问题陈述中所期望的那样):
df = pd.read_csv('your.csv', on_bad_lines=lambda x: x[:-1], engine='python')
df
C1 C2 C3 C4
0 10 11 12 13
1 25 26 27 28
2 80 81 82 83
Run Code Online (Sandbox Code Playgroud)
可调用函数on_bad_lines在每个坏行上调用,并具有函数签名(bad_line: list[str]) -> list[str] | None。如果函数返回None,则坏行将被忽略。如您所见,engine='python'这是必需的。
这样做的好处在于,它为您想要编写任何细粒度逻辑来解决问题打开了大门。
例如,假设您想从行的开头或结尾删除错误数据,并且如果开头和结尾都有错误数据,则只需忽略该行即可:
C1,C2,C3,C4
10,11,12,13
20,21,22,23,garbage
60,61,62,63
trash,80,81,82,83
trash,90,91,82,garbage
Run Code Online (Sandbox Code Playgroud)
def line_fixer(x):
if not x[0].isnumeric() and x[-1].isnumeric():
return x[1:]
if not x[-1].isnumeric() and x[0].isnumeric():
return x[:-1]
return None
Run Code Online (Sandbox Code Playgroud)
df = pd.read_csv('your.csv', on_bad_lines=line_fixer, engine='python')
df
C1 C2 C3 C4
0 10 11 12 13
1 20 21 22 23
2 60 61 62 63
3 80 81 82 83
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
37872 次 |
| 最近记录: |