2013-02-09 2 views
1

40k 행의 데이터가 포함 된 CSV 파일이 있습니다.파이썬에서 큰 csv 파일을 처리하는 방법은 무엇입니까?

내 각 기능은 csv 파일을 열고 함께 작동 한 다음 닫습니다. 파일을 한 번 열고 닫은 다음 원하는 때에 언제든지 사용할 수있는 방법이 있습니까? 나는 별도의 목록에 각 필드를 넣으려고했는데 사전이나 호출 할 때마다 부엉이로 작동하지만 두 프로세스 모두 1k 행까지 잘 작동합니다. 그 이상으로 처리하는 데 오랜 시간이 걸린다면 필터링 속도를 높일 수있는 방법을 찾았습니다. 그 (것)들을 적용하는 그러나 확실하지 않다.

내 코드 샘플.

files=open("myfile.csv","r") 


def spec_total(): 
    total = 0.0 
    files.readline() # skip first row 
    for line in files: 
     field=line.strip().split(",") #make Into fields 
     tall=float(field[0])  
      if tall >= 9.956: 
     total +=tall 
    print("The sum is: %0.5f" % (total)) 

spec_total() 
files.close() 

다른 기능

files=open("3124749c.csv","r") 
def code(): 
    match= 0 
    files.readline() # skip first row 
    for row in files: 
     field=row.strip().split(",") #make Into fields 
     code=(field[4]) 
     import re 
     if re.search(r'\[[A-Za-z][0-9]+\][0-9]+[A-Za-z]{2}[0-9]+#[0-9]+', code) is None: 
      match += 1 
    print("The answer that do not match code is :",match) 

code() 

files.close() 

과마다 CSV 파일을 열고 내가 언급하고있는 필드 인식하기 위해 필드로 분할 많은 더 많은 기능이 있습니다.

+2

"해야합니까?" 왜? "XY를 얻고 싶습니다. 지금까지 해보았습니다"라는 질문에 다시 말하면, 더 나은 행운을 얻게 될 것입니다. –

+0

표준 라이브러리''csv''를 사용하면' 'total (field [0])''이며 전역 데이터에 액세스하지 않습니다. – sotapme

+0

@Dragets : 당신이 성취하고자하는 것이 무엇인지는 분명하지 않습니다. 다시 말해 줄래? – pillmuncher

답변

1

내가하려고 제대로 이해한다면 :

import csv 
total = 0.0 
for row in csv.reader(open("myfile.csv")): 
    tall = float(row[0]) 
    if tall >= 9.956: 
     total += tall 

print("The sum is: %0.5f" % total) 

더 복잡한 버전 - 각 행을 처리하는 계산 클래스를 만들 수 있습니다. 너무 문자 그대로되지 않는 - 단지 설명을 목적으로 구문 등의

너무 베어 - 지루한 일이었다

class Calc(object): 
    def process(self,row): 
     pass 
    def value(self): 
     pass 

class SumColumn(Calc): 
    def __init__(self, column=0,tall=9.956): 
     self.column = column 
     self.total = 0 

    def process(self, row): 
     tall = float(row[0]) 
     if tall >= self.tall: 
      self.total += tall 

    def value(self): 
     return self.total 

class ColumnAdder(Calc): 
    def __init__(self, col1, col2): 
     self.total = 0 
     self.col1 = col1 
     self.col2 = col2 

    def process(self, row): 
     self.total += (row[self.col1] + row[self.col2]) 

    def value(self): 
     return self.total 

class ColumnMatcher(Calc): 
    def __init__(self, col=4): 
     self.matches = 0 

    def process(self, row): 
     code = row[4] 
    import re 
    if re.search(r'\[[A-Za-z][0-9]+\][0-9]+[A-Za-z]{2}[0-9]+#[0-9]+', code) is None: 
     self.match += 1 

    def value(self): 
     return self.matches 

import csv 
col0_sum = SumColumn() 
col3_sum = SumColumn(3, 2.45) 
col5_6_add = ColumnAdder(5,6) 
col4_matches = ColumnMatcher() 

for row in csv.reader(open("myfile.csv")): 
    col0_sum.process(row) 
    col3_sum.process(row) 
    col5_6_add.process(row) 
    col4_matches.process(row) 

print col0_sum.value() 
print col3_sum.value() 
print col5_6_add.value() 
print col4_matches.value() 

이 코드는 SO에 입력했다.

+0

이 코드를 사용하면 여전히 각 함수에 대해 csv 파일을 열고 분할 할 필요가 있습니다 ...이 직업을 담당하는 함수를 작성하고 어떻게 든 다른 모든 함수와 관련 짓고 있다고 생각했습니다. 다른 모든 함수는 관련되어 있기 때문입니다 csv 파일에있는 데이터. –

+0

나는 당신의 질문을 잘 모르겠다. 아마도 그것을 증명할 수있는 코드를 작성할 수있을 것이다. 만약''n'' 함수가 실제로 각 행의 컬럼을 기반으로 계산한다면, 각 계산에 대해 클래스를 생성하는 것이 가장 좋습니다. 내가 의미하는 바를 보여주기 위해 편집 할 것입니다. – sotapme

