;;; -*- Mode:LISP; Package:USER; Base:10 -*-
(defun y (f)
  (funcall #'(lambda (d) (funcall d d))
	   #'(lambda (x) (funcall f #'(lambda () (funcall x x))))))

(defun fct (c)
  #'(lambda (n)
      (if (zerop n)
	  1
	(* n (funcall (funcall c) (decf n))))))

;;; And now, for continuation passing style!

(defun cps-zero? (n if-zero if-not)
  (if (zerop n)
      (funcall if-zero)
    (funcall if-not)))

(defun cps--1+ (n cont)
  (funcall cont (decf n)))

(defun cps-* (a b cont)
  (funcall cont (* a b)))

(defun cps-fct (c cont)
  (funcall cont
    #'(lambda (n cont)
	(cps-zero? n
	  #'(lambda () (funcall cont 1))
	  #'(lambda ()
	      (cps--1+ n
		#'(lambda (decd)
		    (funcall c
		      #'(lambda (fact)
			  (funcall fact decd
			    #'(lambda (ranswer)
				(cps-* n ranswer cont))))))))))))

(defun cps-y (f cont)
  ((lambda (d cont) (funcall d d cont))
   #'(lambda (x cont1)
       (funcall f #'(lambda (cont) (funcall x x cont)) cont1))
   cont))

(defmacro => (argl &rest body)
  `(function (lambda ,argl ,@body)))

(defun cps-fct (c cont)
  (funcall cont
    (=> (n cont)
      (cps-zero? n
	(=> () (funcall cont 1))
	(=> () (cps--1+ n
		 (=> (decd)
		   (funcall c
		     (=> (fact)
		       (funcall fact decd
			(=> (ranswer)
			  (cps-* n ranswer cont))))))))))))

(defun cps-y (f cont)
  ((lambda (d cont) (funcall d d cont))
   (=> (x cont1)
       (funcall f (=> (cont) (funcall x x cont)) cont1))
   cont))

				  