program sample(input, output); begin writeln('Hi'); end.も
program sample(input, output); begin writeln('Hi'); end.も全く同じ意味である。しかし、
pro gram sample(input, output); begin write ln('Hi'); end.は文法エラーになる。 (pro と gram の間、 write と ln の間にスペースが 入っているため)。
PASCAL のプログラムは、すべて、以下のような構造を持つ。
program プログラム名(ファイル名, ... ,ファイル名); 宣言部 実行文部.
その後の () とその中のファイル名何とかは、 ここのシステムのPascalの場合は指定し
なくてもいい。慣習により、 (input,output) と書いておくのが普通である。
つまり、
program sample;
と書いても、
program sample(input,output);
と書いても、プログラムの動きにかわりはない。
定数宣言部 型宣言部 変数宣言部 手続き・関数宣言部
という形をしている。定数名は、プログラム名と同じような、英字から始まる
文字列である。値は、整数、実数、あるいは文字列定数である。この宣言があ
ると、「値」が必要なところで、「定数名」を書いて済ませることができる。
例えば、
const pi =3.1415926535;
と書いてあれば、以下のプログラムでいちいち 3.1415926535 と書かなくても
pi と書けば済む。
レコード型を使う場合、型宣言部は必須である。というのは、レコード型は、
もともとあるものではなくてこちらで作るものだからである。レコード型の宣
言は以下のような形をしている。
type 型名 = record
フィールド名 : 型;
......
フィールド名 : 型
end;
型表記は、 integer, real, longint のような単純型、 「 array [start..end] of 型表記」という形の配列、レコード型 の型名などが使える。
プログラム先頭で宣言してある変数は、メインプログラムと手続き、関数のど ちらでも使える(同じものである)。
var i : integer; とすれば、 i は整数型の変数で、 -32768 から 32767 までの数を扱える。
var x : real; とすれば、 x は実数型である。
var data : array [1..100] of real; とすれば、 data は実数変数 100 個からなる配列である。
var mat : array [1..100,1..100] of real; とすれば、 data は実数変数 10000 個からなる2次元配列である。 (mat[1,1] から mat[100,100]まで)
手続き頭部は
procedure 手続き名(仮引数; .... ; 仮引数);
関数頭部は
function 手続き名(仮引数; .... ; 仮引数) : 型表記;
の形をしている。
仮引数は 引数名 : 型表記 または var 引数名 : 型表記 の形をして いる。
例えば procedure print(n:integer); は、print という手続きが n という整 数型の引数 1 つをとるという宣言になる。実行部でこの手続きを呼び出すに は、例えば print(5) とかすればいい。なお、実行部で呼び出す時には、 5 のかわりに整数型の変数とか値が整数である式も書ける。例えば i,j が整数型 変数なら、 print(i)とかprint(i+j) とかできる。
function cube(x:real):real; とかすると、これは、 cube が実数の引数 1 つをとって実数を帰す関数であると宣言したことになる。実行部では、例えば y := cube(x); と単純に代入する、あるいは y := cube(x)*z; とかいったよ うに、式の中で使うことができる。
さて、宣言部であるが、宣言部の説明は 上の宣言部のところそのものである。 つまり、ここにも、また定数宣言部、型宣言部、変数宣言部、手続き・関数宣 言部といったものを書くことができる。ここで宣言したものは、プログラム先 頭で宣言したものと違い、この手続き(または関数)の中でしか使えない。こ の辺の事情は教科書 を参照のこと。
実行文部も、形式はプログラム本体の実行文部と全く同じである。
代入文は 変数 := 式 または 関数名 := 式
関数名 := 式 の形は、関数宣言部のなかの実行文部でだけ出てくる。
変数は、変数名または添字つき変数(配列要素)またはフィールド指定子であ る。
変数名は、変数宣言部で宣言した名前である。
添字つき変数は 配列変数[式, ... ] の形をしたもので、配列変数は array of 何とかと宣言した変数名である。[]の中の式は整数式である。 式の数は、宣言した数とあっている必要がある。
フィールド指定子は、レコード変数.フィールド名 という形のものである。
式はめんどくさいので後で述べる。
手続き文は 手続き名; または 手続き名(実引数, ... , 実引数); という形を している。仮引数がない手続きでは前者の形、あれば後者の形をとる。実引数 の型は、対応する位置にある仮引数の型と同じでないといけない。
複文は以下の形をしている。 begin 文; 文; ... ;文 end
条件文は以下の形をしている if 論理式 then 文 または if 論理式 then 文 else 文
ちょっと注意して欲しいのは、ここで「文」は構造化文でもいいということで ある。つまり、 then や else のあとに来る文は複文、条件文、 あるいは繰り返し文でも構わない。論理式の値が真なら then の次の 文が実行され、偽なら、 else があればその後の文が実行される。なけ れば何も起きない。
繰り返し文は for 文、 while 文、 repeat 文のいずれか である
for文は以下の形をしている。 for 制御変数 := 最初の値 to 最後の値 do 文;
制御変数は整数型の変数でないといけない。まず制御変数に最初の値を代入し、 文を実行する。次に制御変数に1を加え、また文を実行する。制御変数が最後 の値になったら、また文を実行する。これで終りである。もし最初の値が最後 の値よりも大きいと、文は一度も実行されない。また、文が実行されたかどう かに無関係に、 for 文の実行が終ったあとの制御変数の値はどうなって いるかわからない。
while 文は以下の形をしている。
while 論理式 do 文;
まず論理式の値を計算し、真であったら文を実行する。実行が終ったらまた論 理式の値を計算し、真であったら文をもう一度実行する。論理式が真でなくな るまでこれを繰り返す。
repeat 文は以下の形をしている。
repeat 文; .... ;文 until 論理式 ;
まず repeat と untilの間の文; .... ;文を実行する。実行が終ったら論 理式の値を計算し、偽であったら文; .... ;文をもう一度実行する。論理式が 真にな るまでこれを繰り返す。 while文との違いは、必ず1度は実行されるとい うことである。
単純式でない式は以下の形をしている
単純式 関係演算子 単純式関係演算子には以下のものがある
演算子 意味 = 等しい <> 等しくない < より小さい <= より小さいか等しい > より大きい >= より大きいか等しい単純式は以下の形をしている
[+/-] 項 または [+/-] 項 加算演算子 項加算演算子には以下のものがある
演算子 意味 + 加算 - 減算 or 論理和項は以下の形をしている
項 または 因子 乗算演算子 因子乗算演算子には以下のものがある
演算子 意味 * 乗算 / 実数除算 div 整数除算 mod 剰余 and 論理積因子は以下の形をしている
符号なし定数 または 変数 または 関数名 または 関数名(引数、、、) または (式) または not 因子注:ここで、 (式)というのは「括弧のなかに式がある」ものである。
...... というのが、PASCAL の文法定義にそった式の構文規則なのだが、これ では全くなんだかわからないに違いないので、ちょっと補足。
上で、「因子」とか「項」とか「単純式」とかいったなんだかわからないもの が定義されているのは、演算子の優先順位を決めるためである。つまり、たと えば 1 + 2 * 3 > y + g(x)/f(x) と書いた時に、これは (1 + (2 * 3)) > (y + (g(x)/f(x))) と解釈されることになる。これ は、式が上のように定義されているからである。
もう少し普通にいうと、演算子の優先順位は 関係演算子、加算演算子、乗算演算子、 not の順で高くなるというこ とである。
1 2 3 4 5 6 7 8というデータファイルがあったとき、 readln(infile,a); readln(infile,b) とすれば、a, b の中身はそれぞれ行の 先頭の 1 と 5 であるが、 read(a); read(b) なら b には 2 が入る。