EssenMemo0009
のバックアップ(No.2)
[
トップ
] [
新規
|
一覧
|
単語検索
|
最終更新
|
ヘルプ
]
バックアップ一覧
差分
を表示
現在との差分
を表示
ソース
を表示
EssenMemo0009
へ行く。
1 (2017-06-14 (水) 11:06:06)
2 (2017-06-14 (水) 13:21:42)
3 (2017-06-14 (水) 17:33:25)
4 (2017-06-14 (水) 17:33:25)
5 (2017-06-15 (木) 17:45:29)
6 (2017-06-16 (金) 06:20:31)
実現したい機能のために仕様を考える#1
(by
K
, 2017.06.14)
↑
引数の渡し方
[1]
C言語では、変数aと変数bを交換する関数を書くとしたら、呼び出し時には swap(&a, &b); と書かなければいけない。
私はこれはかっこよくないと常々感じている。この&を書かずに済ませる方法はないだろうか。
ちなみにC++なら参照型とかを使ってこれを解決できる。
Essenでは関数側の要求に合わせて引数リストを解釈するのではなく、何の事前情報もなしに引数リストを評価して、それを関数に渡すという方式を採用したい。なぜならそのほうがずっと簡単だから。
となるとC++方式は採用できない。
要するにとにかく (a b) と書いたときに、aやbの値を参照してそれを埋めてしまってはいけない。つまり単純に (1 2) とかに変換してはいけない。これじゃあ swap は実現できなくなる。
どんな方法にすべきかは後で考えるとして、とにかくこれだけはありえない。
[2]
どうすればいいか。それはここにはひとまず a と書いてありましたという情報のままにしておくしかない。しかも同じ a でも文脈(スコープ)によって指すものが変わるから、その情報も持たせるべきだ。それをここでは @a とでもあらわすことにしよう。
そうすると (a b) は内部的にはこうなる。 (@a @b)
それで print (a b) とすると、まず内部で (@a @b) が生成されて、表示するために値が評価されて、それで (1 2) が出てくる。
なるほどこれはいけるかもしれない。
この方法だと、 (@a @b) を生成した後でも、評価する前にaやbの値を変更すれば、その新しい値が反映されるということになる。
これは面白いが危険だ。
a = 1 b = 2 x = (a b) a = b = 0 printt x
これで表示されるのは (0 0) でしたっていうのは明らかに直感に反する。ここは (1 2) であるべきだ。
どうすれば両立できるか。
代入演算子の意味を見直そう。
通常の代入では、 @a や @b みたいな情報を検出したら、それを評価して定数化してしまう。そうではなくて参照情報を参照情報のまま代入したいのであれば、 ::= とかを使え、とすればいい。
これでこの問題はひとまず解決する。
[3]
なお、変数が単独で現れずに、式の形で現れた場合は、参照情報は生成しない。たとえば (a + 0 b * 1) など。
この場合は即座に (1 2) になる。
この何もしないっていう演算子は役に立つかもしれない。 ~~ っていうのを作ろう。
[4]
::= 演算子を使えば、遅延評価みたいな仕組みも実現できそう。まあそれがやりたかったというわけではないけれど。
↑
こめんと欄
コメント
お名前
NameLink