2. 値を変数で扱おう

値と演算子から式を書き、処理系が評価した結果を確認できるようになりましたね。 プログラマーは、値に 名前を付けて 扱います。 この章では、値に名前を付けたり、名前を使った式を書けるようになりましょう。

前章から引き続き、対話モードにプログラムを入力しながら読み進めてくださいね (コマンドラインの先頭に >>> と表示されていれば準備完了です)。

2.1. 変数で値に名前を付けよう

2.1.1. 数値に名前を付ける

まずは数値に名前を付けてみます。

>>> a = 4
../_images/3-2_variable_terminal_shot.png

Enterキーを押すと、対話モードには何も表示されずに、再度プロンプトが現れます。 これで 4 という数値に a という名前が付きました。

対話モードに名前 a を入力してみましょう。

>>> a
4
../_images/3-2-2_terminal_variable_value.png

a も式です。 この式の評価結果は、a という名前が指す 4 となります。

ここで見た a のように、値に付ける名前を「変数 (へんすう)」と言います。 プログラミングでは、変数を 値の名札 として使います。

../_images/3-1_nameplate_image.drawio.png

a と書かれた名札を、整数の 4 に付けた

変数は 値そのもののように扱えます。 試しに、変数 a を使った式を書いてみましょう。

>>> a * 6
24

変数を評価した結果は、変数が指す値になります。 式 a * 6 の評価では、変数 a が指す 4 が使われて、4 * 6 が評価されました。

../_images/3-3_use_variable.drawio.png

名札が付いている値が評価に使われる

続いて、数値 6b という別の名前を付けます。

>>> b = 6
>>> b
6

変数 ab がそれぞれ指す値を掛けてみましょう。

>>> a * b
24

a が指す値 4b が指す値 6 の積 4 * 6 が評価されました。

../_images/3-4_use_variables.drawio.png

ab は別々の名札

2.1.2. 練習問題

変数に慣れる練習です。 ab を使った式(掛け算以外)を対話モードで評価してください。 そして、変数が指す値で評価されているか確認してみてください。

例えば 33 - a のように変数を1つだけ使ってもいいですし、a - b のように変数を2つ使ってもいいです。

[コラム] アルファベットは文字列にも変数にもなる

ab といった変数(名前)を使ってきました。 アルファベットを使っていますが、ab は文字列ではないことに注意してください。

シングルクォートやダブルクォートを付けないアルファベットの並びは、変数 になります。 c = "c" のように、文字列 "c"c という名前を付けることもできます。

2.1.3. 文字列に名前を付ける

文字列に名前を付けるときも、数値のときと同様です。 プログラミングでは、どんな型の値でも変数で名前を付けることができます。

変数 banzai を文字列 "万歳!" の名札にしてみます。

>>> banzai = "万歳!"
>>> banzai
'万歳!'
../_images/3-5_string_value.drawio.png

文字列にも名札を付けられる

変数 banzai は値そのもののように扱えますから、文字列の繰り返しを評価してみます。

>>> banzai * 3
'万歳!万歳!万歳!'

"万歳!" * 3 が評価されていますね。

繰り返しの回数を表す整数にも変数を使ってみましょう。

>>> banzai * b
'万歳!万歳!万歳!万歳!万歳!万歳!'

"万歳!" * 6 が評価されました! 変数にはだいぶ慣れましたか?

本書ではしばらくの間、ローマ字表記の変数 を使います(例: goukeigoukei_kingaku)。

[コラム] NameErrorを見かけたら、変数を入力し間違えていないか見直そう

変数を使い始めると、NameError というエラーによく出会うようになります。 これは、その変数が名札として使えず、プログラムを実行できなかったことを表します。 具体的には、変数を入力し間違えている 場合です。

試しに、banzai という変数を入力し間違えてみましょう。

>>> banzai
'万歳!'
>>> baznai * 3
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
NameError: name 'baznai' is not defined

banzaibaznai と間違えたところ、処理系は NameError を出しました。 "万歳!" の3回繰り返しは実行されていません。

変数の入力間違いを直せばNameError は現れません。

>>> banzai * 3
'万歳!万歳!万歳!'

[発展] 変数に使える文字の決まり

変数には、アルファベットの大文字・小文字、アンダースコア_、数字 が使えます(例:banzai_3sho)。 制約は、先頭が数字で始められない(例:3banzai とできない)ことだけです。 変数を表す文字の長さに制限はなく、好きなだけ長くできます:boku_ga_kangaeta_saikyou_no_hensu_mei。 変数のアルファベットの大文字小文字は区別されます(banzaiBANZAIBanzaiBanZai は変数としては別物ということです)。

2.2. 代入

ここでプログラミングの用語を1つ紹介します。 a = 4 のように、値に名札を付けることを 代入 (だいにゅう)と言います。 「変数 a4 を代入する」プログラムと説明されます。

../_images/3-8-2_assignment.drawio.png

代入は、値に名札を付けること

変数に値を代入することを「変数を定義する」や「変数を初期化する」とも言います。 前の節のコラムで紹介した NameError は、値を代入していない変数を使おうとした場合のエラーです。

