Casio Basic入門24

Casio Basic入門
<目次>

誤字脱字・記載ミスや分かりにくい表現は随時追記・修正します
最終更新: 2015/07/03

 4. CasioBasicを使ってみる(続き)

Chapter 5

◆ Chapter 5 の目標: サブルーチンを使いこなす

前回: Casio Basic入門23 を見る

「世界時間表示プログラム TIME ZONE 」 を実際に作ってゆきます。

Chapter 5 では、以前実際に考えたり作ったりしたことを振り返るために、以前の記事やCasio Basicコマンドリファレンスへのリンクも紹介してゆきます。

プログラムを作る時は、できるだけわかりやすくソースコードを書く ことを心がけます。機能追加が楽になり、バグの発生も少なくなるからです。そして、最初から欲張って多くの機能を盛り込もうとはせずに、全体の骨組みになる部分から作り始めます。その後、徐々に機能を追加するのが確実です。今回は、サブルーチンをうまく使ってゆきます。

そこて、最初に大まかな方針を作ります。


大まかな方針

方針1. 1 画面内で表示と入力を行う。
  → 入力ボックスを使う

方針2. 最初に、日本・ドイツ・ロサンゼルス(LA)時間の換算プログラムを作り、後から機能追加して夏時間の計算とヨーロッパ・北米のそれぞれのタイムゾーンへの変更と計算をできるようにする。

方針3. ドイツは8時間、ロサンゼルスは17時間だけ日本時間から戻せば(引き算)すれば良い。これは夏時間でない時。

方針4. 時間は24時制を使う。

方針5. 時間は 1024、930 といった整数で扱い、時間を格納する変数には、この整数を入れる。

方針6. 時間表示は、必ず4桁表示とする。例えば 1024、0930、0010 、0004 など、3~1桁の場合は頭に 0 を付加する。4桁に揃えないと、一覧表示が見づらく、勘違いする可能性が増える。

方針7. 大きな骨組みとして、プログラム構造を考える。

 [初期設定] 
 [初期表示]
 While 1
   [メニュー番号取得処理]
   [メニュー番号に応じた入力処理]
   [メニュー番号に応じた時間計算]
   [時間表示の更新]
 WhileEnd


方針8. あとは、実際に作りながら考え、細かいところは必要に応じて変更する。


今回作成するのは、日本時間を入力すると、中央ヨーロッパ時間と北米太平洋時間を表示する機能です。

今回完成させるプログラムを一番下に載せているので、先にそれを見て分かれば先に進むのも良いでしょう。



Chapter5-2
Getkey、入力ボックス、Locate の活用

では、大まかな方針に従って、具体的にプログラムを書いてゆきます。

先ず最初に、日本時間を入力すると、ドイツとロサンゼルスの時間を表示する機能を作ります。

画面デザイン

メイン画面を以下のようにします。

35-TZ1_main   

0:JST
これは日本時間です。[0] キーを押すと日本時間を入力します。項目 1 や 2 で海外の時間を設定した場合は、それに合った日本時間を、ここに表示します。

1:CET
これは、中央ヨーロッパ時間 (Central Europe Time)で、プログラム起動時の初期設定を CET とします(私の好みです...)。[1] キーを押すと CET の時間を入力します。ドイツ、フランス、イタリアなど多くの国がこのタイムゾーンに含まれます。項目 0 や 2 で時間を設定した場合は、それに合った CET 時間がここに表示されます。ドイツが含まれるので、しばらくはドイツ時間と言うことにします。

2:PST
これは、アメリカの太平洋時間 (Pacific Standard Time)で、プログラム起動時の初期設定を PST とします。[2] キーでの入力や表示については、上と同様です。ロサンゼルス(LA)が含まれるので、しばらくはロサンゼルス時間と言うことにします。


この画面を作るプログラムは、以下の通り。

Locate 1,1, "0:JST"
Locate 1,2,"1:CET"
Locate 1,3,"2:PST"
Locate 1,4,"<AC>:QUIT"


上の方針で決めたように、後で機能追加する時に、夏時間を設定する機能や、タイムゾーンを変更する機能を追加します。その時、前回紹介したようにタイムゾーンの略称を現地で使われるように変更する予定なので、画面表示を変える必要がでてきます。つまり、上の5行のプログラムは、徐々に複雑になることが予想されるので、画面の表示をサブルーチンにしてメインルーチンから呼び出すようにします。

