Skip to content

Instantly share code, notes, and snippets.

@ha2ne2
Last active August 29, 2015 14:19
Show Gist options
  • Select an option

  • Save ha2ne2/0fd8c37b2b4b35cf3e2e to your computer and use it in GitHub Desktop.

Select an option

Save ha2ne2/0fd8c37b2b4b35cf3e2e to your computer and use it in GitHub Desktop.
;; compose、compose2両関数とも同じ動きをするが、生成するラムダ式の構造が違う
;; (funcall (compose #'not #'evenp #'+) 3 2 2)
;; T
(defun compose (&rest fs)
(if (null (cdr fs))
(car fs)
(let ((g (apply #'compose (cdr fs))))
(lambda (&rest args) (funcall (car fs) (apply g args))))))
;; (lambda (&rest args)
;; (funcall #'not
;; (apply (lambda (&rest args)
;; (funcall #'evenp
;; (apply #'+
;; args)))
;; args)))
(defun compose2 (fn &rest functions)
(reduce (lambda (f g)
(lambda (&rest args)
(funcall f (apply g args))))
functions
:initial-value fn))
;; (lambda (&rest args)
;; (funcall
;; (lambda (&rest args)
;; (funcall
;; #'not
;; (apply #'evenp args)))
;; (apply #'+ args)))
(defmacro comp (&rest fs)
(let ((args (gensym)))
(labels ((rec (fs)
(if (null (cdr fs))
`(apply #',(car fs) ,args)
`(,(car fs) ,(rec (cdr fs))))))
`(lambda (&rest ,args) ,(rec fs)))))
;; (comp not evenp +)
;;=> (LAMBDA (&REST #:G2049) (NOT (EVENP (APPLY #'+ #:G2049))))
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment