プログラム講座 上級編8
- 1/1000秒を計測する -
上級編8です。今回は「1/1000秒を計測」してみます。
◆Time Manager(タイムマネージャー)
FBが標準でサポートしているToolboxコールのTICKCOUNTでは1/60秒までしか計測する事ができません。そこで登場するのがPascal Converterです。Pascal Converterについては第7回でやりましたので、変換方法についてはそちらを参照して下さい。
変換するのは「Time Manager(タイムマネージャー)」のヘッダーファイルです。変換が面倒な人は、トップページに圧縮したものを用意してありますので、その中から利用して下さい。
Time Manager(タイムマネージャー)の中にはいくつか呼び出しがありますが、今回使用するのは
FN Microseconds(@microTickCount&)
という呼び出しです。これは指定した変数にミリセコンドの秒数を返すものです。指定する値は符号なし32ビット数値となっています。
◆Future BASIC上で使用するには
Future BASIC上で使用する場合、符号無し32ビット数値という変数は用意されていませんので、符号付き32ビット変数(末尾に&を付加)で代用します。簡単にできないものかと思ってUNS$を使用してみましたが、どうも内部的にうまく変換されない(0になる)ので別の方法を使用しました。
符号付き32ビット数値の場合、内部では31ビット目(最上位ビット)が符号を表しています。ビットが0であれば「正数」、1であれば「負数」となります。そこで「論理演算」を利用して強制的に正数に変換します。AND(論理積)を利用すると手軽に正数に変換できますが、ミリセコンド以上の秒数を計測する場合は注意する必要があります。
最上位ビットを0にするには、以下のようなビットマスクと論理積を取ります。
0111 |
1111 |
1111 |
1111 |
1111 |
1111 |
1111 |
1111 |
16進数にすれば7FFFFFFFとなります。次にFN Microseconds(@microTickCount&)からの戻り値ですが、ミリセコンド(12.35秒といった形式)にする場合は1000000(100万)で除算する必要があります。
今回はサンプルとして「ダブルクリックの速度」を表示するプログラムを作成してみました。1/1000単位での計測を行いたい場合に参考になるでしょう。符号無し32ビット数値にするうまい方法がありましたら誰か教えて下さい。if文を使うのもイマイチですし、論理式でやるのもイマイチかなあ。
◆終わりに
今回使用した方法では長い時間を計測するのにはむいていません。長時間計測する場合は、TIME$やTICKCOUNTを使用するように切り分けましょう。
次回は・・・と予告通りに書いたことがないので未定にしておきます(笑)
◆今回のプログラムリスト
'------------------------------------------------
' "1/1000秒単位の計測を行うプログラム"
'------------------------------------------------
LOCAL MODE
LOCAL FN Microseconds(@microTickCount&)
` MOVE.L ^microTickCount&,-(SP)
` DC.W $A193,$225F,$22C8,$2280
END FN
CLS
PRINT "Push Any Key to End!"
WHILE INKEY$=""
PRINT "Push Mouse Button to Start!"
WHILE FN BUTTON = _false:WEND
stm! = FN Microseconds(startTime&) AND &H7FFFFFFF
WHILE FN BUTTON = _true:WEND
WHILE FN BUTTON = _false:WEND
WHILE FN BUTTON = _true:WEND
etm! = FN Microseconds(endTime&) AND &H7FFFFFFF
total! = (etm! - stm!)/1000000
PRINT "Time is ";total!;" sec."
WEND