このようにすると、画面の表示を変える場合でも、メインルーチンを変更せずに済むので、プログラムがわかりやすいままで、バグの発生も抑えられる筈です。

画面表示サブルーチンのファイル名を TZM とします(メイン画面 → MainM なので、TZ + M )。
ちなみに、TZTIME ZONE の略称。

TZM のプログラム
Locate 1,1, "0:JST"
Locate 1,2,"1:CET"
Locate 1,3,"2:PST"
Locate 1,4,"<AC>:QUIT"



次に、メインルーチンを作ってゆきます。
メインルーチンのファイル名を TZ とします。TIME ZONE だから、TZ です。

ドイツと日本の時差は、夏時間でない時は8時間、ロサンゼルスとの時差は17時間です。この値は、プログラムで絶対に使うので、変数に入れておきます。ドイツとの時差を変数 P として 9 で初期化、ロサンゼルスとの時差を変数 Q として 17 で初期化します。
8→P:17→Q


ここまでの TZ のプログラム
8→P:17→Q
Prog "TZM"




今回具体的に作るのは、[0] キーを押した時、日本時間 (JST) を入力させ、ドイツ時間とロサンゼルス時間を計算し、その結果を画面表示する機能を作ります。

1.メニュー番号取得処理
ループの中で Getkey コマンドを使って、[0] キーが押された時、メニュー変数 M0 を設定する。なお、この処理では、何かキーが押されるまでプログラムは先に進まず、入力待ちの状態にする。

2.入力処理
M=0 の時、入力処理を行い、その結果を 日本時間を格納する変数 J に入れ、0:JST の右に入力した時間を表示する。

3.時差計算
M=0 の時、入力された日本時間に対応したドイツ時間とLA時間を計算する。

4.時間表示の更新
日本、ドイツ、LAの時間の表示を更新する。

5.ループ構造
項目1~3の処理は繰り返し行うので、これらを While 1 ~ WhileEnd ループの中に入れる。


以上を、擬似的なプログラムで表現してみます。

