2012-02-29 82 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