;; Enable lexical bindings
(setq lexical-binding t)
;; In a lexically scoped environment lambda functions evaluates to
;; closures objects. Closures are functions that capture the lexical
;; environment where they are defined. The lexical environment is
;; captured in an alist terminated by 't'. See below.
;; Let's define an high order functions that returns a lambda (a
;; closure). Every time the lambda is funcall-ed it returns an
;; incremented integer (remembering the previous value):
(defun incrementer (x)
(lambda ()
(setq x
(1+ x))) ; The lambda evaluate to a closure => (closure (t) nil (setq x (1+ x)))
)
;; Let's create an incrementer starting from 1
(setq inc-from-1 (incrementer 0)) ; => (closure ((x . 0) t) nil (setq x (1+ x)))
(funcall inc-from-1) ; => 1
(funcall inc-from-1) ; => 2
;; Thanks to the homiconicity of Lisp, a closure object can be
;; manipulated as a regular list during runtime and the captured
;; environment can be modified:
;; Let's modify the closure and jump the incrementer to 100 directly:
(setf (caadr inc-from-1) '(x . 100))
(funcall inc-from-1) ; => 101
Created: 2021-08-29 Sun 18:52