While 1

   [メニュー番号取得処理] (ここで入力待ち)

  If M=0:Then
     [日本時間の入力処理
  IfEnd

  If M=0:Then
     [時間の計算] 
  IfEnd

  [時間表示の更新]


WhileEnd



While 1WhileEnd は無限ループです。PCなどのプログラムでは、無限ループはCPUパワーを無駄に食いつぶすだけでなく、プログラムを正常終了できなくなる可能性もあるので、基本的に使うべきではありません。特に Windows プログラミングでは、できるだけ速やかに制御を Windows (OS) に戻すのが作法です。

しかし、Casio Basic の場合は、[AC] キーを押せば、いつでもプログラムを終了可能で、終了のための特別な処理が不要です。従って、これまでに作ってきたプログラムも、[AC] キーで終了させるようにしています。従って、Casio Basic を用いた電卓プログラムでは、無限ループを積極的に利用します。




1.メニュー番号取得処理

Getkeyコマンドの使い方は、以下に詳しく説明していますので、まだよく分からない場合は参照してください。
 ⇒Casio Basic コマンドリファレンス: Getkey
 ⇒Casio Basic入門3: Getkey と Locate コマンドを使いこなす


条件ジャンプの ⇒命令については、以下のコマンドリファレンスや、過去のCasio Basic入門を参考にしてください。
 ⇒Casio Basic コマンドリファレンス: ⇒命令


メインルーチンTZ:メニュー番号取得処理のプログラム
-1→M
Do
Getkey→K
LpWhile K=0
K=25⇒0→M


[0] キーのキーコードは 25 です。


ここで、1つ大切な注意点:

最初に、変数 M を -1 で初期化しています。キーコード取得のための Do ループは、K の値が 0 の時ループを継続します。キーコードが 0 と言うのは、キーが何も押されていない状態を示します。

さて、このプログラムを起動する前に、電卓を様々な用途で使うわけで、その際に変数 M に 0 以外の何かの値が入ることが十分有り得ます。

もし、-1で M を初期化しておらず、M に 0 が入っていた場合、[0] 以外の何かキーが押されたことを想定します。その場合、このループを脱出して先に進み、M には想定外の値 0 が入っています。すると、[0]を押していないのに、メニュー番号0が選択されたと誤判定されます。このように想定外の M の値によって、プログラムが意図しない動作をするわけです(要するにバグ)。
そこで、変数 M を完全に把握して制御することで、プログラムを意図に従った動作以外できなくします。

このバグは簡単に発生します。メニュー番号変数 M は、0 以上の整数とするつもりなので、絶対にメニュー番号になり得ない -1 で初期化しておきます。

使う変数は、使う前に初期化をする癖を付けると、バグが入りにくくなってプログラミングが楽になります。



2.入力処理

本プログラム TIME ZONE では、時間を24時制とし、4桁の数字で時間を表すことにしています。
 ・10:24 は、1024
 ・9:30 は、0930
 ・0:20 は、0020
 ・6:00 は、0600
 ・0:05 は、0005


INPI の使い方

入力には、入力ボックス:INPI を使います。
Chapter 3 / Chapter 6 で 入力ボックス:INPI を作りました。その時に作ったプログラムが fx-5800P に残っていない場合は、先ず入力してください。INPI のソースコードは、以下にあります。

 ⇒ fx-5800P プログラムライブラリ - INPI 
INPI はバージョンアップ (Ver 2.0/2.1) し [Chapter 6 参照]、キー入力の反応が大幅に改善しています。 

INPI の使い方や動作について、詳しくは上記プログラムライブラリーを参照してください。


サブルーチン:INPIメインルーチンから呼び出す直前に、4つの変数 XYDE の値を設定します。INPI はこれらの変数を参照して動作します。

 ・X: 入力ボックス開始位置の X 座標
 ・Y: 入力ボックス開始位置の Y 座標
 ・D: 入力ボックスの桁数
 ・E: インジケータの表示方法(サイズ)を設定するフラグ、0 で大きな表示、1 で小さな表示

サブルーチン:INPI は、入力確定してメインルーチンに戻る時、変数 Z に入力値を格納します。従って、INPI の直後で、変数 Z の値を、メインルーチンで使用する変数に代入しておく必要があります。

INPI を使う時は、5つの変数(XYDEZ)は、その値が変化します。つまり、これらの変数をメインルーチンで使う時は、値が変化することを前提にしてください。

0:JST の横、(X, Y) = (8, 1) の位置に、4桁の入力ボックスを表示させ、小さいインジケータ(▶E)を表示させるので、プログラムは以下のようになります。変数 J は、上でも述べたように、日本時間を格納する変数です。

8→X:1→Y:4→D:1→E
Prog "INPI"
Z→J


INPI の変数とメインルーチンの予約変数
メインルーチンでは、日本時間 J、ドイツ時間 G、ロサンゼルス時間 U、時差 P, Q など、他のサブルーチンで勝手に変更されては困る変数があります。これを予約変数と呼び、他で値が変更されても構わない変数を使い捨て変数と呼んでいます。
INPIで使う変数は当然それらの値は変更されるので、メインルーチンの予約変数には使えません。

メインルーチンの予約変数は、以下のINPIで使う変数を避けて使います。

INPI で使う変数
 C: 入力中の桁数
 D: 入力ボックスの桁数
 E: 確定ガイドフラグ
 I: for文制御変数、入力キー
 K: キーコード
 X: 入力開始桁
 Y: 入力開始行
 Z: 入力数値
 配列変数 Z[n]n = 21~23, 25, 31~33, 35~37


・時間から「時」と「分」を分離して計算する

本プログラムでは、時差の計算が最も重要な仕事です。

時差は時間単位で決まっています。そこで、日本時間 10:24 に対して、例えばドイツ時間は 2:24 であり、「分」はそのままで、「時」だけが 8 減っています。

そこで、時間から「時」と「分」を分離して、「時」を変数 A に入れ、「分」を変数 B に入れておくと、時差計算が便利になります。

時間の変数に格納される整数について、下位2桁が「分」となります。例えば日本時間 J については、以下のようにすれば「時と「分」が得られます。

Int(J÷100)→A
J-100A→B


J の値が、3桁 (0905など)、2桁(0020など)、1桁(0005など)でも、この計算が正しいことは、試してみると分かります。

ここで使っている Int( ) 関数は、( ) 内の数値の整数部分を取り出すものです。
 ⇒ Casio Basicコマンドリファレンス: Int( ) / Frac( )


・省略した入力への対応

例えば、9:00 を入力したい時、900 と 3桁を入力するよりは、9 と1桁の入力で済ませた方が楽です。6:30 を入力するには、630 と 3桁入力が楽です。

INPI の最初のバージョンは fx-5800P では応答性があまり良くなく、キー入力が速すぎると、処理が追いつかずに入力を取りこぼすことがありました。そこで入力桁数を少なくできる省略入力機能をつけました。しかしその後バージョンアップして充分な応答性が実現しましたが、利便性を考えて、この機能を残します。

入力を省略できるのは、1桁および2桁入力の時で、入力したものを「時」として判断するようにします。そこで、入力して得られた数が2桁以下の時、つまり 100未満の数の時、その数は「時」であると判断させます。具体的には、以下のプログラムになります。

If J<100:Then
J→A:0→B

Else
Int(J÷100)→A
J-100A→B
IfEnd


これには、上記の「時」と「分」の分離計算を含みます。

但し、この計算は日本時間を入力する時だけでなく、ドイツ時間やLA間の入力時にも使いますので、サブルーチンにしておくことにします。

そこで、INPI 実行直後は、変数 Z は入力した時間になっているので、このサブルーチンでは、変数 Z で時間の値を受け取ります。サブルーチン実行後は、「時」を変数 X に、「分」を変数 Y に入れることにして、サブルーチン直後で、X→A:Y→B とすれば、メインルーチンの変数 A B に「時」」と「分」を受け渡しできます。

※ このロジックだと、例えば0時20分を入力するために 0020 と入力したり、0時5分を入力するために 0005 と入力すると、おかしなことになります。0020 と入力して [EXE] キーを押すと 2000 と表示され、0005 と入力して [EXE] キーを押すと 0500 と表示されます。0時xx分のときだけは、24xx と入力する必要があります。0時台の時間入力を例外的に 24xx と入力させるのですが、他の時間の入力の利便性を優先させることにします。

このサブルーチンのファイル名を TZC とします。計算 (Calculation) の C を使って、TZ + CTZC です。

サブルーチン:TZC のプログラム
If Z<100:Then
Z→X:0→Y
Else
Int(Z÷100)→X
Z-100X→Y
IfEnd



以上をまとめると、日本時間の入力処理は以下のようになります。

メインルーチンTZ:入力処理のプログラム

If M=0:Then
8→X:1→Y:4→D:1→E
Prog "INPI"
Prog "TZC"
X→A:Y→B:Z→J
IfEnd




3.時間の計算

・入力した日本時間からドイツ時間とLA時間を得る方法

さて、今後使う予定のメインルーチンの予約変数を先に決めておきます。

 ・J: 日本時間
 ・G: ドイツ時間 (中央ヨーロッパ時間)、実はドイツ = Germany から変数を G にしました。
 ・U: LA時間 (アメリカ太平洋時間)、アメリカ = USA から変数を U にしました。
 ・A: 入力した時間を分割した「時」
 ・B: 入力した時間を分割した「分」
 ・P: 日本とドイツとの時差
 ・Q: 日本とLAとの時差

AB、P、Q  から、J、G、 U を計算して、それを表示するのが、ここでの処理です。

・日本時間:
  - 「時」 = A
   但し、A が 24以上になる場合は、24 を引く (この場合は日付が変わる)
   コードは、
    A≧24⇒A-24→A
   
となる。
  - 「分」 = B
  - 時間: J = 100A + B
   コードは、
    100A+B→J
   
となる。

上記の省略入力機能では、0:05 と設定するために 0005 や 005 と入力すると 5:00 と認識され、このままだと 0:05 と設定できません。そこで、0:05 の代わりに、24:05 と設定すると、つまり 2405 と入力すれば 0:05 と認識できれば良いわけです。そこで、

A≧24⇒A-24→A

としました。

・ドイツ時間: 日本時間から時差 P (9時間) を引く
 - 「時」 = A - P (= C とおく)
  但し、A - P の結果が 0 未満になる場合は、24 を足す (この場合は日付が変わる)
  プログラムは、
   A-P→C
   C<0⇒C+24→C
  
となる。
 - 「分」 = B
 - 時間: G = 100C + B
  プログラムは、
   100C+B→G
  
となる。

・LA時間: 日本時間から時差 Q (17時間) を引く
 - 「時」 = A - Q ( = C とおく)
  但し、A - Q の結果が 0 未満になる場合は、24を足す (この場合は日付が変わる)
  プログラムは、
   A-Q→C
   C<0⇒C+24→C

  
となる。
 - 「分」 = B
 - 時間: U = 100C + B
  プログラムは、
   100C+B→U
  
となる。

日本時間が 7:00 の時、ドイツは時差8時間なので、「時」から 8 を引き算するのですが、7 - 8 = -1 となります。これは前日の 23:00 である筈なので、7 に 24 を足した上で、8 を引けば 23 が得られます。

日本時間が 7:00 の時、LAでは 前日の 14:00 ですが、7 から時差の 17 を引くと、-10 となってしまうので、上と同様にして、一旦 24 を足してから 10 を引く計算をします。

これが、C<0⇒C+24→C とした理由です。

以上のようにして、J (日本時間)、G (ドイツ時間)、U (LA時間) を計算できるようになりました。これをまとめておきます。

メインルーチン TZ:日本、ドイツ、LAの時間を計算するプログラム
If M=0:Then
A≧24⇒A-24→A
100A+B→J
A-P→C
C<0⇒C+24→C
100C+B→G
A-Q→C
C<0⇒C+24→C
100C+B→U

Prog "TZD"
IfEnd



4.得られた時間を更新表示

時間を更新表示する部分は、何度も繰り返し使うので、サブルーチンにします。

ファイル名: TZD
表示 = Display なので、TZ + D から TZD としました。

先ずは、以下のプログラムが出発点です。

Locate 8,1,J
Locate 8,2,G
Locate 8,3,U


ここで、J は日本時間、G はドイツ時間、U はLA時間です。


時間の変数 J、G、U には、4桁だけでなく、3桁や 2桁、さらに1桁の場合もあります。一方で、大まかな方針で決めたように、表示は必要なら頭に 0 を加えて、必ず4桁の表示にします。

そこで、一旦 0000 と表示したところに、上書きして時間を表示します。

サブルーチン TZD のプログラム
Locate 8,1, "0000"
Locate 8,1,J
Locate 8,2,"0000"
Locate 8,2,G
Locate 8,3,"0000"
Locate 8,3,U



一旦、ここまでで メインルーチンTZのプログラムをまとめてみます。

メインルーチンTZ のプログラム
8→P:17→Q
Prog "TZM"

While 1

-1→M
Do
Getkey→K
LpWhile K=0
K=25⇒0→M

If M=0:Then
8→X:1→Y:4→D:1→E
Prog "INPI"
Prog "TZC"
X→A:Y→B:Z→J
IfEnd

If M=0:Then
A≧24⇒A-24→A
100A+B→J
A-P→C
C<0⇒C+24→C
100C+B→G
A-Q→C
C<0⇒C+24→C
100C+B→U
IfEnd

Prog "TZD"

WhileEnd



これを実行してみます。

日本時間を 8:04 にするとき、804 と3桁を入力してみると、以下のような表示になりました。

36-TZ1_wrong_time  

本来は、以下の表示になるべきなので、プログラムに問題があります。

0:JST      0804
1:CET     0004
2:PST     1504
<AC>:QUIT


日本時間の変数 J には 804 が、ドイツ時間の変数 G には 4 が、LA時間の変数 U には 1504 が入っています。
従って、
 ・Locate 8,1,J 804 を8桁目から表示
 ・Locate 8,2,G4 を8桁目から表示
しているので、おかしくなります。

Locate 8,3,U
は、変数 U に入っている4桁の数 1504 を表示するので、たまたま問題ない、と言うことが分かります。

そこで Locate コマンドでは、
 ・表示する数が、1桁の場合は、11桁目から表示
 ・表示する数が、2桁の場合は、10桁目から表示
 ・表示する数が、3桁の場合は、9桁目から表示
 ・表示する数が、4桁の場合は、8桁目から表示

となるようにすれば良いことが分かります。

そこで、変数 JGU の桁数が分かれば、それぞれ

 ・Locate 12-[J の桁数],1,J
 ・Locate 12-[G の桁数],2,G
 ・
Locate 12-[U の桁数],3,U

に変更できれば、うまくゆきます。あとは、数の桁数を知る方法があれば、問題解決です。

・・・・・・・・・・

いきなり解決策を提示します。
J に入っている数の桁数は、下記の式で求められます。

1+Int(log(J))

これは、自分のプログラムで多用しており、非常に便利なものです。この式について、詳しくは以下を参考にしてください。

Casio Basic入門: Locate

fx-5800P: Locate【桁数のコントロール】


これで、Locate で正しく時間を表示できるようになりました。

Locate 8,1,"0000"
Locate 11-Int(log(J)),1,J
Locate 8,2,"0000"
Locate 11-Int(log(G)),2,G
Locate 8,3,"0000"
Locate 11-Int(log(U)),3,U


但し、このままですと、日本時間を 0:00 にするために、0 を入力するとエラーが発生します。

実は、対数関数 log( ) を使う際の非常に重要なポイントを忘れていたからです。

対数関数 log( ) は、( ) の中の数は正の数でなければなりません。これは fx-5800P 固有の問題ではなくて、対数関数の定義です。時間は 0:00 となることがあり、日本時間の変数 J は、0:00 にするために、0 と入力すれば、0 になることがあります。日本時間が 8:00 の時は、ドイツ時間は 0:00 となり、ドイツ時間の変数 G の値は 0 になります。

幸いなことに、上の時間表示のソースでは、先ず最初に 0000 と表示してから、Locate コマンドで時間を上書きするようになっているので、時間の変数が 0 の時は、上書き表示を行わないようにすれば 0000 の表示のままで、00:00 を示します。

そこで、J が 0 でない時に時間表示を行うようにします。

例えば、Locate 11-Int(log(J)),1,J を

If J≠0:Then
Locate 11-Int(log(J)),1,J
IfEnd


とすれば良いわけです。

If 文の条件判定は、その条件が「真」なら Then 以下の処理を実行し、「真」でない( = 「偽」) ならば実行しないとなっています。

そこで、以下のようにしても良いですね。

If J:Then
Locate 11-Int(log(J)),1,J
IfEnd


「真」とは、J0 でないことで、J0 だと「偽」となります。


この3行の処理を、以下のように、スッキリと1行に記述することもできます。

J⇒Locate 11-Intlog(J)),1,J