2.2.1. 文で動作を指示する

a = 4 のような代入のプログラムについて少し掘り下げてみましょう。

対話モードに式を入力すると、評価した結果が表示されましたね。 それに対して、a = 4 を対話モードに入力したときは、何も表示されませんでした。

a = 4 が何かというと、「文」です。 文は、処理系に動作を指示 します。 a = 4 は処理系に代入するように指示しているのです。 その結果、a4 の名札となります。

皆さんはすでに2種類の文を知っています。 1つは代入、もう1つは対話モードに入力した 式自体 です。 5 + 7 のような式も、処理系に 評価を指示 するので文なのです。 この後の章では、これら以外の文も登場しますよ。

プログラムは様々な文を組み合わせて書かれます。 処理系がやっていることは、文を実行する、ただそれだけです。

2.2.2. 評価結果に名前を付ける

式を使うと、評価結果を変数に代入できます。 4 * 6 という掛け算の結果を変数 seki に代入してみましょう。

>>> seki = 4 * 6
>>> seki
24

式(掛け算)がまず評価されて、その結果が seki に代入されました (掛け算の計算結果を積と言うことから、この名前にしました)。 式の評価が先 に行われ、評価した結果の値に名前が付く という順番です。

../_images/3-8_assignment.drawio.png

評価した結果に、名前を付ける

式には変数も使えますから、ある変数を使った式の評価結果を別の変数に代入できます。 すでに 4 を代入した変数 a を使った例です。

>>> a
4
>>> seki2 = a * 6
>>> seki2
24

a * 6 の評価結果が、変数 seki2 に代入されました。

../_images/3-9_assign_result.drawio.png

変数を使った式の評価結果に別の名前を付ける

桁が大きくて 暗算できない場合 に、式を使った代入は便利です。

>>> ookii_seki = 3600 * 24 * 365

3600 * 24 * 365 の評価結果をプログラマーが暗算できなくても問題ありません。 この積には ookii_seki という名前が付いているので、この変数を使えば続きの計算に進めます。

2.2.3. 代入の使い所

式に加えて代入も使うことで、プログラマーができることは広がります。

  1. 評価結果を再利用できる

  2. 名前を使うことで分かりやすい式にできる

前項の ookii_seki のように評価結果に名前が付くと、ookii_seki を使った別の式を書けますね。 このように 評価結果を再利用 できます。 名前を付けながら評価を積み重ねていき、最後には欲しい結果に至れます。

評価結果の再利用だけを考えると ab のような名前でもいいと思うかもしれません。 ですが、時間が経って何についての処理かをあなたが忘れてしまった場合に備えて、評価結果が何を表すか明確にする名前 を付けることが重要です (10 章名前は重要」もお楽しみに)。

例として、分かりやすい式を使って、1年(365日)は何秒かを求めてみます。 1日は24時間で、1時間は3600秒ですね。 まず1日の秒数を求め、その値を代入した変数を使って、1年の秒数を求めます。

>>> ichinichi_byou = 3600 * 24
>>> ichinen_nichi = 365
>>> ichinen_byou = ichinichi_byou * ichinen_nichi

1日の秒数に1年の日数を掛けて、1年の秒数を求めました。 途中の評価結果を変数に代入して、何を求めているかを示しながら、求める答えまで計算しています。 後で見返した時、変数を手がかりにして、「1年の秒数を求めているプログラムだ」と思い出せますね。

2.3. 代入で変数を活用する

この節では、プログラマーが使う代入のやり方2つを見ていきます。

  1. 同じ変数に繰り返し代入する

  2. 自身を使った式で変数を更新する

特に2はよく使われます。

2.3.1. 同じ変数に繰り返し代入する

同じ変数に複数回代入できます。 その変数は 最後に代入した値を指す 名前となります。

整数 4 を指す変数 a で試してみましょう。

>>> a
4
>>> a = 2
>>> a
2

変数 a は最後に代入した値 2 を指すようになりました。 a はもう 4 の名札ではありません。

次の式では、( 4 * 6 ではなくて) 2 * 6 が評価されます。

>>> a * 6
12

1つの変数は1つの値の名札 です。 2 にも 4 にも同名の a という名札は付けられません。 変数は、最後に代入した値を指します。 それまでに指していた値のことは一切指さなくなると考えてください。

../_images/3-11_assign_multiple_times.drawio.png

名札 a4 から外れ、代わりに 2 の名札となる

2.3.2. 自身を使った式で変数を更新する

同じ変数に繰り返し代入を利用して、自身を使った式を評価した結果で変数の指す値を更新 できます。 これは初めて見たとき、少し面食らうかもしれません。 プログラミングではよく使われる書き方ですので、慣用句だと思ってください。 理解が追いつかないように感じたときは、対話モードで何回か練習して手で覚えてみましょう。

例として、5 を指す変数 c を用意します。 c + 25 + 2 が評価されて 7 となりますね。

>>> c = 5
>>> c + 2
7

プログラミングでは、次のような書き方をすることができます。 変数 c に、式 c + 2 を評価した結果を代入 します。

