前回まで,ハードウェアがないとプログラムを動作させられなかったので,読者の皆さんにも疑似体験していただけるようパソコンの上で動作が再現できるシミュレータを開発しました。まずこれをご紹介しましょう。
ちなみに,第2回補足ではハードウェアトラブルが起きてしまいましたが,ソフトウェアの方はこのシミュレータを使ってテストしています。
シミュレータとその使い方
シミュレータの動作環境として,PHPの4または5を利用しています。Webサーバから利用できる必要があり,gdライブラリも使いますが,一般的なLinuxのディストリビューションであればどれもパッケージが用意されていると思います。サンプルの制御プログラムを動かす場合にはコマンドライン版のPHPも必要ですが,これもLinux環境なら問題ないと思います。Windowsでも問題なく利用できます。
まず,シミュレータや関連ファイルを以下のリンクからダウンロードしてください。
なお,前回まではコントローラを指すようURLを192.168.0.100にしていましたが,今回からはシミュレータを指すようにしています。
ダウンロードしたファイルを解凍したら,適当なWeb公開用のディレクトリに,simrail.php(シミュレータ本体)とrailconf.txt(設定ファイル)を置きます。railconf.txtはWebサーバから書き換えますので,chmod a+rw railconf.txtなどとして,書き込み権限を与えておいてください。
なお,サンプルはすべて/gh/rail/simrail.phpにアクセスするようになっていますので,ここにファイルを配置すると簡単です。ただしインターネットには公開しない方がよいでしょう(usleepを使っているのでサーバの負荷が高くなります)。
リスト1 初期状態のrailconf.txt
# 10 13 20 30 37 40 50
# 10 _____+--------+_____
# 13 + +
# | |
# 20 + +
# | |
# 27 +_____ _____+
# 30 +---00--+
R00,3030,2030,1327,1020,1313,2010,3010,3713,4020,3727,3030
TA,2030,3030,50
TB,2010,3010,50
S0000,D
この状態で,上記のsimrail.phpにWebブラウザからアクセスすると,シミュレータの画面が表示されます。初期状態では,環状のレールを車両が2つ走行している状態になります。
先にも書きましたが,プログラムをテストするときは,まずレール配置などを記述したrailconf.txtという名前のファイルを用意します。railconf.txtは実行に従って上書きされてしまいますので,別に用意したテキストファイルからコピーするのがよいでしょう。たとえば前回の最後に紹介した2重ループのレイアウトサンプルであれば,ダウンロードして解凍した中のrail22.txtを使用します。
cp rail22.txt railconf.txtなどとして,railconf.txtに反映してください。これで,シミュレータの画面が変わるはずです。
リスト2 rail22.txt(2重ループのレイアウト)
# 10 13 20 25 30 37 40 45 50 57 60
# 10 _____+---|-04-+--------+---|-00-+
# 13 + p2 ~~~~~+ ~~~~~+
# | | |
# 20 + + +
# | | |
# 27 +_____ p3 _____+ _____+
# 30 +05-|----+--------+01-|----+
R00,4530,5030,5727,6020,5713,5010,4510
R01,4530,4030
p0301,4030,2530
P0304,2530,3030,3727,4020
R04,4510,4010
p0204,4010,2510
P0204,4020,3713,3010,2510
R05,2530,2030,1327,1020,1313,2010,2510
TA,4030,4530,50
TB,4510,5010,50
S0000,AAppAA
最後に,線路のレイアウトに応じたプログラム(スクリプト)を実行します。このとき,リスト中のURLを自分のサーバのsimrail.phpを指すように変更してください。
コマンドラインから./rail22.phpなどと入力してスクリプトを実行すると,シミュレータの画面に様子が表示されます。起動できない場合は,php -f rail22.phpも試してみてください。
rail22.phpを実行したところ(シミュレータが古いバージョンのため,多少動作がぎこちないところがあります)
サンプルには,そのほかにも第1回,第2回で扱ったレイアウトに対応したプログラムが入っています。それぞれのスクリプトと設定ファイル(railconf.txtにコピーするもの)は,以下のようになりますので試してみてください。
表1 プログラム(レールレイアウト)とファイル名
| 直線レイアウト | rail11.txt |
|---|---|
| 第1回サンプル | rail10.php,rail11.php,rail11a.php |
| 第2回サンプル | rail21.php |
| 引き込み線レイアウト | rail12.txt |
| 第1回サンプル | rail12.php |
| 2重ループレイアウト | rail22.txt |
| 第2回サンプル | rail22.php |
シミュレータの仕組み
本題とはあまり関係ないのですが,シミュレータの仕組みについて説明しておきましょう。普通,連続的なシミュレーションには常駐プロセスを使用し,そこと他のプログラムが通信するスタイルを取るのが普通だと思います。ただ,ここではあまり複雑なことをしたくなかったので,以下のような方法にしました。
ブラウザや制御プログラムからsimrail.phpがアクセスされると,railconf.txtを読み込んだあと,前回からの経過時間を調べます。そして,その時間分のシミュレーションをおこなったあと,リクエストや画面表示の処理をおこないます。ゲームで,プレイヤーがいない間に起こったできごとを,前回セーブしたときからの経過時間に応じて,ロード時に再現するものがありますが,それと似たような考え方です。
この方法を使うには,あるリクエストのときに行ったシミュレーションの途中の状態を,次のリクエストに引き継げる必要があります。そこで,railconf.txtにシミュレーションの結果を毎回書き出しています。複数のリクエストが同時に来る可能性があるため,flockで排他処理を行っています。またrefreshを使い,定期的にブラウザに再読み込みさせることで画面を更新し,定期的にリクエストが発生することでシミュレーションが進むようになっています。