条件ジャンプ命令 ⇒ を使っています。実は、上の If 文よりも ⇒ 命令の方が、処理速度が少し速くなります。

そこで、今回は ⇒命令を使ったコードを採用します。


If 文や ⇒命令について、詳しくは以下を参考にしてください。

Casio Basic コマンドリファレンス: If ~ then ~ IfEnd

Casio Basic コマンドリファレンス: ⇒ 命令 (条件ジャンプ)


そこで、TZD は以下のようになります。

サブルーチン TZD のプログラム
Locate 8,1,"0000"
J⇒Locate 11-Int(log(J)),1,J
Locate 8,2,"0000"
G⇒Locate 11-Int(log(G)),2,G
Locate 8,3,"0000"
U⇒Locate 11-Int(log(U)),3,U


では、変更した TZD の動作確認のために、TZ を起動し、[0] キーを押して日本時間として 804 と入力してみます。
以下のように、目標通りに表示することを確認できました。

37-TZ1_correct_time 


log(J) は、J が正の数の時のみ正しく計算します。J が負の数の時はエラーとなります。
上のソースでは、J が 0 でない時に Locate 11-Int(log(J)),1,J を実行するようにしました。

J⇒Locate 11-Int(log(J)),1,J

対数関数 log( ) の定義では、J>0 とすべきです。これを具体的に書けば、

