Python "while"ループ(不定反復)

Python "while"ループ(不定反復)

Iterationは、同じコードブロックを何度も、場合によっては何度も実行することを意味します。 反復を実装するプログラミング構造は、loopと呼ばれます。

プログラミングには、不定と確定の2種類の反復があります。

  • indefinite iterationでは、ループが実行される回数は事前に明示的に指定されていません。 むしろ、特定の条件が満たされる限り、指定されたブロックが繰り返し実行されます。

  • definite iterationでは、指定されたブロックが実行される回数は、ループの開始時に明示的に指定されます。

このチュートリアルでは、次のことを行います。

  • 不定反復に使用されるPython制御構造であるwhileループについて学習します

  • ループから抜け出す方法またはループの繰り返しを時期尚早に確認する

  • 無限ループを探索する

終了したら、Pythonで無限反復を使用する方法を十分に理解する必要があります。

Free Bonus:Click here to get our free Python Cheat Sheetは、データ型、辞書、リスト、Python関数の操作など、Python3の基本を示しています。

__ Take the Quiz:インタラクティブな「Python「while」ループ」クイズで知識をテストします。 完了すると、学習の進捗状況を経時的に追跡できるようにスコアを受け取ります。

whileループ

Pythonのwhileステートメントを使用してループを構築する方法を見てみましょう。 シンプルに始めて、装飾を加えていきます。

基本的なwhileループのフォーマットを以下に示します。

while :
    

<statement(s)>は、繰り返し実行されるブロックを表します。これは、ループの本体と呼ばれることがよくあります。 これは、ifステートメントの場合と同様に、インデントで示されます。

Remember: Pythonのすべての制御構造は、インデントを使用してブロックを定義します。 確認するには、前のチュートリアルのgrouping statementsに関する説明を参照してください。

制御式<expr>には通常、ループを開始する前に初期化され、ループ本体のどこかで変更される1つ以上の変数が含まれます。

whileループが検出されると、<expr>は最初にBoolean contextで評価されます。 真の場合、ループ本体が実行されます。 次に、<expr>が再度チェックされ、それでもtrueの場合、本体が再度実行されます。 これは、<expr>がfalseになるまで続きます。falseになると、プログラムの実行はループ本体を超えて最初のステートメントに進みます。

このループを考えてみましょう:

>>>

 1 >>> n = 5
 2 >>> while n > 0:
 3 ...     n -= 1
 4 ...     print(n)
 5 ...
 6 4
 7 3
 8 2
 9 1
10 0

この例で何が起こっているのかを次に示します。

  • nは最初は5です。 2行目のwhileステートメントヘッダーの式はn > 0であり、これはtrueであるため、ループ本体が実行されます。 3行目のループ本体の内部で、n1から4にデクリメントされてから、出力されます。

  • ループの本体が終了すると、プログラムの実行はループの先頭の2行目に戻り、式が再度評価されます。 それはまだ真なので、本文が再度実行され、3が出力されます。

  • これは、n0になるまで続きます。 その時点で、式がテストされるとき、それは偽であり、ループは終了します。 ループ本体に続く最初のステートメントから実行が再開されますが、この場合は実行されません。

whileループの制御式は、他の何かが起こる前に最初にテストされることに注意してください。 最初がfalseの場合、ループ本体はまったく実行されません。

>>>

>>> n = 0
>>> while n > 0:
...     n -= 1
...     print(n)
...

上記の例では、ループが発生すると、n0になります。 制御式n > 0はすでにfalseであるため、ループ本体は実行されません。

数値比較ではなく、リストを含む別のwhileループを次に示します。

>>>

>>> a = ['foo', 'bar', 'baz']
>>> while a:
...     print(a.pop(-1))
...
baz
bar
foo

list is evaluated in Boolean contextの場合、要素が含まれている場合は真実であり、空の場合は偽です。 この例では、aは、要素が含まれている限りtrueです。 .pop()メソッドですべての項目が削除され、リストが空になると、aはfalseになり、ループは終了します。

Pythonのbreakおよびcontinueステートメント

これまで見てきた各例では、whileループの本体全体が各反復で実行されます。 Pythonは、ループの反復を途中で終了させる2つのキーワードを提供します。

  • Pythonのbreakステートメントは、ループを即座に完全に終了します。 プログラムの実行は、ループ本体に続く最初のステートメントに進みます。

  • Pythoncontinueステートメントは、現在のループの反復を即座に終了します。 実行はループの先頭にジャンプし、制御式が再評価されて、ループが再度実行されるか終了するかが決定されます。

breakcontinueの違いは、次の図に示されています。

breakステートメントを示すbreak.pyというスクリプトファイルを次に示します。

 1 n = 5
 2 while n > 0:
 3     n -= 1
 4     if n == 2:
 5         break
 6     print(n)
 7 print('Loop ended.')

コマンドラインインタープリターからbreak.pyを実行すると、次の出力が生成されます。

C:\Users\john\Documents>python break.py
4
3
Loop ended.

n2になると、breakステートメントが実行されます。 ループは完全に終了し、プログラムの実行は7行目のprint()ステートメントにジャンプします。

