If the mutation is only to housekeep the two lists:
(define (intersect-mutable (lst1 '()) (lst2 '()))
(define (method-insert lst1? value)
(if lst1?
(set! lst1 (cons value lst1))
(set! lst2 (cons value lst2)))
message-handler)
(define (method-intersect)
;; intersect is a working intersect without mutation
(intersect lst1 lst2))
(define (message-handler msg)
(case msg
((insert) method-insert)
((insert1) (lambda (v) (method-insert #t v)))
((insert2) (lambda (v) (method-insert #f v)))
((lst1) lst1)
((lst2) lst2)
((intersect) method-intersect)
(else (error "No such method" msg))))
message-handler)
(define obj (intersect-mutable '(10) '(30)))
((obj 'insert) #t 5)
((obj 'insert2) 10)
(obj 'lst1) ; ==> (5 10)
(obj 'lst2) ; ==> (10 30)
((obj 'intersect)) ; ==> (10)
However notice that intersect doesn't really mutate anything. I think perhaps the whole point with this is OO so I imagine we can make operate on one list like this:
(define (list-object (lst '()))
(define (method-insert . values)
(set! lst (foldl cons lst values))
message-handler)
(define (method-intersect lst2)
;; intersect is a working intersect without mutation
(set! lst (intersect lst lst2))
message-handler)
(define (method-member? value)
(member value lst))
(define (message-handler msg)
(case msg
((insert) method-insert)
((intersect) method-intersect)
((member?) method-member?)
((lst) lst)
(else (error "No such method" msg))))
message-handler)
(define obj (((list-object '(5)) 'insert) 10 20 30))
(obj 'lst) ; ==> (30 20 10 5)
((obj 'intersect) '(10 30 60))
(obj 'lst) ; ==> (20 30)
Imagine you make many objects like this, then you can make (tiny)CLOS type generic methods:
;; generic. Works on any object that has
;; member? method and lists
(define (member? value obj)
(if (procedure? obj)
((obj 'member?) value)
(member value obj)))
;; Another object type that has member?
;; only that it means the values binary bits
;; are set on the object
(define (number-object value)
(define (method-member? value2)
(= value2 (bitwise-and value value2)))
(define (message-handler msg)
(case msg
((member?) method-member?)))
message-handler)
;; test objects
(define num1 (number-object 24))
(define lst1 (list-object '(1 8)))
;; some test
(member? 2 num1); ==> #f
(member? 8 num1); ==> #t
(member? 8 lst1); ==> (8) (true)
(member? 9 lst1); ==> #f
(member? 9 '(1 3 5 9 10)) ; ==> (9 10)
;; map is the ultimate test
(map (lambda (o) (member? 8 o)) (list num1 lst1))
; ==> (#t (8))