If J>0:Then
Locate 11-Intlog(J)),1,J
IfEnd


とすべきです。すでに、気付いて、オカシイと思われた方もいらっしゃるでしょう。


大きなうっかりミス

INPI は、負の数を扱わない仕様なので、INPI で入力すれば必ず 0 か正の数が得られます。プログラム上 J が負になる可能性はゼロです。

上の If J>0 を使ったソースのままで、もし万一 J が負になる場合は、表示が 0000 のままになります。エラーが出ずに、間違った結果を表示することになり、このバグに気付かないかも知れません。

従って、プログラム上は、絶対に J が負にならないが、他の理由で J が負いなることがあるかどうか?
もしあれば、その原因を最初から潰す必要があります。

・・・・・・・


正直に言えば、私は当初 J が負になるケースを全く想定していませんでした。でも、何度か使っているうちに、Argument ERROR (引数エラー) が発生し、問題に気付きました。うっかりしていました。

J が負になる可能性が、1つ残っていました。

電卓で他のプログラムを走らせたり、何か計算を行っている時に、J に負の数が入る可能性があります。しかし、本プログラムが起動した直後は J の値は決まっていません。と言うのも J が初期化されていないからです。

J が 0 の時は、上記のサブルーチン:TZD で対数関数 log( ) を使う時の対処で、 問題に対処できています。
プログラムが起動する前に J に負の数が入っている可能性を取り除くには、初期化処理において J を 0 で初期化します。