次のスクリプトcontinue.pyは、breakの代わりにcontinueステートメントを除いて同じです。

 1 n = 5
 2 while n > 0:
 3     n -= 1
 4     if n == 2:
 5         continue
 6     print(n)
 7 print('Loop ended.')

continue.pyの出力は次のようになります。

C:\Users\john\Documents>python continue.py
4
3
1
0
Loop ended.

今回は、n2の場合、continueステートメントによってその反復が終了します。 したがって、2は出力されません。 実行はループの先頭に戻り、条件が再評価され、それでも真です。 ループが再開され、以前と同様に、n0になると終了します。

else

Pythonでは、whileループの最後にオプションのelse句を使用できます。 これはPythonのユニークな機能であり、他のほとんどのプログラミング言語には見られません。 構文は次のとおりです。

while :
    
else:
    

else句で指定された<additional_statement(s)>は、whileループが終了したときに実行されます。

thought balloon

今頃、あなたは「それはどのように役立つのか」と考えているかもしれません。 elseを使用せずに、whileループの直後にこれらのステートメントを配置することで、同じことを実現できます。

while :
    

違いは何ですか?

後者の場合、else句がないと、whileループが終了した後、何があっても<additional_statement(s)>が実行されます。

<additional_statement(s)>else句に配置されると、ループが「枯渇によって」終了した場合、つまり、制御条件がfalseになるまでループが繰り返された場合にのみ実行されます。 ループがbreakステートメントによって終了した場合、else句は実行されません。

次の例を見てください。

>>>

>>> n = 5
>>> while n > 0:
...     n -= 1
...     print(n)
... else:
...     print('Loop done.')
...
4
3
2
1
0
Loop done.

この場合、条件がなくなるまでループが繰り返されました。n0になったため、n > 0はfalseになりました。 ループはその自然な生活を生き延びたので、いわばelse句が実行されました。 ここで違いを観察します。

>>>

>>> n = 5
>>> while n > 0:
...     n -= 1
...     print(n)
...     if n == 2:
...         break
... else:
...     print('Loop done.')
...
4
3
2

このループはbreakで途中で終了するため、else句は実行されません。

elseという単語の意味は、ifステートメントと同様に、whileループに完全には適合していないように見える場合があります。 Pythonの作成者であるGuido van Rossumは、実際に、もう一度やり直す必要がある場合は、whileループのelse句を言語から除外すると述べています。

次の解釈のいずれかが、より直感的になるのに役立ちます。

  • ループのヘッダー(while n > 0)は、何度も実行されるifステートメント(if n > 0)と考えてください。条件が満たされると、最終的にelse句が実行されます。 falseになります。

  • breakがなかった場合、後続のブロックが実行されるという点で、elsenobreakであるかのように考えてください。

これらの解釈のいずれかが役に立たない場合は、お気軽に無視してください。

whileループのelse句が役立つのはいつですか? 1つの一般的な状況は、特定のアイテムのリストを検索している場合です。 アイテムが見つかった場合はbreakを使用してループを終了でき、else句には、アイテムが見つからなかった場合に実行されることを意図したコードを含めることができます。

>>>

>>> a = ['foo', 'bar', 'baz', 'qux']
>>> s = 'corge'

>>> i = 0
>>> while i < len(a):
...     if a[i] == s:
...         # Processing for item found
...         break
...     i += 1
... else:
...     # Processing for item not found
...     print(s, 'not found in list.')
...
corge not found in list.

Note:上記のコードは概念を説明するのに役立ちますが、実際にはそのようにリストを検索することはほとんどありません。

まず、リストは通常​​、whileループではなく、明確な反復で処理されます。 明確な反復については、このシリーズの次のチュートリアルで説明します。

第二に、Pythonはリスト内のアイテムを検索する組み込みの方法を提供します。 in演算子を使用できます。

>>>

>>> if s in a:
...     print(s, 'found in list.')
... else:
...     print(s, 'not found in list.')
...
corge not found in list.

list.index()メソッドも機能します。 このメソッドは、アイテムがリストに見つからない場合にValueError例外を発生させるため、それを使用するには例外処理を理解する必要があります。 Pythonでは、tryステートメントを使用して例外を処理します。 例を以下に示します。

>>>

>>> try:
...     print(a.index('corge'))
... except ValueError:
...     print(s, 'not found in list.')
...
corge not found in list.

このシリーズの後半で、例外処理について学習します。

whileループを持つelse句は少し奇妙で、あまり見られません。 ただし、コードがわかりやすくなると感じる場合は、遠慮しないでください。

無限ループ

理論的には決して終わらないwhileループを作成するとします。 奇妙に聞こえますか?

この例を考えてください。

>>>

>>> while True:
...     print('foo')
...
foo
foo
foo
  .
  .
  .
foo
foo
foo
KeyboardInterrupt
Traceback (most recent call last):
  File "", line 2, in 
    print('foo')

