DOSEIの日記

技術メモ+日常ログ

An Original Language (0)

自作言語が作りたい。いろいろアイディアは暖めてあるので、そろそろ本気で作り出そうかと考え中。まずは、チョコチョコメモしていく。

まず、一番初めに考えたコンセプト、もしくはパラダイムは、コンテキスト・リファレンス方式(勝手に命名)。オブジェクト指向言語で、すべてのオブジェクトは、リファレンス(参照)で繋がれている。そして、オブジェクト間のみならず、プログラムの実行コンテキスト(文脈)にもリファレンスで繋がれてる。って、ぜんぜん意図が表現できてないか。

つまり、プログラム実行のどの瞬間にも、そのシステムが何か参照をつかんでいる。たとえば、普通のC++言語では、メンバ関数を使うのに

anyobject.anyfunction()

となるわけだ。ここで、"."はanyobjectのメンバを参照する演算子である。しかし、今考えてる言語では、オブジェクト名に演算子を書くのではなく、その瞬間のコンテキスト参照にたいして、メンバの参照が行われる。たとえばメソッドの実行を":"で表わすとすると

:function

である。このとき、どのオブジェクトに対してなのかは、それまで実行してきた過程で最終的にシステムが参照したオブジェクトである。これをコンテキストリファレンス(単にコンテキスト)と呼ぶ。
コンテキストリファレンスを変更するには、プロパティを参照するか、明示的に参照を変更するか、新しいオブジェクトを生成したときのいずれか。参照を保持する変数のようなものがあるとして、これをリファラと呼ぶとする。リファラが保存している参照にコンテキストを変更するには

@referer

とかくとする。たとえば、あるオブジェクトを指すリファラaがあって、そのオブジェクトのメソッドmethod1を実行するには

@a :method1

とする。メソッドの実行ではコンテキストは変更されないので、

@a :method1 :method2 :method3 :method4

のように、連続的に書ける。永続的に続くwith構文だと思ってもいいかも。
メソッドは、引数を取ることもある。引数の話は、また後で。しかし、返り値はない。PASCALのPROCEDUREと同じ。
オブジェクトは、1つ以上の参照によって束縛されている間存続する。つまり、すべての参照がなくなった場合、自動的に解放される(ただし、解放されるタイミングは規定しない。残ったままでもいいし、すぐに解放してもいい。キューでタイミングを見計らって処理してもいい。実装依存)。コンテキストも参照の一種なので、コンテキストで縛られてる間は少なくとも解放はされない。
オブジェクトはプロパティと呼ばれる参照リストを持っている。プロパティで参照されているオブジェクトが、今のオブジェクトの性質を保持している。何かメソッドによって変更された性質は、プロパティを参照することで確認できる。プロパティを使うとは、単にコンテキストを変更する意味合いでしかない。指定したプロパティにコンテキストを移動して、それを処理するという流れを作る。
プロパティ参照は"."で表わす。プロパティが参照された時点でカレントコンテキストはそのプロパティ参照に変更される。たとえば、windowsアプリを作ってるような場面を想定して、

@textbox1 .text :clear

とか。あんまりわかりやすい例じゃないけど。
さて、コンテキストをスタック構造によって、入れ子に記憶できる。たとえば、コンテキストを変更した後、元に戻す必要かある場合、

@window1
{
  .canvas :clear
}
:show

って感じ。"{}"の前後で同じコンテキストになる。
コンテキスト参照を明示的に解放したい場合もあるかもしれない。そのときは、";"で、指定する。このときコンテキストはデフォルトコンテキストに変更される。メソッド定義の中だったら、そのメソッドを持つオブジェクトがデフォルトコンテキスト、"{}"で入れ子のときは、一番近い外側のコンテキスト。

@obj1
{
  .prop1 .subprop :submethod ;
  .prop2 :method2
}
:method

オブジェクトの生成は、"[]"で表わそう。初期化とかあんまり考えてないけどとりあえず。あと、現在のコンテキストをリファラに保存するのは"="、リファラを忘れるには"!"にしよう。この2つではカレントコンテキストは変更されない。

[window] =w1 :title("New Window") :size( (0,0,150,80) ) :show
[window] =w2 :title("Next Window") :size( (20,40,100,40) ) :show
!w1
!w2 ;

1行目ではwindowオブジェクトが作られ、リファラw1に参照されて、3つメソッドが実行される。引数の書き方はまだ未定。2行目では今までのコンテキストは変更されるが、w1に参照されているので、前のオブジェクト自体は消えない。次のオブジェクトも同じようにメソッドが呼ばれる。3行目では最初のオブジェクトがリファレンスフリーになるので、(たぶん)解放される。というか、もう参照するすべがないのでわからないというか。最後の行でw2の参照解除が行われるが、コンテキストがまだ参照している。最後の";"で、2番目のオブジェクトも解放されるだろう。