0→J

を、初期化処理に追加することにします。


使う変数は、できるだけ初期化してその値を確定しておくのが安全だと、再認識しました。



ここまでで、作ったプログラムは、以下の通り:

メインルーチン TZ のプログラム
9→P:17→Q
0→J
Prog "TZM"

While 1

-1→M
Do
Getkey→K
LpWhile K=0
K=25⇒0→M

If M=0:Then
8→X:1→Y:4→D:1→E
Prog "INPI"
Prog "TZC"
X→A:Y→B:Z→J
IfEnd

If M=0:Then
A≧24⇒A-24→A
100A+B→J
A-P→C
C<0⇒C+24→C
100C+B→G
A-Q→C
C<0⇒C+24→C
100C+B→U
Prog "TZD"
IfEnd

WhileEnd




サブルーチン:TZM のプログラム (メイン画面表示)
Locate 1,1, "0:JST"
Locate 1,2,"1:CET"
Locate 1,3,"2:PST"
Locate 1,4,"<AC>:QUIT"




サブルーチン:TZC のプログラム (時間を「時」と「分」に分離)

If Z<100:Then
Z→X:0→Y
Else
Int(Z÷100)→X
Z-100X→Y
IfEnd




サブルーチン TZD のプログラム (時間の表示)
Locate 8,1,"0000"
J⇒Locate 11-Int(log(J)),1,J
Locate 8,2,"0000"
G⇒Locate 11-Int(log(G)),2,G
Locate 8,3,"0000"
U⇒Locate 11-Int(log(U)),3,U





