エレベーターのしくみをプログラミングで考える|呼び出しても通り過ぎるのはなぜ?

エレベーターを待つとき、乗場にある[上]や[下]のボタンを押します。しばらくするとエレベーターがやってきます。

ところが、同じ[上]のボタンを押していても、その階で止まってくれることもあれば、目の前をそのまま通り過ぎることもあります。同じ操作をしているのに、なぜ結果が違うのでしょうか。

この記事では、乗場から見えるエレベーターの動きを観察しながら、「止まる」「通り過ぎる」をどのような条件で判断しているのかを、できるだけ単純な形で考えてみます。

エレベーターの動きを観察する

まずは、エレベーターを待っている人から見える動きを比べてみます。

[上]ボタンを押すと止まってくれることがある

上の階へ行きたいときは、乗場の[上]ボタンを押します。

エレベーターが近づいてきて、その階で止まり、ドアが開けば、そのまま乗ることができます。利用する側から見ると、「[上]を押す」と「エレベーターが止まる」が自然につながっているように見えます。

[上]ボタンを押しても通り過ぎることがある

しかし、[上]ボタンを押して待っていても、近づいてきたエレベーターが止まらず、そのまま下の階へ向かっていくことがあります。

押したボタンは同じ[上]です。それでも、止まる場合と通り過ぎる場合があります。

ここで大切なのは、エレベーターが「[上]ボタンが押されたか」だけを見ているわけではない、ということです。

エレベーターは何を基準に止まる・通過するを判断している?

この記事ではしくみを考えやすくするため、乗場の[上][下]ボタンと、エレベーターが現在どちらへ移動しているか、または停止しているかに注目します。

たとえば、[上]ボタンが押されている階へ、エレベーターが上向きに進んでいるとします。この場合は、利用者が行きたい方向とエレベーターの移動方向が一致しています。

一方、同じ[上]ボタンが押されていても、エレベーターが下向きに進んでいるなら、方向は一致していません。

また、エレベーターが停止している場合は、まだ上向き・下向きという移動方向が決まっていません。呼び出しが入ると、その階へ向かう方向を決めて動き始めます。

この記事では、しくみを単純にして、エレベーターが移動中なら「呼び出した方向」と「エレベーターの移動方向」が一致していれば止まり、一致していなければ通り過ぎるものとして考えます。エレベーターが停止中なら、呼び出された階を目的地として、まずその階へ向かうものとします。

実際のエレベーターでは、複数の呼び出しや行き先、安全のための制御など、さらに多くの条件が使われます。ここでは、止まる・通り過ぎるという違いを考えるために必要な部分だけを取り出します。

エレベーターのプログラムを考える

ここからは、見えている動きをプログラムの処理に置き換えて考えます。

この記事では、エレベーターの状態を「停止中」「上向き」「下向き」の3つとして考えます。

呼び出された階で止まるときはどう判断しているか

エレベーターが移動中で呼び出された階に近づいたとき、まず「どちらの方向のボタンが押されているか」を確認します。

次に、エレベーター自身が現在どちらへ移動しているかを確認します。

たとえば[上]が押されていて、エレベーターも上へ移動しているなら、二つの方向は一致しています。この記事では、このときその階で止まり、ドアを開くものとします。

同じ[上]ボタンでも、エレベーターの状態が違えば結果が変わります。プログラムは、ボタンの情報だけではなく、現在の移動方向も組み合わせて判断していると考えられます。

一方、エレベーターが停止中なら、まだ移動方向はありません。呼び出しが入ったら、その階を目的地として移動を始め、到着したら止まるものとします。たとえば、停止している位置より下の階で[上]が押された場合は、いったん下向きに移動して、その人を迎えに行きます。

ここでは、この「迎えに行く動き」と、移動中に途中の階で止まるかどうかの判断を分けて考えます。

呼び出されても通り過ぎるときはどう判断しているか

[上]が押されている階へ、下向きに移動しているエレベーターが近づいた場合を考えます。

[上]という呼び出しはありますが、エレベーターが進んでいる方向とは一致していません。この記事では、この場合はその階に止まらず、現在の方向へ移動を続けるものとします。

ただし、呼び出しそのものがなくなったわけではありません。エレベーターの向きが変わり、呼び出した方向と一致したときに、あらためてその階へ向かうと考えます。

つまり、「呼ばれた階だから必ず止まる」のではなく、そのときの状態を確認してから動作を決めています。

エレベーターのプログラムのフロー図を考える

ここまで考えた処理を、フロー図で整理します。

まずエレベーターが停止中か、移動中かを確認します。停止中なら、呼び出された階を目的地として移動し、到着したら止まります。移動中なら、乗場ボタンの方向と現在の移動方向を確認し、方向が一致していれば止まり、一致していなければ通り過ぎます。

文章では順番に説明してきましたが、フロー図にすると、「停止中か」「方向が一致しているか」という条件によって処理が分かれることが見えやすくなります。

フロー図の役割は、文章をそのまま置き換えることではありません。同じボタンが押されていても、エレベーターの状態によって結果が変わることを、ひとつの流れとして見えるようにすることです。

Scratchでエレベーターを作ってみよう

ここまで考えた動きを、Scratchでプログラミングしてみましょう。素材は当サイトで用意しています。

・エレベーター|初級

・エレベーター|中級・上級

完成コードは掲載していません。どんな情報を覚えておき、どの条件で動きを分ければよいかを考えながら作ってみてください。

あとがき

エレベーターは、乗場のボタンを押せば必ずその場で止まるわけではありません。同じ[上]ボタンを押していても、止まることもあれば、通り過ぎることもあります。

今回考えたのは、その違いを生む条件です。単純化したモデルでは、停止中なら呼び出された階へ向かい、移動中なら「呼び出した方向」と「エレベーターの現在の移動方向」が一致しているかを確認して、止まるか通り過ぎるかを決めました。

身の回りの機械は、同じ操作をしても、いつも同じ動きをするとは限りません。そのとき機械がどのような状態にあるのかまで考えると、プログラムがどの情報を使って判断しているのかが見えやすくなります。

この記事を書いた人

Flowz

プログラミングと数学のしくみを、図や具体例で伝えています。「なぜそうなるのか」を、一つずつ考える学びを大切にしています。