303

我在一个包含非常大字段的 csv 文件中读取了一个脚本:

# example from http://docs.python.org/3.3/library/csv.html?highlight=csv%20dictreader#examples
import csv
with open('some.csv', newline='') as f:
    reader = csv.reader(f)
    for row in reader:
        print(row)

但是,这会在某些 csv 文件上引发以下错误:

_csv.Error: field larger than field limit (131072)

如何分析具有大字段的 csv 文件?跳过具有大字段的行不是一种选择,因为需要在后续步骤中分析数据。

4

8 回答 8

423

csv 文件可能包含非常大的字段,因此增加field_size_limit

import sys
import csv

csv.field_size_limit(sys.maxsize)

sys.maxsize适用于 Python 2.x 和 3.x。sys.maxint仅适用于 Python 2.x ( SO: what-is-sys-maxint-in-python-3 )

更新

正如 Geoff 指出的那样,上面的代码可能会导致以下错误:OverflowError: Python int too large to convert to C long. 为了避免这种情况,您可以使用以下快速而肮脏的代码(它应该适用于每个使用 Python 2 和 Python 3 的系统):

import sys
import csv
maxInt = sys.maxsize

while True:
    # decrease the maxInt value by factor 10 
    # as long as the OverflowError occurs.

    try:
        csv.field_size_limit(maxInt)
        break
    except OverflowError:
        maxInt = int(maxInt/10)
于 2013-02-25T09:38:02.160 回答
172

这可能是因为您的 CSV 文件嵌入了单引号或双引号。如果您的 CSV 文件是制表符分隔的,请尝试将其打开为:

c = csv.reader(f, delimiter='\t', quoting=csv.QUOTE_NONE)
于 2013-08-23T17:52:10.650 回答
42

.csv字段大小通过[Python.Docs] 控制: csv.field_size_limit([new_limit])重点是我的):

返回解析器允许的当前最大字段大小。如果给出了new_limit,这将成为新的 limit

它默认设置为1310720x20000 ( 128k ),对于任何体面的.csv来说应该足够了:

>>> import csv
>>>
>>>
>>> limit0 = csv.field_size_limit()
>>> limit0
131072
>>> "0x{0:016X}".format(limit0)
'0x0000000000020000'

但是,当处理具有(至少)一个字段长于此大小的.csv文件(具有正确的引用和分隔符)时,会弹出错误。
为了消除错误,应该增加大小限制(为避免任何担忧,尝试最大可能值)。

在幕后(查看[GitHub]: python/cpython - (master) cpython/Modules/_csv.c了解实现细节),保存这个值的变量是一个C long ( [Wikipedia]: C data types ),它的大小取决于CPU架构和操作系统( I L P )。经典的区别:对于064 位 操作系统(和Python构建),类型大小(以位为单位)为:

  • 尼克斯64
  • 32

当尝试设置它时,新值被检查是否在边界内,这就是为什么在某些情况下会弹出另一个异常(因为sys.maxsize通常是064位宽 - 在Win上遇到):

>>> import sys, ctypes as ct
>>>
>>>
>>> "v{:d}.{:d}.{:d}".format(*sys.version_info[:3]), sys.platform, sys.maxsize, ct.sizeof(ct.c_void_p) * 8, ct.sizeof(ct.c_long) * 8
('v3.9.9', 'win32', 9223372036854775807, 64, 32)
>>>
>>> csv.field_size_limit(sys.maxsize)
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
OverflowError: Python int too large to convert to C long

为避免遇到此问题,请使用技巧设置(最大可能)限制( LONG_MAX)(感谢[Python.Docs]:ctypes - A foreign function library for Python)。它应该适用于Python 3Python 2,在任何CPU / OS上。

>>> csv.field_size_limit(int(ct.c_ulong(-1).value // 2))
131072
>>> limit1 = csv.field_size_limit()
>>> limit1
2147483647
>>> "0x{0:016X}".format(limit1)
'0x000000007FFFFFFF'

064 位 PythonNix之类的操作系统上:

>>> import sys, csv, ctypes as ct
>>>
>>>
>>> "v{:d}.{:d}.{:d}".format(*sys.version_info[:3]), sys.platform, sys.maxsize, ct.sizeof(ct.c_void_p) * 8, ct.sizeof(ct.c_long) * 8
('v3.8.10', 'linux', 9223372036854775807, 64, 64)
>>>
>>> csv.field_size_limit()
131072
>>>
>>> csv.field_size_limit(int(ct.c_ulong(-1).value // 2))
131072
>>> limit1 = csv.field_size_limit()
>>> limit1
9223372036854775807
>>> "0x{0:016X}".format(limit1)
'0x7FFFFFFFFFFFFFFF'

对于032 位 Python,事情应该运行顺利,没有技巧(因为sys.maxsizeLONG_MAX都是032位宽)。
如果这个最大值仍然不够,那么.csv将需要手动干预才能从Python处理。

查看以下资源以获取更多详细信息:

于 2019-02-04T13:31:55.473 回答
34

下面是检查电流限制

csv.field_size_limit()

出[20]:131072

下面是增加限制。将其添加到代码中

csv.field_size_limit(100000000)

尝试再次检查限制

csv.field_size_limit()

输出[22]:100000000

现在您不会收到错误“_csv.Error:字段大于字段限制 (131072)”

于 2018-03-20T14:28:37.893 回答
4

我刚刚在“普通”CSV 文件中遇到了这种情况。有些人可能会称其为无效的格式文件。没有转义字符,没有双引号,分隔符是分号。

此文件中的示例行如下所示:

第一个单元格;Second " 带有一个双引号和前导空格的单元格;'部分引用'单元格;最后一个单元格

第二个单元格中的单引号会使解析器偏离轨道。起作用的是:

csv.reader(inputfile, delimiter=';', doublequote='False', quotechar='', quoting=csv.QUOTE_NONE)
于 2019-03-12T14:16:56.620 回答
1

有时,一行包含双引号列。当 csv 阅读器尝试阅读此行时,不理解列的结尾并触发此提升。解决方案如下:

reader = csv.reader(cf, quoting=csv.QUOTE_MINIMAL)
于 2017-08-14T14:51:52.233 回答
-1

您可以使用read_csvfrompandas跳过这些行。

import pandas as pd

data_df = pd.read_csv('data.csv', error_bad_lines=False)
于 2019-10-10T11:03:40.510 回答
-2

找到通常放在 .cassandra 目录下的 cqlshrc 文件。

在该文件中追加,

[csv]
field_size_limit = 1000000000
于 2019-01-26T03:45:24.363 回答