この文書は非常に難解な『関数ライブラリ』である worldcomponent のマニュアルである。このライブラリを使用することで、ライブラリ作者が推奨する『FRP』が実現可能になる。しかし、その基礎部分が高度な哲学的理論により構成されているため、使いこなすには IQ145 以上の頭脳が必要になる。一般人には理解することすら不可能であるため、あらゆる批判は全て誹謗中傷であり、告訴の対象となる。
※ここでの『関数ライブラリ』や『FRP』という用語はライブラリ作者独自の概念が含まれており、一般的な意味とは異なることに注意されたい。
ライブラリ全体をソースコードの最初に貼り付けることで使用できる。また、node.js 環境では "npm install worldcomponent" でインストールすることも可能でる。
ライブラリを使用する場合は worldcomponent
のエイリアスとして ___
を使用することが推奨される。
-
ソースコードを貼り付ける場合
/* ここにライブラリのソースコードを全て貼り付け */ var ___ = worldcomponent;
-
npm でインストールする場合
var ___ = require("worldcomponent");
関数 func を評価する。func()
と記載した場合と全く同一の動作になる。ただし、関数の戻り値を取得する方法や引数を渡す方法はない。
var ___ = worldcomponent;
var hello = function() {
console.log("hello");
}
___.world = hello;
// print> hello
文字列 msg を出力する関数を返す。console.log.bind(console, msg)
と記載した場合と全く同一の動作になる。
var ___ = worldcomponent;
var hello = ___.log("hello");
___.world = hello;
// print> hello
状態 state をラップしたオブジェクトを返す。以下、このオブジェクトを worldobj と表記する。worldobj は状態を表す state と関数の配列 computingF を保持する。作成直後の状態では state の値は undefined
であり、init ではない。
慣例として、変数名は ___
から始めなければならない。
var ___ = worldcomponent;
var ___a = ___(0);
___.world = ___.log(___a.now());
// print> undefined
関数 func の登録と状態の初期化を同時に行う関数を返す。返される関数を評価したとき、下記動作を行う。
- 関数 func を内部配列 computingF の末尾の追加する。
- 内部状態 state に worldobj 作成時に指定した初期値 init を代入する。
- 内部配列 computingF に登録されている全ての関数(1.で追加した関数 func を含む)について、初期値 init を引数として順番に評価する。
- 3.の結果として、評価された関数の個数と同じ長さで全ての要素が
undefined
である配列が作成される。ただし、この配列は使用されずに、GCに回収される。
返される関数を評価したときの戻り値はない。また、評価される度に状態の初期化は毎回実施される。単独では使用せず、worldcomponent.world =
を用いて即時に評価する方法が推奨される。
var ___ = worldcomponent;
var ___a = ___(0);
___.world = ___a.compute(function(v) {
___.world = ___.log("run");
});
// print> run
___.world = ___.log(___a.now());
// print> 0
状態を値 value に変更する関数を返す。返される関数を評価したとき、下記動作を行う。
- 内部状態 state に 値 value を代入する。
- 内部配列 computingF に登録されている全ての関数について、値 value を引数として順番に評価する。
- 2.の結果として、評価された関数の個数と同じ長さで全ての要素が
undefined
である配列が作成される。ただし、この配列は使用されずに、GCに回収される。
返される関数を評価したときの戻り値はない。単独では使用せず、worldcomponent.world =
を用いて即時に評価する方法が推奨される。
var ___ = worldcomponent;
var ___a = ___(0);
___.world = ___a.compute(function(v) {
___.world = ___.log("run");
});
// print> run
___.world = ___a.appear(1);
// print> run
___.world = ___.log(___a.now());
// print> 1
内部状態 state を返す。他の二つと違い、関数を返すのではなく、即座に評価される。また、上記のように worldobj 自体は内部状態 state が変化する mutable なオブジェクトであり、返す値は常に同じとは限らないため、参照透明ではない。ライブラリ作者が推奨する『FRP』での時間変化する状態を取得できる。
var ___a = ___(0);
___.world = ___.log(___a.now());
// print> undefined
___.world = ___a.compute(function(v) {
___.world = ___.log("run");
});
// print> run
___.world = ___.log(___a.now());
// print> 0
___.world = ___a.appear(1);
// print> run
___.world = ___.log(___a.now());
// print> 1
何かしらのイベントが登録されるまで、状態は初期化されない。なぜなら、イベントが無い世界は存在しないからだ。
イベントが登録されると言うことは世界の様態が変更されると言うことだ。様態の異なる世界に対応するためには、世界を一度初期化しないといけない。
あらゆるイベントは正常に動作しなければならない。イベント登録によって様態の変化した世界が正常に動作するかを確認するために、全てのイベントを一度実行する必要がある。
時間は前へのみ進んでいく。削除という時間を逆行する操作ができるわけがない。現実世界が過去にさかのぼれないのと同じだ。
もし、どうしてもイベントを削除したい場合は、世界そのものを破棄し、新しい世界(New World)を作ればいい。
一度作られた物を削除することは不可能だ。削除はせずにdisplay:none
で隠せばいい。
もし、どうしてもコンポーネントを削除したい場合は、世界そのものを破棄し、新しい世界(New World)を作ればいい。
『関数型プログラミング』では配列の操作には何かしらの値を返さなければならない。イベントは内部配列 computingF に保存されているため、配列内の関数を順次評価するときは forEach()
ではなく map()
を使用しなければならないことは『関数型プログラミング』の基本中の基本である。一見無駄なようなにみえるが、『関数型プログラミング』では当たり前のことであり、重要な要素の一つとなっている。
※ここでの『関数型プログラミング』という用語はライブラリ作者独自の概念が含まれており、一般的な意味とは異なることに注意されたい。
勉強になりました。今後も応援してます
ローヤー長澤