2012-04-20 7 views
0

ファイルのリストがあり、行ごとに1つずつ単語を検索しようとしています。 common_wordsファイルのサンプルは次のとおりです。Pythonでファイルを読み取っているときに無限ループが発生する

yourself 
yourselves 
z 
zero 

リストは辞書順にソートされています。

def isCommonWord(word): 

    commonWordList = open("common_words", 'r') 
    commonWord = commonWordList.readline() 
    commonWord = commonWord.rstrip("\n") 

    while commonWord <= word: 
     if commonWord == word: 
      return True 
     commonWord = commonWordList.readline() 
     commonWord = commonWord.rstrip("\n") 

    return False 

if isCommonWord("zeros"): 
    print "true" 
else: 
    print "false" 

この関数は無限ループに入っています。私はこれがどのように起こっているのか分かりません。どんな助けでも大歓迎です。 "ゼロ"以外の変数を試しても問題ないです。私は問題に直面している "ゼロ"だけで。ありがとうございました。あなたが探している単語が>のいずれかである場合ので、あなたのループ条件が常に真である、あなたは、ファイルの末尾を越えて読み取ろうとするとき

+0

あなたも、ファイルの終わりに達した後、 'readline'をやって続けているようです。 – jogojapan

+0

このfuctionで何を達成したいですか? –

+0

@AshwiniChaudhary私はファイルの中に単語のリストを持っており、特定の単語がファイル内の単語リストの中にあるかどうかを確認する必要があります。 –

答えて

1

"yourself"<="zeros"条件は真でループは無限に続きます。

したがって、その関数に任意の単語を渡している場合は、lexicographicallyが他の単語よりも大きい場合、プログラムは無限ループになります。例えば、 。 "zz"の場合 < = "zz"はzzlexicographicallyであるため、ファイルcommon_wordsのすべての他の単語よりも大きいので、無限ループに入ります。

isCommonword()の改良版は次のようになります。

def isCommonWord(word): 

    commonWordList = open("common_words.txt") 
    commonWord = [x.rstrip() for x in commonWordList] 
    if word in commonWord: 
     return True 
    else:return False 
+0

は単にcommonWord 代わりの 場合(真)に言葉を返す:返す真他 :私はちょうどに固執しようとしていた偽 –

+0

を返しますOPによって使用される形式。 –

+0

あなたのコードに何も問題はありません、私のコメントはそれほど冗長ではない(そしてもっと明確にする) –

2

readlineは空の文字列を返し、空の文字列は''任意の単語を比較しますファイル内の単語。

問題の真の解決策は、一度ファイルを読み込み、そこからsetを構築することですがこれは

def isCommonWord(word): 
    with open("common_words") as f: 
     for w in f: 
      w = w.rstrip() 
      if w == word: 
       return True 
      elif w > word: 
       break 

    return False 

としてループを書き換えることにより固定することができます。

common = set(ln.rstrip() for ln in open("common_words")) 
print("true" if "zeros" in common else "false") 
+0

しかし、関数は "ゼロ"の場合を除いてすべての場合にうまく機能します。リスト内の単語でもリスト内の単語でもない –

+0

@QuaziFarhan:これは '' zeros''が '>' 'ファイル内の単語を比較するためです。変更のために 'zzz'を試してください。無限ループに入るでしょう。 –

+0

最後のものの前に辞書編集的にリスト内にない単語に対して機能します。 – UmNyobe

1

おそらく、"zeros"はファイルcommon_words内のすべての単語の後ろにあるため、一致するものはありません。 (<fobj>.readline()で読んだ)commonWordは、入力ファイルのEOFを打つと空("")になり、空の文字列( "forever"が返されます)は "0"より小さくなり、ループ条件は決して終了しません。

変更するには、ループ条件:あなたは言葉が見つかり、ファイルの最後の単語の後lexographicallyですされていない場合、ループを終了する方法を追加していない

while commonWord and commonWord <= word: 
    ... 
0

。 「ゼロ」は、ファイルの終わりに達したときに自動的に終了し動作しますあなたのwhileループのかなり直接的な翻訳がforループ

for commonWord in commonWordList: 
    commonWord = commonWord.rstrip("\n") 
    if commonWord <= word: 
     break 
    elif commonWord == word: 
     return True 
return False 

ザ・かもしれないファイルである、ではなく「ゼロ」

+1

- 単語がファイルの中央にない場合、ループは終了します。 – katrielalex

3

zerosはの後にとなりますが、これはチェックしません。さらに、readline()は、ファイルの最後に達した場合は空の文字列を返します。したがって、ループは「まだ存在していない」と考え続け、永遠に続きます。

ちなみに、リストがソートされているという事実を利用して、これを行うより良い方法があります:バイナリ検索をご覧ください。

実際には、余分なメモリがある場合はそれよりも優れています。ファイル全体を大量のsetに読み込んでから、メンバーシップをチェックするのに一定の時間がかかります。

+0

リストはメモリ(理論的には)が非常に大きくなる可能性があるので、十分なメモリがあると常に仮定することはできませんが、バイナリ検索の何らかの方法を実装できると述べたのでもちろんです。私はそうするつもりです、ちょうどその初期段階です。 –

+0

十分に良い。 (また、大規模なセットを保持するためにshelve' 'のようなものを使用することができます。) – katrielalex

0

問題はご使用の状態である可能性がありますcommonWord <= word!=を使用して、readlineが何かを返すことを確認してください。単語がリストにある場合、ループを破るものがない場合はtrueを返します。

関連する問題