2012-02-29 78 views
0

對於下面的工作代碼,我訴諸創建一個類實例來存儲我的文件輸出[a_string]的名稱變量和文件對象本身[f_object]。我發現在第一個if語句中分配的變量沒有出現在以下elif語句內的作用域中。變量賦值在裏面,然後如果循環

#Text file splitter, data bewteen the '*' lines are copied into new files. 

class Output_file(): 
    def __init__(self,a_string='none',f_object='none'): 
     self.name=a_string 
     self.foutput=f_object 

outputfile=Output_file() 

n=0 
filehandle=open('original file.txt') 
for line in filehandle: 

    if line[0]=='*': #find the '*' that splits the rows of data 
     n+=1 
     outputfile.name = 'original file_'+str(n)+'.txt' 
     outputfile.foutput= open(outputfile.name,'w') 
     outputfile.foutput.write(line) 

    elif len(line.split()) ==5 and n > 0: #make sure the bulk data occurs in blocks of 5 
     outputfile.foutput= open(outputfile.name,'a+') 
     outputfile.foutput.write(line) 


outputfile.foutput.close() 

我是否必須使用類實例來存儲文件名和對象,還是有更好的方法嗎?

+0

你怎麼知道他們不會攜帶到,如果我想模仿你的風格,我想這樣的代碼它接下來的elif聲明? – 2012-02-29 18:40:12

回答

3

ifelif語句中定義的變量應該出現在另一箇中。例如:

>>> for i in range(5): 
... if i%2==0: 
... x = i 
... print(x) 
... else: 
... print(x) 
... 
0 
0 
2 
2 
4 

這不會是塊作用域語言的情況下,但不幸的是Python是不是塊範圍的,因此這應該工作。

但請注意,要使用它,您的name=必須在嘗試使用之前執行。也就是說,您的if語句必須在您的elif語句前至少執行一次。

您的代碼沒有意見,但我相信你的數據看起來有點像:

This is a header 
blah blah blah 
************** 
16 624 24 57 32 
352 73 47 76 3 
25 6 78 80 21 331 
************** 
234 234 4 64 7 
************** 
************** 
86 57 2 5 14 
4 8 3 634 7 

而想將它們分割成單獨的文件,但只有當它是「有效」的數據。

def isSeparatorLine(line): 
    return line[0] = '*' 
def isValidLine(line): 
    return len(line.split())==5 

groupNum = 0 
outputFile = None 
with open('original file.txt') as original: 
    for line in original: 
     if isSeparatorLine(line): 
      groupNum += 1 
      outputFilename = 'original file_{}.txt'.format(groupNum) 
      if outputFile: 
       outputFile.close() 
      outputFile = open(outputFilename, 'w') 
      outputFile.write('New file with group {}'.format(groupNum)) 
     elif group>0 and isValidLine(line): 
      outputFile.write(line) 

我不過個人更喜歡把它寫像這樣:

from itertools import * 

FILENAME = 'original file.txt' 
FILENAME_TEMPLATE = 'stanza-{}.txt' 

def isSeparatorLine(line): 
    return all(c=='*' for c in line) 
def isValidLine(line): 
    return len(line.split())==5 
def extractStanzas(text): 
    """ 
     Yields: [stanza0:line0,line1,...], [stanza1:lineN,lineN+1,...], [stanza2:...] 
     where each stanza is separated by a separator line, as defined above 
    """ 
    for isSeparator,stanza in groupby(text.splitlines(), isSeparatorLine): 
     if not isSeparator: 
      yield stanza 

with open(FILENAME) as f: 
    stanzas = list(extractStanzas(f.read())) 

for i,stanza in enumerate(stanzas[1:]): 
    assert all(isValidLine(line) for line in stanza), 'invalid line somewhere: {}'.format(stanza) 
    with open(FILENAME_TEMPLATE.format(i), 'w') as output: 
     output.write('\n'.join(stanza)) 
+0

「for循環的每次迭代都會重置內部分配的所有變量。」這不是真的。除非你明確地重新初始化變量,否則它將保持它的值,直到它超出範圍(即過程或模塊結束)。如果這不是真的,你不可能像循環內迭代一個值。 – Allan 2012-02-29 18:10:54

+0

謝謝艾倫,我沒有清楚地思考,忘記python是不是塊範圍。我的錯。再次感謝。 – ninjagecko 2012-02-29 18:41:24

+0

啊,這就是它: – Naaaysmith 2012-02-29 20:09:00