Scheme可愛いよって話をしていたら、「括弧が多い」って言われたので
今日は昼間、会社の同僚と久しぶりに会って話していました。
そして、話しているうちにSchemeかわいいという話を僕がしていて、実際にFizzBuzzのコードを書いてみせて、その後Project-Eulerの問題を解いてみせたんですが、「でも、括弧が多いし…」と言われたのでちょっと括弧とか"lambda"というのを極力書かない書き方をしてみせてみた。
お題はProjectEuler Problem 2より"Even Fibonacci numbers"。
フィボナッチ数列の項は前の2つの項の和である. 最初の2項を 1, 2 とすれば, 最初の10項は以下の通りである.
1, 2, 3, 5, 8, 13, 21, 34, 55, 89, ...
数列の項の値が400万より小さい, 偶数値の項の総和を求めよ.
普通に解いてみる。
とりあえず、手続きfib*1があるとして、(fib n)が400万を超える適当なnを決めている状態で解く。
(fold + 0 (filter even? (filter (lambda (x) (>= 4000000 x)) (map fib (iota 100 1)))))
これで答えが出ます。短い!素敵!
実際には400万を超えるのは(fib 34)のときなので、100はふっかけすぎだけどまぁいいや。
で、これを見た同僚が「括弧多い」っていうので、括弧を減らしてみた。
($ fold + 0 $ filter even? $ filter (^n (>= 4000000 n)) $ map fib $ iota 100 1)
括弧が少ない!lambdaっていう文字列もない!素敵!
まぁGaucheだから出来たんですが、こんな感じでどうでしょう。
ただ、
これはあくまで好みの問題ですし、こういった構文糖衣は濫用されがちなので 気をつけてください。けれどもスパイスのように、控えめな隠し味として使うと、 しばしばとても有用です。
Gauche ユーザーリファレンスより
ということですので、ほどほどにしませう。。
Problem2について
どうでもいいことだけど問題の雰囲気だと、どちらかというと下のように解くほうが良い気がするんだけど、あくまでも上のは例として書いたので適当で。
(define (fib n) (define (iter a b max-value) (if (< max-value a) () (cons a (iter (+ a b) a max-value)))) (iter 1 0 n)) (define (even-sum li) (apply + (filter even? li))) (even-sum (fib 4000000))
*1:割りと高速な奴じゃないと時間かかるので注意