今回は、日本時間を入力したら、ドイツ時間とLA時間が表示されるところまで、作りました。
次回は、ドイツ時間やLA時間を入力した時の処理も追加してゆきます。



つづく...


Casio Basic入門25 / 目次




応援クリックをお願いします。励みになるので...

人気ブログランキングへ


FC2ブログランキングへ



カシオプログラム関数電卓 FX-5800P-N カシオプログラム関数電卓 FX-5800P-N
(2006/09/22)
CASIO(カシオ)

商品詳細を見る



keywords: fx-5800PCasioBasic、世界時間換算, プログラミング入門プログラム関数電卓

リンク集 | ブログ内マップ


関連記事

テーマ : プログラム関数電卓
ジャンル : コンピュータ

コメントの投稿

非公開コメント

最新記事
最新コメント
カテゴリ
C# (3)
検索フォーム
Visitors
Online Counter
現在の閲覧者数:
プロフィール

やす (Krtyski)

Author:やす (Krtyski)
since Oct 30, 2013


プログラム関数電卓は、プログラムを作り・使ってナンボ!

実際に触って気づいたこと、自作プログラム、電卓プログラミングについて書いています

おもしろい・役に立つならクリックしてください。励みになります。

人気ブログランキングへ


FC2ブログランキングへ


写真: 「4駆で泥んこ遊び@オックスフォード郊外」

リンク
月別アーカイブ
Sitemap

全ての記事を表示する

RSSリンクの表示
最新トラックバック
ブロとも申請フォーム

この人とブロともになる

QRコード
QR