.csv 字段大小通过 [Python 3.Docs]: csv.field_size_limit([new_limit]) 控制(强调是我的):
返回解析器允许的当前最大字段大小。 如果给出 new_limit,这将成为新的限制。
默认设置为 131072 或 0x20000 (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 架构和 OS (ILP) 而异。经典的区别:对于 64bit OS(和 Python 构建),long 类型大小(以位为单位)为:
当试图设置它时,新值被检查为在 long 边界内,这就是为什么在某些情况下会弹出另一个异常(因为 sys.maxsize 是通常 64 位 宽 - 在 Win 上遇到):
>>> import sys, ctypes as ct
>>>
>>>
>>> sys.platform, sys.maxsize, ct.sizeof(ct.c_void_p) * 8, ct.sizeof(ct.c_long) * 8
('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),使用技巧(感谢 @987654324 @)。它应该可以在任何 CPU / OS 上的 Python 3 和 Python 2 上运行。
>>> 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'
64 位 Python 在像 OS 这样的 Nix 上:
>>> import sys, csv, ctypes as ct
>>>
>>>
>>> sys.platform, sys.maxsize, ct.sizeof(ct.c_void_p) * 8, ct.sizeof(ct.c_long) * 8
('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'
对于 32 位 Python,无需任何技巧(如 sys.maxsize 和 LONG_MAX 32 位 宽)。
如果这个最大值仍然不够,那么 .csv 需要人工干预才能从 Python 进行处理。
查看以下资源了解更多详情: