Hata: alan sınırından büyük alan (131072)


232

Çok büyük alanları olan bir csv dosyasında bir komut dosyası okuma var:

# 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)

Ancak, bu bazı csv dosyalarına aşağıdaki hatayı atar:

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

Büyük alanlara sahip csv dosyalarını nasıl analiz edebilirim? Verilerin sonraki adımlarda analiz edilmesi gerektiğinden, satırları büyük alanlarla atlamak bir seçenek değildir.


10
Daha da iyisi, verilerinizde neden bu kadar büyük alanlar olduğunu düşünmek olabilir ? Bazen bu gibi hatalar farklı bir sorunun göstergesi olabilir. Bende rastgele bir çift tırnak karakteri içeren ve bu yüzden burada başka bir cevapta gösterilen QUOTE_NONE seçeneğini kullanmak zorunda bazı kötü veriler vardı.
dustmachine

1
Benim durumumda büyük alanlar olabileceğini belirtmek için sorumu güncelledim. Csv dosyasında hatalı veri yok.
user1251007

1
@dustmachine Böyle şeyler olur çünkü bazen veritabanı tablolarında görüntüleri (veya diğer ikili dosyaları) base64 formatında saklayan insanlar bulursunuz.
wintermute

Yanıtlar:


315

Csv dosyası çok büyük alanlar içerebilir, bu nedenle field_size_limit:

import sys
import csv

csv.field_size_limit(sys.maxsize)

sys.maxsizePython 2.x ve 3.x için çalışır. sys.maxintyalnızca Python 2.x ile çalışır ( SO: python-3-sys-maxint-in-nedir )

Güncelleme

Geoff belirttiği gibi, yukarıdaki kod aşağıdaki hatayı neden olabilir: OverflowError: Python int too large to convert to C long. Bunu atlatmak için, aşağıdaki hızlı ve kirli kodu kullanabilirsiniz (Python 2 ve Python 3 ile her sistemde çalışmalıdır):

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)

14
Python 2.6, Windows 7 64 bit üzerinde maxInt = sys.maxsizegetiri 9223372036854775807Ldolayısıyla bir sonuçlanır TypeError: limit must be an integerçağrılırken csv.field_size_limit(maxInt). İlginçtir, kullanmak maxInt = int(sys.maxsize)bunu değiştirmez. Kaba bir çözüm, csv.field_size_limit(2147483647)diğer platformlarda sorunlara neden olan basit bir kullanımdır . Benim durumumda bu, CSV'deki kırık değeri tanımlamak, diğer uygulamadaki dışa aktarma seçeneklerini düzeltmek ve ihtiyacını kaldırmak için gerekliydi csv.field_size_limit().
roskakori

Bunun için çok teşekkür ederim, bu hatayı yıllardır anlamaya çalışıyorum!
Kevin Hernandez

152

Bunun nedeni, CSV dosyanızda tek veya çift tırnak işareti bulunması olabilir. CSV dosyanız sekmeyle ayrılmışsa dosyayı şu şekilde açmayı deneyin:

c = csv.reader(f, delimiter='\t', quoting=csv.QUOTE_NONE)

1
Teşekkür ederim!! Csvkit (mükemmel bir python kitaplığı ve komut satırı csv araç kiti) kullanıyorsanız ve dosyanızda dengesiz tek veya çift tırnak kullanıldığı için orijinal hatayı alıyorsanız, -u 3komut satırı seçeneği olan QUOTE_NONE'u seçebilirsiniz--quoting 3
nealmcb

22

Akım sınırını kontrol etmek için aşağıda

csv.field_size_limit()

Çıkış [20]: 131072

Aşağıda limiti artırmak için. Koda ekleyin

csv.field_size_limit(100000000)

Sınırı tekrar kontrol etmeyi deneyin

csv.field_size_limit()

Çıkış [22]: 100000000

Artık "_csv.Error: alan, alan sınırından (131072) daha büyük" hatasını almayacaksınız


15

csv alan boyutları [Python 3.Docs]: csv. field_size_limit ( [new_limit] ) :

Ayrıştırıcı tarafından izin verilen geçerli maksimum alan boyutunu döndürür. Eğer NEW_LIMIT verilir, bu yeni sınır haline gelir.

