CindyScript の全般的仕様
この節は、 CindyScript の最も基本的な概念をおおまかに説明します。
CindyScriptは関数型プログラミング言語
CindyScript のすべての計算は関数によって行われます。「関数」とは、引数を与えるとなんらかの計算をして値を返すものと考えてよいでしょう。いろいろな計算は、基本的な関数によってなされます。また、通常の計算のように a+b のようにして計算をすることもできます。この場合、「+」は演算子と呼ばれますが、CindyScriptでは、これを挿入演算子と呼んでいます。同じ計算が、add(a,b) によってもできます。こちらは関数です。そこで、このマニュアルでは、「演算子」と「関数」をほぼ同義なものとして使っています。つまり、add(a,b)のような関数も「演算子」と呼ぶことがあります。
次のコードは、1から10までの整数の和を計算します。
ここで、 .. には、2つの整数 a と b に対して a から b までの整数のリストを出力する機能があります。つまり、 1..10 によって、10個の整数: [1,2,3,4,5,6,7,8,9,10] を生成します。 sum(_) 関数は、単変数関数です。 (1個の引数を与えます)。1つの数のリストを入力として引数に与えると、リストの内容の合計を出力します。したがって、コマンドシェルに sum(1..10) と打ち込むと、関数は結果として 55 を返してきます。
さらに、 if 文のような一見手続き風の命令文が、関数として認識されます。例えば、
if(x<y,print("Mine"),print("Yours"))
という文は、3つの引数を持つ if 関数の例です。第1の引数 x の条件を評価し、その結果により第2または第3の結果 print("Mine") または print("Yours")) を実行します。それが if(_,_,_) 関数の実行結果です。したがって、これは次の命令文と同じです。
print(if(x<y,"Mine","Yours"))
条件の評価結果により if 関数は第2または第3の引数の値を返します。
副作用
関数が CindyScript で評価されるということは、 "副作用" があるかもしれないということです。副作用は、CindyScript のプログラムとシンデレラで作成したものとのいろいろな相互作用にとって重要です。典型的な副作用は次のものです。
例えば、
という命令は、位置 (0,0) に点を打つという副作用があります。
では、点 A の色を ''白" に設定します。
プログラムの流れ
多くのユーザーは、C, Java, Pascal, Basic といった手続き型言語に慣れているでしょう。実際には、CindyScript でプログラムを書くというのはこれらの言語とそれほど違いはありません。 CindyScript では、演算子 ; (セミコロン)を許可しますが、<statement1>;<statement2> では、まず 命令1 を評価し次に 命令2 を評価します。 ; 演算子は、最後の文の結果を出力します。手続き的なプログラムを書くのは比較的簡単で、手続き型言語で書くのとよく似ています。 例えば、次のようなプログラムで、放物線状に9つの点を描きます。
repeat(9,i,
j=i*i;
draw([i,j]);
)
関数 repeat(<number>,<variable>,<program>)
は、プログラムを number 回繰り返します。それぞれの回で、変数 <variable> の値が増加します。 (最初は 1) 繰り返す内容は、 j=i*i; draw([i,j]); の2つの行です。
型の非明示
CindyScript は、文法を最小限にし、関数の働きを最大限にするようにデザインされています。従って、CindyScript は値の型を明示しません。他の言語のように CindyScriptにも variablesの概念があります。しかし、他の言語と対照的に、変数は特定の型を持ちません。どんな型のどんな値でも変数に代入することができます。これはプログラマに、強力なコードを生み出す多くの自由を与えます。 例えば、関数f(x,y) を定義する次のコード
は、整数、複素数、ベクトル、行列のいずれでも使えます。この自由は、一方では、意味がはっきりとわかるようなコードを書くことをプログラマに義務づけます。関数が意味不明なことをすると、プログラムは正しく動きません。そのかわり、「意味がない」ことを表す ___ 印を返します。したがって、上の例で、f([1,2],[3,4]) ならばベクトルの和として [4,6] を返しますが、 f(4,[3,4]) では意味がなく、 ___を返します。
局所変数: 変数#
繰り返し構造に似たものが CindyScript にはいくつかあります。例えば、演算 select(<list>,<condition>) は <list> のすべての要素を走査し、条件に合うものを返します。このため、条件を試すような要素がなければなりません。CindyScript では、このために実行用変数として、初期状態では #を使います。例えば、
という命令では、 1 から 30までのすべての奇数のリストを返します。さらに、この実行用変数を繰り返し使って
とすれば、1 から 9までのすべての数を表示します。2番目の引数として、明確な変数を使うことも可能です。したがって. select(1..30,i,isodd(i)) と repeat(9,i,print(i)) は上の命令文と同じ意味になります。
CindyScript のデータ型
すでに述べたように、 CindyScript は変数の型を明示しません。しかしながら、いくつかの変数の値は明確な型を持ちます。 CindyScript の基本的な型は次の通りです。
- <number>: 数値。整数、実数、複素数のいずれか。
- <list>: 任意の値のリスト。ベクトルや行列はリストで表されます。
- <string>: 文字列
- <geo>: 幾何学的要素
- <boolean>:
true または false のブール値
数値の型は、整数、浮動小数点数、複素数を含みます。
変数とその適用範囲
CindyScript は変数の型を明示的にもたないので、変数は必要に応じて "その場" で作られます。変数は最初に割り当てられるときに作られます。もし x がまだ使われていなければ、
という文は変数 x を作り、値 7 を割り当てます。値が割り当てられると、残りのプログラムを実行中にアクセス可能になります。 値は、関数の局所変数として部分的に多重定義されるかも知れません。次の関数の定義では x と y の値は関数の局所変数です。
関数の実行が完了すると x の元の値が戻されます。また、 createvar(...) 演算子によって局所変数を作ることもできます。
幾何学的要素とその属性へのアクセス
変数は幾何学的要素を操作するためにも用いられます。それらにより、シンデレラとCindyLab が CindyScript にリンクします。変数が幾何学的要素と同じ名前を持つと、その幾何学的要素とリンクします。変数の値は明示的な割り当てによって多重定義させることができます。幾何学的要素の異なる属性 (位置、色、大きさなど) は . 演算子によってアクセス可能です。もし A が点であれば A.size という文は点の大きさを表す整数を返します。 A.xy=[3,4] という文は、点の座標を [3,4] にします。さらに、物理シミュレーションに関する属性 (質量、速度、運動エネルギーなど)も . 演算子によってアクセス可能です。
修飾子
CindyScript の演算子は、一見したところ気がつかないような多くの機能を持ちます。通常、これらの機能は修飾子と呼ばれるものによってアクセスできます。演算子は、初期状態で大部分の状況に適合するように定義されています。しかしながら、初期状態の振舞いを変更する必要があるかも知れません。そこで、必要な修飾子を演算子を呼び出すときに書き並べます。例えば、
という行は、位置 (0,0) に点を描きます。初期状態では色は緑、大きさは3です。
draw([0,0],size->15,color->[1,1,0])
という行では、黄色の点を大きさ15で描きます。size->やcolor->が修飾子です。修飾子は、コンマで区切ります。それらの順序は自由です。
リスト/ベクトル/行列
CindyScriptの基本的なデータ型に リスト があります。リストは、複雑なデータ構造を定義するのに用いられる基本的な仕組みです。ものを列挙するという明らかな利用法に加えて、リストはベクトルや行列を意味するのにも用いられます。ベクトルは数のリストです。同じ長さを持つベクトルのリストは行列であると解釈されます。CindyScript は通常の計算をベクトル、行列、数値に統合的に用います。 a と b の内容に応じて、式 a*b は、数のかけ算であったり、行列のかけ算であったり、行列とベクトルのかけ算であったりします。
CindyScript では、列ベクトルと行ベクトルの区別がありません。しかし、適当な関数を用いて、長さ n のベクトルを (n × 1) 行列、または (1 × n) 行列に変換することができます。
描画
CindyScript には幾何のキャンバスに直接図を描くことのできるいくつかの命令があります。この特徴を用いると、シンデレラで作ったものの動きをかなり豊かにすることができます。点、直線、線分、多角形、表、関数のグラフなどを描くことができます。しかし、幾何で使用しているものと、スクリプトで描いたものを混同しないことが大切です。スクリプトで描いたものをシンデレラで描いたもののように扱うことはできません。例えば、「動かすモード」で動かすことはできません。
もし、スクリプトで描かれたものを修正したいのであれば、まず先にCinderellaの描画ツールでそれを作っておいてCindyScript の命令で位置を変えるようにする必要があります。すべての自由な要素はその位置を表す変数をセットすることで動かせます。
スロット
CindyScript のコードを入力するスクリプトウィンドウは、テキストが入力できる次のようないくつかのスロットがあります。(スロットとは、棚のようなものです。スロットの概念はCindyScriptの大きな特徴です。)
- Draw
- Move
- Initialization
- Timer Tick
- Simulation Start
- Simulation Stop
- …
これらのスロットは、スクリプトが実行する場面と一致します。たとえば Drawスロットは、画面が新しくなる前に直接実行されます。 Initializationスロットは、CindyScript のコードが解釈されたあと直ちに一度だけ実行されます。 Simulation Start スロットはプレイボタンが押されたとき、アニメーションを始める前に実行されます。このメカニズムを使うと、ユーザーの要求にうまく対応するプログラムを書くことができます。
実行エラー処理
CindyScript はプログラム実行環境で動作します。原則として、どんな小さな動きでもスクリプトが評価されます。そのため、実行時にエラーが起きた場合の合理的な設計がなされていなければなりません。通常の操作エラーメッセージが頻繁に出て、そのたびに中断するのでは(特にHTMLページのアプレットで使うときに)困ります。そのため、CindyScript では、最初の10個のエラーだけを報告するようになっています。しかし、ランタイムエラーは決して実行を中断しません。また、ゼロで割る、存在しない配列へのアクセスなどのランタイムエラーは単に無視されます。誤った関数の評価は単に未定義と見なされ、計算は続行されます。(おそらく、さらに未定義となる結果を引き起こすでしょうが。) これにより、エラーが起きても円滑な実行が保証されます。
ランタイムエラーが報告されないというこの特徴は、デバッグを多少厄介にするかもしれません。そのため、あるデータについての仮定が満たされるかどうかを調べる特殊関数 assert(<boolean>,<string>) が導入されました。もし、第1引数の条件が満たされなければ、第2引数の文字列が印字されます。
Contributors to this page: Akira Iritani
.
Page last modified on Monday 05 of March, 2012 [12:04:00 UTC] by Akira Iritani.
The content on this page is licensed under the terms of the License.
|
|