boot2

Playing with the boostrap
git clone https://git.ryansepassi.com/git/boot2.git
Log | Files | Refs | README

081-set-bang.scm (1658B)


      1 ; (set! name value) -- mutate an existing binding in place. Returns
      2 ; unspecified. Must work on globals, lexicals (let-bound, lambda-bound),
      3 ; and lexicals captured by a closure (mutation visible to all closures
      4 ; that captured the same binding).
      5 
      6 ;; --- Global rebind ----------------------------------------------------
      7 (define g 1)
      8 (set! g 2)
      9 (if (= g 2) 0 (sys-exit 1))
     10 
     11 ;; --- Lexical (let-bound) ---------------------------------------------
     12 (if (= 9
     13        (let ((x 1))
     14          (set! x 9)
     15          x))
     16     0 (sys-exit 2))
     17 
     18 ;; --- Lexical, set! does NOT escape the let -------------------------
     19 ;; Outer g is unaffected by the inner set! on a shadowing binding.
     20 (define outer-touched 0)
     21 (let ((g 100))
     22   (set! g 200)
     23   (set! outer-touched g))
     24 (if (= g 2)              0 (sys-exit 3))   ; outer g unchanged
     25 (if (= outer-touched 200) 0 (sys-exit 4))  ; inner saw 200
     26 
     27 ;; --- Lambda parameter --------------------------------------------------
     28 (define (bump x) (set! x (+ x 1)) x)
     29 (if (= (bump 4) 5) 0 (sys-exit 5))
     30 
     31 ;; --- Closure-captured cell: counter pattern --------------------------
     32 (define counter
     33   (let ((n 0))
     34     (lambda ()
     35       (set! n (+ n 1))
     36       n)))
     37 
     38 (if (= (counter) 1) 0 (sys-exit 6))
     39 (if (= (counter) 2) 0 (sys-exit 7))
     40 (if (= (counter) 3) 0 (sys-exit 8))
     41 
     42 ;; --- Two closures sharing the same captured cell ---------------------
     43 ;; Both closures close over the same `s`; mutations through one are
     44 ;; visible through the other.
     45 (define get #f)
     46 (define put #f)
     47 (let ((s 10))
     48   (set! get (lambda ()  s))
     49   (set! put (lambda (v) (set! s v))))
     50 
     51 (if (= (get) 10) 0 (sys-exit 9))
     52 (put 42)
     53 (if (= (get) 42) 0 (sys-exit 10))
     54 
     55 (sys-exit 0)