このコードは[.keys]#Ctrl [.kbd .key-c] #C ##で終了し、キーボードから割り込みが生成されます。 そうでなければ、果てしなく続くでしょう。 多くの `+ foo`出力行が削除され、示されている出力の縦の省略記号に置き換えられています。

明らかに、Trueが偽になることはありません。そうしないと、私たち全員が非常に大きな問題に直面します。 したがって、while True:は、理論的には永久に実行される無限ループを開始します。

たぶんそれはあなたがやりたいことのように聞こえないかもしれませんが、このパターンは実際には非常に一般的です。 たとえば、サービスリクエストを受け入れて起動し、永久に実行するサービスのコードを作成できます。 この文脈における「永遠」とは、あなたがそれをシャットダウンするまで、または宇宙の熱死までのいずれか早い方を意味します。

もっと端的に言えば、ループはbreakステートメントで分割できることを覚えておいてください。 先頭で評価された条件ではなく、ループ本体内で認識された条件に基づいてループを終了する方が簡単な場合があります。

上記のループの別のバリエーションで、リストが空になるまで.pop()を使用してリストからアイテムを連続的に削除します。

>>>

>>> a = ['foo', 'bar', 'baz']
>>> while True:
...     if not a:
...         break
...     print(a.pop(-1))
...
baz
bar
foo

aが空になると、not aがtrueになり、breakステートメントがループを終了します。

ループ内で複数のbreakステートメントを指定することもできます。

while True:
    if :  # One condition for loop termination
        break
    ...
    if :  # Another termination condition
        break
    ...
    if :  # Yet another
        break

このような場合、ループを終了する理由が複数ある場合は、ループヘッダーですべての終了条件を指定するよりも、いくつかの異なる場所からbreakを出力する方が適切な場合がよくあります。

無限ループは非常に便利です。 ある時点でループが確実に中断されるようにしなければならないので、本当に無限にならないようにしてください。

ネストされたwhileループ

一般に、Pythonの制御構造は相互にネストできます。 たとえば、if /elif /else条件ステートメントはネストできます。

if age < 18:
    if gender == 'M':
        print('son')
    else:
        print('daughter')
elif age >= 18 and age < 65:
    if gender == 'M':
        print('father')
    else:
        print('mother')
else:
    if gender == 'M':
        print('grandfather')
    else:
        print('grandmother')

同様に、whileループは、次に示すように、別のwhileループ内に含めることができます。

>>>

>>> a = ['foo', 'bar']
>>> while len(a):
...     print(a.pop(0))
...     b = ['baz', 'qux']
...     while len(b):
...         print('>', b.pop(0))
...
foo
> baz
> qux
bar
> baz
> qux

ネストされたループ内にあるbreakまたはcontinueステートメントは、最も近い囲んでいるループに適用されます。

while :
    statement
    statement

    while :
        statement
        statement
        break  # Applies to while : loop

    break  # Applies to while : loop

さらに、whileループはif /elif /elseステートメント内にネストできます。その逆も可能です。

if :
    statement
    while :
        statement
        statement
else:
    while :
        statement
        statement
    statement
while :
    if :
        statement
    elif :
        statement
    else:
        statement

    if :
        statement

実際、すべてのPython制御構造は、必要な範囲で相互に混在させることができます。 それはそうあるべきです。 「whileループをifステートメントに含めることはできません」や「whileループは相互にネストできるのはほとんどの4つの深さ。」それらすべてを覚えるのは非常に難しいでしょう。

一見任意の数値的または論理的な制限は、不十分なプログラム言語設計の兆候と見なされます。 幸いなことに、Pythonには多くはありません。

1行のwhileループ

ifステートメントと同様に、whileループを1行で指定できます。 ループ本体を構成するブロックに複数のステートメントがある場合、それらはセミコロン(;)で区切ることができます。

>>>

>>> n = 5
>>> while n > 0: n -= 1; print(n)

4
3
2
1
0

ただし、これは単純なステートメントでのみ機能します。 2つの複合ステートメントを1行に結合することはできません。 したがって、上記のようにwhileループをすべて1行で指定し、ifステートメントを1行で記述できます。

>>>

>>> if True: print('foo')

foo

しかし、これはできません。

>>>

>>> while n > 0: n -= 1; if True: print('foo')
SyntaxError: invalid syntax

PEP 8は、1行に複数のステートメントを含めることを推奨しないことに注意してください。 したがって、おそらくこれを頻繁に行うべきではありません。

結論

このチュートリアルでは、Pythonのwhileループを使用してindefinite iterationについて学習しました。 次のことができるようになりました。

  • 基本および複雑なwhileループを構築します

  • breakおよびcontinueによる割り込みループの実行

  • whileループでelse句を使用する

  • 無限ループに対処する

これで、コードの一部を繰り返し実行する方法を十分に把握できるはずです。

__ Take the Quiz:インタラクティブな「Python「while」ループ」クイズで知識をテストします。 完了すると、学習の進捗状況を経時的に追跡できるようにスコアを受け取ります。

このシリーズの次のチュートリアルでは、definite iterationforループ、つまり繰り返し回数が明示的に指定されている反復実行について説明します。