Python基礎講座 #12 制御文の概念と演算子
英語ではcontrol flowと呼ばれる制御文は、プログラムの実行順序を変更したり、条件によって実行すべき命令文を制御するために使われる文です。Pythonで使われる制御文は大きく分けて選択制御文と反復 制御文に分けられ、選択制御文にはif条件文があり、if条件文を補助するelif文とelse文があります。普通、他のプログラミング言語ではelse ifキーワードを使いますが、Pythonでは2つの単語を縮めて elifキーワードを使うという点をぜひ覚えておいてください。また別の制御文として反復制御文であるfor文とwhile文があり、この反復制御文を補助するcontinueとbreakの補助制御文があります。Pythonは 他のプログラミング言語が提供するswitch選択文とdo while反復文は提供しません。しかしswitch文はif文で、do while文はwhile文で十分に代替が可能です。
ここから、ごくシンプルな冷蔵庫プログラムを作りながら、制御文がプログラムの中でどのように使われるかを見ていきましょう。これから作るプログラムの機能は、冷蔵庫の電源が入っている間、1分に1回ずつ冷蔵庫の中の温度を 測定し、温度がしきい値である最高温度を超えたら、最高温度より2度低い温度に調整することです。
実際のコーディングを始める前に、擬似コードを作成しておくのが良いでしょう。
擬似コード (pseudocode) とは、プログラムを設計する段階で、プログラミング言語ではなく日本語や英語などの人間の言語を使って、自分が作ろうとしているプログラムの構造やアルゴリズムを表現することを 言います。簡単に例を挙げると、絵を描く前に鉛筆で下絵を描くのに似ていると考えていただければと思います。擬似コードは、実際のコーディングをする前に、プログラミング言語を知らない人や他の人に自分の考えを分かりやすく伝えるのを 助けてくれ、全体的な構造やアルゴリズムに問題がないか把握するのに重要な役割を果たします。
最もシンプルな擬似コードはこのように書かれるでしょう。
while 冷蔵庫が点いている間
do 1分に1回ずつ温度をチェックし
if 温度が最高温度を超えたら
do 温度を最高温度より2度低く調整する。もう少し具体的な擬似コードを作成すると、こういうコードが完成します。
while 冷蔵庫 == ON :
do 温度チェック
if 現在温度 >= 最高温度:
print '温度を調整します。'
do 現在温度 = 最高温度 - 2
else:
print '温度は正常です。'
do 1分間待機コードを見ながら制御文の機能を見ていきましょう。
ここでwhile反復文は、冷蔵庫の電源が入っている状態であれば、繰り返し下のコードブロックが実行されるよう命令します。if条件文は、現在温度と最高温度を比較し、現在温度が最高温度より同じか高ければ下のコード ブロックを実行し、そうでなければelseキーワードの下のコードブロックを実行させます。
次は、先ほどの擬似コードをフローチャートで表現したものです。
フローチャートは、プログラムの全体プロセスを可視化し、簡単に理解・分析できるよう助けてくれます。擬似コードと同じく、while反復文の実行ブロックと、if、else条件文が実行されるブロックがあるのが分かります。
擬似コードを作成し、フローチャートを描くことは、コーディングを始める前にプログラムを設計する段階でとても重要かつ基本的な部分ですので、しっかり身に着けてください。
先ほど作成した擬似コードをPythonコードに移すと、次のようなプログラムが完成します。
import time
current_temp_list = [5, 3, 4, 6, 5, 4]
is_refrigerator_on = True
max_temp = 5
interval_in_second = 2
current_temp = 0
while is_refrigerator_on:
if len(current_temp_list):
current_temp = current_temp_list.pop(0)
else:
print('プログラムを終了します。')
break
if current_temp >= max_temp:
print('現在の温度は{}度で、{}度に調整します。'.format(current_temp, max_temp - 2))
current_temp = max_temp - 2
else:
print('現在の温度は{}度で、正常です。'.format(current_temp))
time.sleep(interval_in_second)サンプルプログラムなので、温度をチェックする間隔を1分から2秒に調整し、現在温度はあらかじめリストとして定義しておきました。あらかじめ定めておいた現在温度リストの長さが0になるとプログラムが終了するようにしています。
コードを実行すると、次のような結果が出力されます。
現在の温度は5度で、3度に調整します。
現在の温度は3度で、正常です。
現在の温度は4度で、正常です。
現在の温度は6度で、3度に調整します。
現在の温度は5度で、3度に調整します。
現在の温度は4度で、正常です。
プログラムを終了します。私たちが作った冷蔵庫プログラムが、2秒ごとに現在温度を確認し、常に最高温度である5度より低い温度を正常に維持していることを確認しました。もちろん、実際のプログラムを作るときは、決まったリストから温度を入力されるの ではなく、温度計から温度データを受け取って動作し、はるかに複雑なプログラムが作られるでしょう。しかし、とても複雑なプログラムも結局はこのような小さなプログラムが集まって作られるという点をぜひ覚えておいてください。
制御文を使うためには、演算子というものを理解する必要があります。英語ではoperatorと呼ばれる演算子は、変数に値を代入したり、算数の四則演算を行ったり、2つ以上の値を比較するために使われます。演算子の 種類には、算術演算子、代入演算子、比較演算子、論理演算子などがあります。
各演算子を1つずつ見ていきましょう。
1つ目に、算術演算子 (Arithmetic Operators) を見ていきます。算術演算子とは、算数の四則演算のような数値の演算をするときに使われます。足し算、引き算、掛け算、割り算は一般的な算数の四則演算と 同じです。
算術演算子 (Arithmetic Operators)
| 演算子 | 演算 | 使用例 |
|---|---|---|
| + | 足し算 | x + y |
| - | 引き算 | x - y |
| * | 掛け算 | x * y |
| / | 割り算 | x / y |
| % | 剰余 | x % y |
シンプルな算術演算子を実行してみましょう。
>>> a = 5
>>> b = 10
>>> a + b # 足し算
15
>>> b - a # 引き算
5
>>> a * b # 掛け算
50
>>> b / a # 割り算
2.0パーセント (%) キーワードを使う演算子は、2つの値を割った余りの値を返す演算子です。
>>> 10 % 3
1演算子の優先順位は、算数の計算をするときと同じく、掛け算、割り算が先に計算され、足し算、引き算は後に計算されます。足し算と引き算を先に計算したいときは括弧を使ってください。
>>> 1 + 1 * 2 # 掛け算、足し算の順で計算
3
>>> (1 + 1) * 2 # 足し算、掛け算の順で計算
4💡 今日のヒント
数学では0で他の数を割ると0になりますが、プログラムでは0で割ることはできません。0で他の数を割ると、ゼロ除算エラーが発生します。
実際に0で数を割ってエラーを発生させてみましょう。
>>> 10 / 0
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
ZeroDivisionError: division by zeroプログラムを作っていると、割る数がどんな数になるか分からない場合が多くあります。このような場合は、次のように割る値が0でないかを確認する構文を必ず入れる必要があります。
>>> for i in nums:
... if i != 0: # 割る数が 0 でなければ割り算を実行
... print(10 / i)
... else: # 割る数が 0 のときは割り算を実行せず、0 を出力
... print(0)
...
10.0
5.0
0
3.3333333333333335次は代入演算子 (Assignment Operators) です。代入演算子は変数に値を割り当てる演算子です。この演算子は変数の講座でも説明したように、算数のイコールサインのように両側の値が等しいという意味ではなく、 右側の値を左側の変数に割り当てる演算子です。
下の4つの演算子は、2つの演算子を合わせたものと考えていただければと思いますが、2つ目の演算子は変数にxの値を足したあと、結果の値を変数に割り当てます。
代入演算子 (Assignment Operators)
| 演算子 | 使用例 | 別の方法 |
|---|---|---|
| = | x = 1 | x = 1 |
| += | x += 1 | x = x + 1 |
| -= | x -= 1 | x = x - 1 |
| *= | x *= 2 | x = x * 2 |
| /= | x /= 2 | x = x / 2 |
コードを実行してみましょう。
>>> x = 1
>>> x += 1 # x の値に 1 を足した値を x に格納
>>> x
2
>>> x = 2
>>> x -= 1 # x の値から 1 を引いた値を x に格納
>>> x
1
>>> x = 2
>>> x *= 2 # x の値に 2 を掛けた値を x に格納
>>> x
4
>>> x = 4
>>> x /= 2 # x の値を 2 で割った値を x に格納
>>> x
2.0次は比較演算子です。比較演算子は2つの値を比較してTrueまたはFalseを返します。
まずequal演算子から見ていきましょう。equal演算子は両側の値が等しければTrueを、両側の値が違えばFalseを返します。
比較演算子 (Comparison Operators)
| 演算子 | 演算 | 使用例 |
|---|---|---|
| == | 両側の値が等しければTrueを返す | x == y |
| != | 両側の値が等しくなければTrueを返す | x != y |
| > | 左の値が大きければTrueを返す | x > y |
| < | 左の値が小さければTrueを返す | x < y |
| >= | 左の値が右の値と等しいか、より大きければTrueを返す | x >= y |
| <= | 左の値が右の値と等しいか、より小さければTrueを返す | x <= y |
>>> print(0 == 0)
True
>>> print(0 == 1)
False
>>> print('one' == 'one')
True
>>> print('one' == 'two')
False次はnot equal演算子です。Not equal演算子は両側の値が違えばTrueを、両側の値が等しければFalseを返します。
>>> print(0 != 0)
False
>>> print(0 != 1)
True
>>> print('one' != 'one')
False
>>> print('one' != 'two')
True次はless than演算子です。Less than演算子は左の値が右の値より小さければTrueを、2つの値が等しいか左の値が大きければFalseを返します。
>>> print(0 < 1)
True
>>> print(0 < 0)
False
>>> print(1 < 0)
False次はgreater than演算子です。Greater than演算子は左の値が右の値より大きければTrueを、2つの値が等しいか左の値が小さければFalseを返します。
>>> print(1 > 0)
True
>>> print(0 > 0)
False
>>> print(0 > 1)
False次はless than or equal演算子です。Less than or equal演算子は左の値が右の値より小さいか2つの値が等しければTrueを、左の値が大きければFalseを返します。
>>> print(0 <= 1)
True
>>> print(0 <= 0)
True
>>> print(1 <= 0)
False次はgreater than or equal演算子です。Greater than or equal演算子は左の値が右の値より大きいか2つの値が等しければTrueを、左の値が小さければFalseを
返します。
>>> print(1 >= 0)
True
>>> print(0 >= 0)
True
>>> print(0 >= 1)
False今度は論理演算子について見ていきましょう。論理演算子も比較演算子と同じくTrueまたはFalseを返します。他のプログラミング言語とは違い、Pythonの論理演算子は記号ではなくアルファベット
キーワードを使います。
まずAND演算子から見ていきましょう。AND演算子は2つ以上の比較結果の値のうち、すべての値がTrueのときにTrueを返し、1つでもFalseがあればFalseを返します。
実際のコードを見ていきましょう。
>>> print(True and True and True)
True
>>> print(True and True and False)
False
>>> print(False and False and False)
False上で見たように、and演算子はすべての値がTrueのときだけTrueを返します。
次はor演算子です。Or演算子は複数の値のうち1つでもTrueがあればTrueを返します。
Or演算子を使ってコードを実行してみましょう。
>>> print(True or True or True)
True
>>> print(True or False or False)
True
>>> print(False or False or False)
False今度見ていくnot演算子は、すべての値の反対の値を返す演算子です。つまり、Trueの値であればFalseを返し、Falseの値であればTrueを返します。
コードを実行してみましょう。
>>> print(not True)
False
>>> print(not False)
True
>>> print(not (True and False))
True
>>> print(not (True or False))
False次はアイデンティティ演算子です。この演算子は、比較する2つのオブジェクトが実際に同じメモリアドレスを持つオブジェクトかどうかを確認するために使われます。
list_1 = [1, 2, 3]
list_2 = [1, 2, 3]上のように、まったく同じメンバーを持つ2つのリストをイコール演算子とis演算子でそれぞれ比較すると、どんな値が出るでしょうか。実行してみましょう。
>>> list_1 = [1, 2, 3]
>>> list_2 = [1, 2, 3]
>>> print(list_1 == list_2)
True
>>> print(list_1 is list_2)
Falseイコール演算子はTrueを、is演算子はFalseを返しました。なぜでしょうか。それぞれのオブジェクトが持っているメモリアドレスを出力してみましょう。
>>> print(hex(id(list_1)))
0x2136d5e5400
>>> print(hex(id(list_2)))
0x2136d5e3840理由は、イコール演算子は2つのオブジェクトの値だけを比較してTrueを返したのに対し、is演算子は2つのオブジェクトが持つメモリアドレスを比較し、2つのオブジェクトが同じオブジェクトではないためFalseを返したから
です。
次はメンバーシップ (Membership) 演算子です。メンバーシップ演算子は、1つの値があるオブジェクトの中に属しているかを確認するために使われます。メンバーシップ演算子は主に、ある文字列の中にどんな文字列が含まれているかを確認したり、 リストがどんな値を持っているかを確認するときによく使われます。辞書のメンバーを確認するときは、valueを探すのではなくkeyを探すという点をぜひ覚えておいてください。
>>> print('two' in 'one two three')
True
>>> print(2 in [1, 2, 3])
True
>>> print('key_1' in {'key_1': 'value_1', 'key_2': 'value_2'})
True
>>> print(4 not in [1, 2, 3])
True
>>> print('four' not in 'one two three')
True
>>> print('key_3' not in {'key_1': 'value_1', 'key_2': 'value_2'})
True今回の講座では、制御文の役割と演算子について見ていきました。次の講座では、それぞれの制御文の具体的な使い方を勉強していきましょう。