Varsayılan olarak , uygun herhangi bir .csv için yeterli olması gereken 128k veya 0x20000 ( 131072 ) olarak ayarlanmıştır :

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

Ancak, bu boyuttan (en az) bir alan daha uzun olan bir .csv dosyasıyla ( doğru alıntı ve sınırlayıcıyla ) uğraşırken hata açılır.
Hatadan kurtulmak için boyut sınırı arttırılmalıdır (endişeleri önlemek için mümkün olan maksimum değer denenir).

Perde arkasında ( uygulama ayrıntıları için [GitHub]: python / cpython - (master) cpython / Modules / _csv.c'yi kontrol edin), bu değeri tutan değişken C uzunluğundadır ( [Wikipedia]: C veri türleri ). CPU mimarisine ve işletim sistemine ( I L P ) bağlı olarak değişir . Klasik fark: 64 bit işletim sistemi ( Python derlemesi) için uzun tip boyutu ( bit cinsinden):

  • Nix : 64
  • Galibiyet : 32

Ayarlamak çalışırken, yeni değer olması kontrol edilir uzun Başka bir istisna açılan bazı durumlarda (bu durumda yaygındır yüzden, sınırları Win ):

>>> import sys
>>>
>>> sys.platform, sys.maxsize
('win32', 9223372036854775807)
>>>
>>> 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

Bu sorunla karşılaşmamak için bir yapay nesne kullanarak (mümkün olan maksimum) sınırı ( LONG_MAX ) ayarlayın ( [Python 3.Docs] sayesinde : ctypes - Python için bir yabancı işlev kitaplığı ). Herhangi bir CPU / OS'de Python 3 ve Python 2 üzerinde çalışmalıdır .

>>> import ctypes as ct
>>>
>>> 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'

64bit Python bir on Nix gibi OS :

>>> import sys, csv, ctypes as ct
>>>
>>> sys.platform, sys.maxsize
('linux', 9223372036854775807)
>>>
>>> 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'

İçin 32 bit Python işler tekdüze değildir: bu karşılaştığımız davranış var Win .

Aşağıdakiler hakkında daha fazla bilgi için aşağıdaki kaynakları kontrol edin:


2

Bu sadece 'düz' bir CSV dosyasında başıma geldi. Bazı kişiler dosyaya geçersiz biçimlendirilmiş dosya diyebilir. Hiçbir kaçış karakteri, çift tırnak ve sınırlayıcı noktalı virgül oldu.

Bu dosyadaki örnek bir satır şöyle görünecektir:

İlk hücre; İkinci "bir çift tırnak ve önde gelen boşluk ile hücre; 'Kısmen alıntı' hücre; Son hücre

ikinci hücredeki tek alıntı, ayrıştırıcıyı raylarından atacaktır. Ne işe yaradı:

csv.reader(inputfile, delimiter=';', doublequote='False', quotechar='', quoting=csv.QUOTE_NONE)

1

Bazen, bir satır çift tırnak kolonu içerir. Csv okuyucu bu satırı okumaya çalıştığında, sütun sonu anlaşılmadı ve bu zam ateş. Çözüm aşağıdadır:

reader = csv.reader(cf, quoting=csv.QUOTE_MINIMAL)

0

Sen kullanabilirsiniz read_csvgelen pandasbu satırları atlamak için.

import pandas as pd

data_df = pd.read_csv('data.csv', error_bad_lines=False)

Kötü bir satır yok ... soruda yazıldığı gibi: csv dosyaları çok büyük alanlar içeriyor ve bu verilerin analiz edilmesi gerekiyor.
user1251007

1
Bozuk çizgiler kavramı pandas, alan sınırını aşan satırları içerir csv. Dolayısıyla, bu satırları atlamak ve diğer satırları başarıyla okumak istiyorsanız, bu çözümü kullanabilirsiniz. Aksi takdirde, sizin için büyük alanlar gerektiğinde, alan sınırını artırmak csv.field_size_limit(100000000)uygundur.
0x01h

-1

Genellikle .cassandra dizinine yerleştirilmiş cqlshrc dosyasını bulun.

Bu dosya ekinde,

[csv]
field_size_limit = 1000000000
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.