Factorial in Lazy K

http://www.kt.rim.or.jp/%7ekbk/zakkicho/09/zakkicho0912b.html#D20091217-4Lazy K で階乗を計算するプログラム(10進数で入出力するバージョン)を知ったのですが、常識で考えて 9681 byte も必要ないですよね。1324 byte (改行除く) で充分です。

S(S(K(SII(S(K(S(S(KS)(S(KK)(S(KS)(S(S(KS)(S(KK)(S(KS)(S(S(KS
)(S(K(S(SI(KK))))(S(K(S(KK)))(S(S(KS)K)(K(SI(KK)))))))(K(KI)
)))))(K(S(K(S(S(KS)(S(K(SI))(S(KK)(S(K(S(S(KS)K)(S(S(KS)K)I)
(S(SII)I(S(S(KS)K)I)(S(S(KS)K)))))(SI(K(KI)))))))))(S(KK)K))
)))))(K(S(KK)(S(S(S(SI(K(S(S(KS)(S(K(S(KS)))(S(K(S(K(S(S(K(S
(K(S(S(K(S(S(KS)K)I(S(S(KS)K)(S(S(KS)K)I))(S(K(SI))K)))K))))
)(S(K(S(KK)))(S(S(KS)(S(KK)(SI(K(S(K(SI))K)))))(KK))))))))(S
(S(KS)(S(K(S(KS)))(S(KK))))(K(K(S(S(KS)K))))))))(S(K(S(KK)))
(S(S(KS)(S(S(KS)K)(K(S(S(KS)K)))))(K(K(KI))))))))(K(S(S(KS)(
S(KK)(S(KS)(S(K(SI))K))))(KK))))(K(KI)))(K(KI)))))))(SII))))
(S(K(SII(S(K(S(S(KS)(S(K(SI))(S(K(S(KK)))(S(K(S(S(KS)K)))(S(
S(KS)K)(K(S(S(SI(K(S(K(SI))(S(KK)(SI(K(S(S(KS)K))))))))(K(K(
KI))))(KI))))))))(K(KI))))(SII))))(SII(S(K(S(S(KS)(S(K(S(KS)
))(S(K(S(K(S(S(K(SI(KK)))(S(S(SI(KK))(K(SI(K(KI)))))(K(S(S(K
S)K)(S(S(KS)K)I)(S(SII)I(S(S(KS)K)I)(S(K(S(SI(K(KI)))))K))(S
(S(KS)K)I(S(S(KS)K)(SII(S(S(KS)K)I))(S(K(S(SI(KK))))K))(SII(
S(K(S(K(S(SI(K(KI)))))K))(SII))))))))))))(S(S(KS)(S(K(S(KS))
)(S(S(KS)(S(KK)(S(KS)K)))(K(S(K(S(S(S(K(S(S(KS)K)(S(S(KS)K)I
)(S(SII)I(S(S(KS)K)I)(S(S(SI(K(S(K(SI))(S(KK)(SI(K(S(S(KS)K)
)))))))(K(K(KI))))(KI)))))(SI(KK)))(K(S(S(KS)K))))))(S(KK)(S
(K(S(K(S(S(KS)K)I))(S(S(KS)K)(SII(S(S(KS)K)I))))))))))))(K(K
(SI(K(KI)))))))))(KK)))(SII))(KI))))(K(K(SII(SII(S(S(KS)K)I)
))))

以下はコンパイル前のコード

(load "./lazier.scm")
(load "./prelude.scm")
(load "./prelude-numbers.scm")

(lazy-def '(isnumber char)
          '(nth char (48 (cons #f) (10 (cons #t) (list-of #f)))))

(lazy-def '(1- n)
          '(n (lambda(g h)(h (g 1+))) (k 0) i))

(lazy-def '(chartoi char)
          '(48 1- char))

(lazy-def '(atoi self n str)
          '(isnumber (car str)
                     (self (+ (chartoi (car str)) (* 10 n)) (cdr str))
                     n))

(lazy-def '(factorial self n)
          '(ifnonzero n (* n (self (1- n))) 1))

(lazy-def '(divmod10 n)
          '(n (lambda(fun a b) (if> 9 b (fun a (1+ b)) (fun (1+ a) 0))) cons
             0 0))

(lazy-def '(tostr self num str)
          '((lambda(dm10)
              ((ifnonzero (car dm10) (self (car dm10)) i)
               (cons (+ 48 (cdr dm10)) str)))
            (divmod10 num)))

(print-as-cc (laze '(lambda(str)
                      (Y tostr (Y factorial (Y atoi 0 str))
                         end-of-output))))