2016-11-15 4 views
0

プログラムがディレクトリを経由し、各ファイルを順番に開き、特定の行を何かの前にチェックするタスクを実行しようとしています。その行が特定の基準を満たしている(つまり、ディレクトリ内の他のファイルでこの行と一致しない)場合、ファイルは閉じられ、プログラムは次のファイルに移動します。Python - ファイルが条件を満たす場合にファイルを閉じる

については
aps = [] 

import os 
for filename in os.listdir("C:\..."): 
    f = open(filename,"r") 
    (f.readline()) 
    (f.readline()) 
    ap = (f.readline()) 
    ap = ap.rstrip("\n") 
    aps.append(ap) 
    freqs = {} 
    for ap in aps: 
     freqs[ap] = freqs.get(ap, 0) + 1 
    for k, v in freqs.items(): 
     if v == 2: 
      f.close() 
     else: 

「他:」、私はもともと「(0)f.seek」を試してみましたが、閉じられたファイルで作業することができないというのPythonのエラーを得ました。私は 'f = open(filename、 "r")'をもう一度試しましたが、この方法で最初の行を印刷しようとすると奇妙なことが起こります。

このタスクについては、これが最善の方法ですか?そうでなければ、どうすればそれを動かすことができますか?

多くのありがとうございます。

+0

'f.close'の後の' else'ブランチの目的は何ですか?それでもファイルから読み込む必要はありますか? – sal

+0

ファイルを閉じた後に 'break'を追加して、ループを維持しないようにしてください。 –

答えて

2

条件付きでファイルを閉じないでください。開いているファイルで何をする必要があるのか​​を行い、最後に閉じます。 with構造を使用すると、ファイルは自動的に閉じられます。

for filename in os.listdir(path): 
    with open(filename) as f: 
     # do processing here 
     if positive_condition: 
      # do more processing 
1

コードが失敗する理由は次のとおりです。外側のforループの外側にあるapsのリストを初期化すると、ループするすべてのファイルの指定された行が含まれます。その後、開いたファイルごとにfreqs辞書が空にリセットされます。

したがって、これらの行:これまでに読み込まれた各ラインの上に

for ap in aps: 
    freqs[ap] = freqs.get(ap, 0) + 1 

がループ、および周波数をカウントします。問題は、forループの内側に来る:ここに何が起こる

for k, v in freqs.items(): 
    if v == 2: 
     f.close() 

freqsあなたがこれまでに掛け渡されたファイルの数など、潜在的に大きなキーのセットを持っているということです、そしてあなたは、各キーをループされています。最初にキーの値が2になると、現在のファイルは閉じられます。しかしループが続くので、次回のキーの値が2になると、pythonはファイルを閉じようとしますが、すでに閉じられています。

最も簡単な修正はf.close()の後にbreakを追加することです。しかし、このコードを構造化するより良い方法があります。

他の理由がない限り、常にwithコマンドを使用してファイルを開きます。従って:

with open(filename,"r") as f: 
    #code 

こうすれば、ファイルは自動的に終了します。

ファイルをループしている順番は重要ではなく、今まで開いていたものだけでなく、すべてのファイルを含めるように周波数テストを行うことを前提としています。その場合、周波数ディクテーションを組み立てるために2回、周波数要件を満たすファイルに何をしたいのかを2回繰り返す方が簡単です。

aps = [] 
freqs = {} 
# First loop to read the important line from all files 
for filename in os.listdir("C:\..."): 
    with open(filename,"r") as f: 
     f.readline() 
     f.readline() 
     ap = f.readline().rstrip("\n") 
     aps.append(ap) 
# Populate the dictionary 
for ap in aps: 
    freqs[ap] = freqs.get(ap, 0) + 1 
# Second loop to handle the important cases 
for filename in os.listdir("C:\..."): 
    with open(filename,"r") as f: 
     f.readline() 
     f.readline() 
     ap = f.readline().rstrip("\n") 
     if freqs[ap] != 2: 
      #do whatever 

私はそこに到達するより効率的でピジョンの方法が強く疑わしいですが、これは私の最高の考えです。

関連する問題