前回は何で例外が起きちゃったの? | |
『変数の有効範囲』を考えてなかったからだよ。 | |
変数の有効範囲…ってどういうこと? | |
if とか while の中のスクリプトに2つ以上の命令が入ってる時には、
{ と } で囲まれた部分にスクリプトを書いたよね。 例えばこんなふうに。 |
<正しいスクリプト>
うん、確かにそう書くよね。 | |
この { と } で囲まれた部分をブロックって呼ぶんだけど、 ブロックの中で宣言された変数は、そのブロックの中でしか使えないんだ。 | |
えっ、そうなの!? 宣言した後はずっと使えるんじゃないの? |
|
上のスクリプトの場合は input がブロックの外にあるから、宣言した後はずっと使えるんだけど、 こんなふうにブロックの中で宣言すると、input は while ブロックの中でしか使えないんだ。 |
<正しくないスクリプト>
試しに実行してみて。 | |
うん。 ……あ、ホントだ。文字列を入力して OK ボタン押したら『メンバ"input"が見つかりません』っていう例外が起きたね。 でもなんでこんなふうになってるの? |
|
もし変数を宣言した後はずっと使えるようになってたら、 例えばブロックの中だけで一時的に変数を使いたい時でも、 それまでに宣言した変数の名前と重ならないように気をつけないといけないでしょ。 | |
もし名前が重なっちゃってたら、値が書き換えられちゃうってこと? | |
ん、そういうこと。うっかり変数の値を書き換えちゃったら、動作がおかしくなるかもしれないからね。 だから、ちょっとの間しか使わない変数はブロックの中に入れて、色んな所で使う変数だけをブロックの外で宣言すれば、 間違って変数の値を書き換えちゃうミスを減らせるってワケ。 |
|
なるほどね〜。 | |
まとめると、ブロックの中からブロックの外の変数は使えるけど、 ブロックの外からブロックの中の変数は使えないってことだね。 |
あ、ちょっと質問。 | |
ん? | |
ブロックには if とかつけなくてもいいの? | |
うん、こんなふうに何もつけずにブロックを書くこともできるよ。 こうすると { と } が無い時と同じように、 普通にブロックの中身が実行されるんだ。 |
|
へぇ、そうなんだ。 | |
あと、こんなふうにブロックの中と外で同じ名前の変数を作ることもできるんだ。 |
ちょっと実行してみて。 | |
うん。 ……最初に「a の値は 2 です。」って表示されて、 次に「a の値は 1 です。」って表示されたね。 |
|
つまり、ブロックの外の a とブロックの中の a は同じ名前だけど違う変数ってこと。 で、ブロックの中で a って言うと、ブロックの中で宣言されてる a の方を指すんだ。 ブロックの外で a って言うと、もちろんブロックの外で宣言されてる a の方になるよ。 |
|
へぇ…でもなんかちょっとややこしいかも。 | |
ま、確かに普通はブロックの外と中で違う名前にした方がわかりやすいよね。 | |
だね。 | |
それじゃ、前回のスクリプトを直してみよっか。 | |
はーい! | |
まず、このスクリプトのどこが間違ってたと思う? | |
えーっと… エラーメッセージに「メンバ"i"が見つかりません」って表示されてたから、 i の宣言が間違ってるんだと思うんだけど… | |
うんうん。 | |
i は if ブロックの中で宣言してるけど、 ブロックの外側にある while の条件式のところでも使ってるから、これが間違いかな。 | |
ん、そうだね。 じゃあ、i はどこに宣言すればいい? |
|
えっとね… while の条件式はどのブロックにも入ってないから、 i は while ブロックの外に宣言しなきゃいけないんじゃないかな。 | |
じゃあ、スクリプトを書き直してみて。 | |
うん。 |
うん。 これでいいと思うよ。 |
|
じゃ、確かめてみよっか。 | |
うん。 実行して、「100」って入力して、OK。 ……あ、今度はちゃんと 100 分後の時刻が表示されたよ! |
|
次は数値じゃない文字列を入力してチェックね。 | |
じゃあ「10a」って入力して、OK。 ……また入力ウィンドウが表示されたよ。 |
|
ん、これで OK だね。 スクリプトが複雑になってくると、一時的にしか使わない変数はできるだけブロックの中に入れるようにした方がいいんだけど、 有効範囲の外で変数を使っちゃうミスをしないように気をつけてね。 |
|
うん、わかった! | |
じゃ、今回はここまで。 また次回ね。 |