(use-modules (oop goops))
GOOPS has some nice features (you can even use unexported methods with
generics in 1.8) but there is no message passing paradigm. Objective-C
has /tell/ Racket has /send/ but Guile/GOOPS is missing /call/.
This is a first "raw" definition where the parameter /message/ has to be
a quoted symbol.
(define-method (call (receiver <object>) message . arguments)
(apply (slot-ref receiver message) arguments))
The class definition still looks like traditional GOOPS but it works.
An example:
(define-class <receiver> ()
(msg #:init-value (lambda () 'hello-world)))
(define r (make <receiver>))
(call r 'msg) => 'hello-world
Now I'd like to have an easier syntax for describing the slot. The
definition might be:
(define-syntax define-message
(syntax-rules ()
((_ (message-name arguments ... ) body ...)
(message-name #:init-value (lambda (arguments ...) body ...)))))
But the following example doesn't work in 1.8:
(define-class <house> ()
(define-message (phone n)
(repeat n (lambda () (bell) 'rang)) ))
GOOPS complains about malformed slots and *seems* to see the unexpanded
form.*
I could use a little help here, anyone?* Even for the naming scheme:
/send/ is already used by unix sockets and methods are part of the
implementation of generics. Perhaps /message/ isn't that bad.
The missing symbols from my pretext:
(define (natural-number? n)
(and (exact? n)
(integer? n) ; 'integer?' does not check for exactness ...
(> n 0)))
(define-public (repeat n closure)
"Execute closure n times."
(if (not (or (natural-number? n) (= n 0)))
(error "repeat: the parameter n must be an exact natural number
or zero.")
(let loop ((i 0))
(if (< i n)
(begin
(closure)
(loop (1+ i)))) )))
From my pretext.rkt
(define-syntax *broadcast*
(syntax-rules ()
((_ object-list method ...)
(map {lambda (object) (send object method ...)}
object-list))))
(define-syntax *broadcast**
(syntax-rules ()
((_ object-list method ...)
(map {lambda (object) (send* object method ...)}
object-list))))
(define-syntax *define/on-delegate*
(syntax-rules ()
((_ delegate-object (method-name ...))
(define (method-name ...)
(send delegate-object method-name ...)) )))
PS
Perhaps it's better to recreate a clean object model without 3,000 lines
of C code like GOOPS. But then GOOPS really creates the illusion of an
object oriented environment with a MOP ...