>>> c = c + 2
>>> c
7

c = c + 2 でやっていることは、先ほど見た例の seki2 = a * 6 でやっていることと同じです。 seki2 = a * 6 では、式 a * 6 を評価した結果を変数 seki2 に代入します。 それと同じように、式 c + 2 を評価した結果を変数 c に代入 しているのです。 変数 c は最後に代入した値 7 を指すようになります。

../_images/3-13_assign_self.drawio.png

c + 2 の評価結果に、新たに c という名前を付ける

c = c + 2 のように、変数を使った式を変数自身に代入する場合、何回実行したかで結果が変わることに注意しましょう。 c が指す値が2ずつ増えていきます!

>>> c = 5
>>> c = c + 2
>>> c
7
>>> c = c + 2
>>> c
9

これに対して、seki2 = a * 6 は連続で何回実行しても seki2 が指す値は変わりません。 ただし、毎回はじめに c = 5 と初期化すると、c の指す値は常に 7 になります。

[コラム] 代入の慣用句との思い出

c = c + 2 という書き方を初めてみたとき、私はすんなりと理解できませんでした。 理解する上でポイントだったのは、代入の = は、数学で等しいを表す \(=\) (イコール)とは別物 という気付きです。

大学のプログラミングの授業で何回か、この書き方の説明を受けたのですが、数式のイコールと違うことに気付くのに私はかなり時間がかかりました。 説明を聞いてもすっきり理解できない期間は、何度も書いて手で覚える ようにしていました(大学では単位を取らなければなりませんからね)。

もし皆さんも、プログラミングで説明を読んでも腑に落ちないときがあれば、手を動かして、対話モードの結果を都度確認しながら、少しずつ理解を深めていきましょう。

2.3.3. 練習問題

代入の「慣用句」に慣れるために練習問題を用意しました。 プログラムは対話モードで入力するとします。

  1. 変数 c5 を代入した後で、c = c - 3 を実行すると、c が指す値はいくつでしょうか。

  2. (1)の後に、c = c * 4 を実行すると c が指す値はいくつでしょうか。

(3) 変数 kakutodani"さしもしらじな" を代入した後で、 kakutodani = kakutodani + "もゆるおもひを" を実行すると、kakutodani が指す値は何でしょうか。

[解答] (1)

5 - 3 の評価結果が c に代入されて 2 となります。

>>> c = 5
>>> c = c - 3
>>> c
2

[解答] (2)

2 * 4 の評価結果が c に代入されて 8 になります。

>>> c = c * 4
>>> c
8

[解答] (3)

"さしもしらじな" + "もゆるおもひを" の評価結果が代入されて、'さしもしらじなもゆるおもひを' となります。

>>> kakutodani = "さしもしらじな"
>>> kakutodani = kakutodani + "もゆるおもひを"
>>> kakutodani
'さしもしらじなもゆるおもひを'

この章では、変数という新しい概念と出会いました。 よく分からないところがあっても、あまり気にしないでくださいね。 書いてあることが全部分かるまで、先を読んではいけないということはありません。 先に進む中で納得することもあります。 また、繰り返し手を動かす中で、「こういうことだったのか!」と納得する瞬間が訪れることもあります。

初めてプログラミングに取り組むというだけで大きな挑戦です。 いくつか分からない箇所があったとしても、「それ以外は分かった!」という成果を持って、次に進みましょう。

[発展] 代入を使って変数自身を更新する結果になる別の書き方

c = c + 2 と同じ結果になる別の書き方を紹介します。

>>> c = 5
>>> c += 2
>>> c
7

c += 2 という書き方をしました。 += の部分は、演算子(ここでは +)と代入のイコール = をつなげて書きます。 整数、浮動小数点数、文字列では、2つの書き方は同じ結果 となります。 しかし厳密には動作が異なり、値の型によっては同じ結果にはなりません(この後登場する「リスト」という型の場合)。

../_images/3-14_plus_assign.drawio.png

c = c + 2 と同じ結果になる

先ほどの練習問題(1)〜(3)を += のような演算子とイコールの形で書き直して練習してみましょう。

(3)のように長い名前の場合は、この書き方だとスッキリしますね。

>>> kakutodani = "さしもしらじな"
>>> kakutodani += "もゆるおもひを"
>>> kakutodani
'さしもしらじなもゆるおもひを'

[発展] 複数の変数に同時に代入する

複数の変数に一度に代入する こともできます。

>>> d, e = 3, 5

これは、変数 d3e5 を同時に代入する書き方です。 このプログラムを実行すると de も値を指すようになります。

../_images/3-15_assign_multiple_variables.drawio.png

2つの値に同時に名前を付ける

>>> d
3
>>> e
5
>>> d * e
15

2つの変数に限らず、3つ以上の変数にも同時に代入できます。 同時に代入する書き方のルールは以下のようになります:

  • = の左側に変数をカンマで区切って並べます(例: d, e

  • = の右側に値や変数、それらを使った式を、カンマで区切って並べます(例: 3, 5

重要な点は、=左側と右側に並べる数は同じにする ということです。