![見出し画像](https://assets.st-note.com/production/uploads/images/84135258/rectangle_large_type_2_3fa08fc57790de09f01ef6092e05714a.jpeg?width=1200)
シーケンシャルかランダムか
I/Oデバイスには、シリアルとランダムがあり、デバドラを書くときは、この2つの書き方をおさえておけば間に合います。ディスクはデバイスとしてはランダムアクセスデバイスですが、ファイルとしてアクセスする場合は、シーケンシャルとランダムの両方での手段が提供されています。
今のOSでは、シーケンシャルといってもテキストとして扱うか、バイナリとして扱うかによって挙動に違いがありますし、ランダムと言っても、先頭からの位置をバイト単位で指定するか、固定長ブロック構造を仮定してレコード単位で指定するかの方法があります。また、面倒なのが既存のファイルサイズを超えてアクセスする場合で、OSによってかなり挙動が異なります。
今回はAppleDOSの話に絞りましょう(MS-DOSやUNIXなんかは別の機会に)。AppleDOSのファイル属性にはテキストとバイナリしかありません。まずはテキストファイルから確認していきましょう。
テキストファイルを作るには、
OPEN TEXT1
WRITE TEXT1
の2つのDOSコマンドを実行すると、その後
CLOSE TEXT1
までに実行されたPRINT文の出力がディスクに書き出されます。
作ったファイルを読むには
OPEN TEXT1
READ TEXT1
として、INPUTまたはGET文を実行して変数に読み込みます。INPUTで改行までの文字列を読み込むのですが、改行自身と”,”はセパレータに使われているので、読み込めません。読み終えたら
CLOSE TEXT1
です。
最後まで読んだことがわかる仕組みはありません。読んでみて値が$00だと”END OF DATA”というエラーが出るので、これをON ERROR GOTO文で拾います(これを有効に機能させるためには、DOSは隙間を0で埋めるようにしています)。ディスクの読み書きは、いつ”I/O ERROR”が出ても不思議はないので、必ずエラー処理を仕込んでおくものです。
ファイルに内容を追加するには、WRITEの代わりにAPPENDを実行してから、PRINT文で追加します。
基本的には、これだけです。
ファイルハンドルという考え方はありません。入力と出力がそれぞれひとつのファイルに結び付けられるだけです。ファイルを開いたまま入力と出力を切り替えることはできますが、同時に複数のファイルに書き出すことはできなかったハズです。
オプション機能として、WRITEおよびREADにはBオプションがあって、読み書きを始める先頭からのバイト位置を指定することが出来ます。B0であれば指定しないのと同じことになります。なおBオプションで使えるのが32767までの正の値なので、テキストファイルは基本的には32Kまでのサイズに制限されます(ファイルサイズがこれを超えてもエラーにはならなかったかも)。
POSITIONという命令で、読み書きの途中でバイト位置をスキップする命令があるのですが、便利な使い方をした覚えがないので動作は忘れました。指定したバイト数だけ読み書き位置を後ろにできるようです。相対値を指定するので、R0だと何もしないのと同じです。正の値しか指定できないので戻ることはできません。
さてさて、ここまでは普通のテキストファイルでしたが、テキストファイルを固定長のレコードからなるファイルとみなしてアクセスする方法もあります。ファイルを開く際に、Lオプションでレコードのバイト数を指定します。
OPEN RANDOM1,L64
この方法で開いたファイルを読み書きするときには、
READ RANDOM1,R4
とすれば、64×4の256バイト目から読み込みます。WRITEも同様です。レコードごとにファイルがあるかのような動作をするので、Bオプションも併用することが出来ます。
READ RANDOM1,R2,B16
とすれば、2つめのレコードの16バイト目、すなわち先頭から144バイト目から読み出すことになります。
いずれにせよBASIC側の入力はINPUTかGETなので、レコード長を指定しても読み書きの位置を指定するだけで、読み書きする変数の長さが指定されるわけではありません。さらにレコード長を超えて読み書きしても、そのままファイル位置が動いていくだけでエラーにはならなかったと思います。
なお、この方法でファイル書き込み位置がファイルの長さよりも長い場所に書き込んだ場合、そこまでのファイルには0が埋められるようになっていたはずです。ちゃんと0で埋めているので、読み出した時に0を見つけて”END OF DATA”にすることができるのです。ただGETで読むとNULLは読めちゃったような気もするんですよね。
さてさてファイルにはテキストファイル以外に、2つのBASICプログラムファイルとバイナリファイルがあるのですが、こちらは部分的に読み書きすることはなくて、
LOAD
SAVE
BLOAD
BSAVE
で、まとめて読み書きするだけです。また
RUN
CHAIN
BRUN
で読み込んだ後に実行することも指定できます(CHAINは変数の値を保ったまま、メモリにあるプログラムをクリアして指定されたプログラムを実行します)。
バイナリファイルは基本的には書き込んだときのアドレスに読み込まれるのですが、オプションで好きな場所に読むこともできます。
面白いのは、これらはDOSコマンドであってBASICではないので、オプションで$で始まる16進数が使えることです。AppleのBASICでは数値に16進数を扱う機能はついていないので、A=$200などはできないのですが、DOSコマンドでは BLOAD BINARY1,A$2000 などと16進が使えるのですね。
そういえばファイル名を指定する時に引用符で括られていないことに気が付きました?ファイル名もDOSコマンドの一部で、DOSコマンド自身がBASICからみたら文字列に過ぎないのですから。このあたりが他のDISK BASICと違うので違和感を持つ人もいると思います。
そのへんの話は
にも書いたので、そちらもお読みください。
ここまで来たら、次は、このファイルをどのようにディスクにしまっているのかの話ができますね。
いいなと思ったら応援しよう!
![kzn](https://assets.st-note.com/production/uploads/images/111925158/profile_dffba6e25229ee04f46397fb91bbfc20.jpg?width=600&crop=1:1,smart)