+0

더 구체적인 질문을 다시 작성하고 예제를 추가하십시오 –

0

모두가 Python의 객체입니다. 즉, 함수를 의미합니다.
우리가 정의한 모든 함수가 이미 '클래스의 인스턴스'라는 의미에서 객체이기 때문에 이러한 클래스의 인스턴스로 함수를 생성하기 위해 특수 클래스를 정의 할 필요가 없습니다. sotapme이 있습니다.

예를 들어 누군가가 같은 유형의 여러 함수를 만들어야하는 경우 (예 : 각각 정확한 CSV 파일 열의 모든 값을 추가하는 경우) 반복되는 프로세스로 이러한 많은 함수를 만드는 것이 좋습니다.
이 시점에서 질문 : 제기 함수 팩터 리 또는 클래스?

Personnaly는 덜 장황하기 때문에 공장 방식을 선호합니다.
Theran의 대답 HERE에서도 더 빠름을 발견했습니다.

다음 코드에서 globals()로 트릭을 사용하여 함수 팩터를 통해 생성 된 각 함수에 특정 이름을 지정합니다. 어떤 사람들은 그것이 나쁘다고 말하지만, 나는 왜 그런지 모른다. 같은 것을 할 수있는 또 다른 방법이 있다면, 나는 그것을 배우게되어 기쁠 것이다.

코드에서 3 개의 함수는 함수 팩터 리로 빌드되며 일반적인 일반 정의 (op3)로 정의됩니다.

파이썬이 환상적입니다!

import csv 
import re 

# To create a CSV file 
with open('Data.csv','wb') as csvhandle: 
    hw = csv.writer(csvhandle) 
    hw.writerows(((2,10,'%%',3000,'-statusOK-'), 
        (5,3,'##',500,'-modo OOOOKKK-'), 
        (1,60,'**',700,'-- anarada-'))) 
del hw 

# To visualize the content of the CSV file 
with open(r'Data.csv','rb') as f: 
    print "The CSV file at start :\n "+\ 
      '\n '.join(map(repr,csv.reader(f))) 


def run_funcs_on_CSVfile(FUNCS,CSV): 
    with open(CSV,'rb') as csvhandle: 
     for f in FUNCS: 
      # this is necessary for functions not created via 
      # via a function factory but via plain definition 
      # that defines only the attribute col of the function 
      if 'field' not in f.__dict__: 
       f.field = f.col - 1 
       # columns are numbered 1,2,3,4,... 
       # fields are numbered 0,1,2,3,... 
     for row in csv.reader(csvhandle): 
      for f in FUNCS: 
       f(row[f.field]) 

def SumColumn(name,col,start=0): 
    def g(s): 
     g.kept += int(s) 
    g.kept = start 
    g.field = col -1 
    g.func_name = name 
    globals()[name] = g 

def MultColumn(name,col,start=1): 
    def g(s): 
     g.kept *= int(s) 
    g.kept = start 
    g.field = col - 1 
    g.func_name = name 
    globals()[name] = g 

def ColumnMatcher(name,col,pat,start = 0): 
    RE = re.compile(pat) 
    def g(s,regx = RE): 
     if regx.search(s): 
      g.kept += 1 
    g.kept = start 
    g.field = col - 1 
    g.func_name = name 
    globals()[name] = g 

SumColumn('op1',1) 
MultColumn('op2',2) 
ColumnMatcher('op4',5,'O+K') 

def op3(s): 
    s = int(s) 
    if s%2: 
     op3.kept += (2*s) 
    else: 
     op3.kept += s 
op3.kept = 0 
op3.col = 4 


print '\nbefore:\n ' +\ 
     '\n '.join('%s.kept == %d' 
       % (f.func_name, f.kept) 
       for f in (op1,op2,op3,op4)) 

# The treatment is done here 
run_funcs_on_CSVfile((op2,op3,op4,op1),r'Data.csv') 
# note that the order of the functions in the tuple 
# passed as argument can be any either one or another 


print '\nafter:\n ' +\ 
     '\n '.join('%s(column %d) in %s.kept == %d' 
       % (f.func_name, f.field+1, f.func_name, f.kept) 
       for f in (op1,op2,op3,op4)) 

. 결과는 입니다.

The CSV file at start : 
    ['2', '10', '%%', '3000', '-statusOK-'] 
    ['5', '3', '##', '500', '-modo OOOOKKK-'] 
    ['1', '60', '**', '700', '-- anarada-'] 

before: 
    op1.kept == 0 
    op2.kept == 1 
    op3.kept == 0 
    op4.kept == 0 

after: 
    op1(column 1) in op1.kept == 8 
    op2(column 2) in op2.kept == 1800 
    op3(column 4) in op3.kept == 4200 
    op4(column 5) in op4.kept == 2 
관련 문제