どんなプログラミング言語にも当たり前にある要素の1つとして、関数が挙げられます。もちろん、Expressoにも存在しますが、Expressoの場合、モジュールの関数と、クラスのメソッドが存在します。実装上は、前者はモジュールクラスのstaticメソッド、後者は普通にクラスのメソッドです。
module main; def test() { let a = 10; return a + 10; } def test2(n (- int) { return n + 10; } def test3(n (- int) -> int { return n + 20; } def test4(n (- int) -> int { if n >= 100 { return n; }else{ return test4(n + 10); } } def main() { let a = test(); let b = test2(20); let c = test3(20); let d = test4(80); println(a, b, c, d); }
このコードもテストコードから引っ張ってきたものですが、Expressoの関数は、戻り値は常に省略しても、本体から推論されますが、この仕様を変えるか悩んでいます(上記の例は、全てintを返す関数と解釈されます)。Kotlinでは、Unit(Voidとほぼ同義)の時のみ推論が効くので、Expressoもそうすべきかもと思っています。
引数の方は、デフォルト値がある時のみ推論が効きます(上記の例には存在しませんね)。
上記の例は上から解説すると、
- 引数なし、戻り値省略
- 引数あり、戻り値省略
- 引数あり、戻り値明示
- 引数あり、戻り値明示の再帰呼び出し
余談ですが、可変長引数をとる関数のパースはできるようになっているものの、コード生成をするようにしてないので、まだ動きません。とりあえず、print*系のために導入したもので、C#にもあるからまあいいかと思っているものですが、具体的なユースケースがそれほど思いつかず、どうしようか悩んでいます。実装自体はそんなに難しくないので、とりあえず入れてしまうのが正解なのかな〜・・・同様に、一般にString interpolationと呼ばれる機能も導入するか迷っています。これがあると、printFormat関数を置き換えることができるんですよね。実に悩ましいところです。(2018/4/8 追記: string interpolationを実装し、printFormat関数を廃止しました)
0 件のコメント:
コメントを投稿
なにか意見や感想、質問などがあれば、ご自由にお書きください。