10 |
|
|
11 |
@menu |
@menu |
12 |
* Equality:: When are two values `the same'? |
* Equality:: When are two values `the same'? |
13 |
* Property Lists:: Managing meta-information about Scheme objects. |
* Object Properties:: A modern interface to object properties. |
|
* Primitive Properties:: A modern low-level interface to object properties. |
|
14 |
* Sorting:: Sort utility procedures. |
* Sorting:: Sort utility procedures. |
15 |
* Copying:: Copying deep structures. |
* Copying:: Copying deep structures. |
16 |
* General Conversion:: Converting objects to strings. |
* General Conversion:: Converting objects to strings. |
17 |
|
* Hooks:: User-customizable event lists. |
18 |
@end menu |
@end menu |
19 |
|
|
20 |
|
|
74 |
@end deffn |
@end deffn |
75 |
|
|
76 |
|
|
77 |
@node Property Lists |
@node Object Properties |
78 |
@section Property Lists |
@section Object Properties |
79 |
|
|
80 |
Every object in the system can have a @dfn{property list} that may |
It's often useful to associate a piece of additional information with a |
81 |
be used for information about that object. For example, a |
Scheme object even though that object does not have a dedicated slot |
82 |
function may have a property list that includes information about |
available in which the additional information could be stored. Object |
83 |
the source file in which it is defined. |
properties allow you to do just that. |
84 |
|
|
85 |
Property lists are implemented as assq lists (@pxref{Association Lists}). |
An object property is most commonly used to associate one kind of |
86 |
|
additional information with each instance of a class of similar Scheme |
87 |
Currently, property lists are implemented differently for procedures and |
objects. For example, all procedures have a `name' property, which |
88 |
closures than for other kinds of objects. Therefore, when manipulating |
stores the name of the variable in which the procedure was stored by a |
89 |
a property list associated with a procedure object, use the |
@code{define} expression, or @code{#f} if the procedure wasn't created |
90 |
@code{procedure} functions; otherwise, use the @code{object} functions. |
by that kind of expression. |
91 |
|
|
92 |
|
Guile's representation of an object property is a procedure-with-setter |
93 |
|
(@pxref{Procedures with Setters}) that can be used with the generalized |
94 |
|
form of @code{set!} (REFFIXME) to set and retrieve that property for any |
95 |
|
Scheme object. So, setting a property looks like this: |
96 |
|
|
97 |
|
@lisp |
98 |
|
(set! (my-property obj1) value-for-obj1) |
99 |
|
(set! (my-property obj2) value-for-obj2) |
100 |
|
@end lisp |
101 |
|
|
102 |
|
@noindent |
103 |
|
And retrieving values of the same property looks like this: |
104 |
|
|
105 |
|
@lisp |
106 |
|
(my-property obj1) |
107 |
|
@result{} |
108 |
|
value-for-obj1 |
109 |
|
|
110 |
|
(my-property obj2) |
111 |
|
@result{} |
112 |
|
value-for-obj2 |
113 |
|
@end lisp |
114 |
|
|
115 |
|
To create an object property in the first place, use the |
116 |
|
@code{make-object-property} procedure: |
117 |
|
|
118 |
|
@lisp |
119 |
|
(define my-property (make-object-property)) |
120 |
|
@end lisp |
121 |
|
|
122 |
|
@deffn {Scheme Procedure} make-object-property |
123 |
|
Create and return an object property. An object property is a |
124 |
|
procedure-with-setter that can be called in two ways. @code{(set! |
125 |
|
(@var{property} @var{obj}) @var{val})} sets @var{obj}'s @var{property} |
126 |
|
to @var{val}. @code{(@var{property} @var{obj})} returns the current |
127 |
|
setting of @var{obj}'s @var{property}. |
128 |
|
@end deffn |
129 |
|
|
130 |
|
A single object property created by @code{make-object-property} can |
131 |
|
associate distinct property values with all Scheme values that are |
132 |
|
distinguishable by @code{eq?} (including, for example, integers). |
133 |
|
|
134 |
|
Internally, object properties are implemented using a weak key hash |
135 |
|
table. This means that, as long as a Scheme value with property values |
136 |
|
is protected from garbage collection, its property values are also |
137 |
|
protected. When the Scheme value is collected, its entry in the |
138 |
|
property table is removed and so the (ex-) property values are no longer |
139 |
|
protected by the table. |
140 |
|
|
141 |
@deffn {Scheme Procedure} object-properties obj |
@menu |
142 |
@deffnx {Scheme Procedure} procedure-properties obj |
* Property Primitives:: Low level property implementation. |
143 |
@deffnx {C Function} scm_object_properties (obj) |
* Old-fashioned Properties:: An older approach to properties. |
144 |
Return @var{obj}'s property list. |
@end menu |
|
@end deffn |
|
|
|
|
|
@deffn {Scheme Procedure} set-object-properties! obj alist |
|
|
@deffnx {Scheme Procedure} set-procedure-properties! obj alist |
|
|
@deffnx {C Function} scm_set_object_properties_x (obj, alist) |
|
|
Set @var{obj}'s property list to @var{alist}. |
|
|
@end deffn |
|
|
|
|
|
@deffn {Scheme Procedure} object-property obj key |
|
|
@deffnx {Scheme Procedure} procedure-property obj key |
|
|
@deffnx {C Function} scm_object_property (obj, key) |
|
|
Return the property of @var{obj} with name @var{key}. |
|
|
@end deffn |
|
|
|
|
|
@deffn {Scheme Procedure} set-object-property! obj key value |
|
|
@deffnx {Scheme Procedure} set-procedure-property! obj key value |
|
|
@deffnx {C Function} scm_set_object_property_x (obj, key, value) |
|
|
In @var{obj}'s property list, set the property named @var{key} |
|
|
to @var{value}. |
|
|
@end deffn |
|
|
|
|
|
[Interface bug: there should be a second level of interface in which |
|
|
the user provides a "property table" that is possibly private.] |
|
145 |
|
|
146 |
|
|
147 |
@node Primitive Properties |
@node Property Primitives |
148 |
@section Primitive Properties |
@subsection Low Level Property Implementation. |
149 |
|
|
150 |
@deffn {Scheme Procedure} primitive-make-property not_found_proc |
@deffn {Scheme Procedure} primitive-make-property not_found_proc |
151 |
@deffnx {C Function} scm_primitive_make_property (not_found_proc) |
@deffnx {C Function} scm_primitive_make_property (not_found_proc) |
177 |
@end deffn |
@end deffn |
178 |
|
|
179 |
|
|
180 |
|
@node Old-fashioned Properties |
181 |
|
@subsection An Older Approach to Properties |
182 |
|
|
183 |
|
Traditionally, Lisp systems provide a different object property |
184 |
|
interface to that provided by @code{make-object-property}, in which the |
185 |
|
object property that is being set or retrieved is indicated by a symbol. |
186 |
|
|
187 |
|
Guile includes this older kind of interface as well, but it may well be |
188 |
|
removed in a future release, as it is less powerful than |
189 |
|
@code{make-object-property} and so increases the size of the Guile |
190 |
|
library for no benefit. (And it is trivial to write a compatibility |
191 |
|
layer in Scheme.) |
192 |
|
|
193 |
|
@deffn {Scheme Procedure} object-properties obj |
194 |
|
@deffnx {C Function} scm_object_properties (obj) |
195 |
|
Return @var{obj}'s property list. |
196 |
|
@end deffn |
197 |
|
|
198 |
|
@deffn {Scheme Procedure} set-object-properties! obj alist |
199 |
|
@deffnx {C Function} scm_set_object_properties_x (obj, alist) |
200 |
|
Set @var{obj}'s property list to @var{alist}. |
201 |
|
@end deffn |
202 |
|
|
203 |
|
@deffn {Scheme Procedure} object-property obj key |
204 |
|
@deffnx {C Function} scm_object_property (obj, key) |
205 |
|
Return the property of @var{obj} with name @var{key}. |
206 |
|
@end deffn |
207 |
|
|
208 |
|
@deffn {Scheme Procedure} set-object-property! obj key value |
209 |
|
@deffnx {C Function} scm_set_object_property_x (obj, key, value) |
210 |
|
In @var{obj}'s property list, set the property named @var{key} |
211 |
|
to @var{value}. |
212 |
|
@end deffn |
213 |
|
|
214 |
|
|
215 |
@node Sorting |
@node Sorting |
216 |
@section Sorting |
@section Sorting |
217 |
|
|
232 |
|
|
233 |
@deffn {Scheme Procedure} merge alist blist less |
@deffn {Scheme Procedure} merge alist blist less |
234 |
@deffnx {C Function} scm_merge (alist, blist, less) |
@deffnx {C Function} scm_merge (alist, blist, less) |
235 |
Take two lists @var{alist} and @var{blist} such that |
Merge two already sorted lists into one. |
236 |
@code{(sorted? alist less?)} and @code{(sorted? blist less?)} and |
Given two lists @var{alist} and @var{blist}, such that |
237 |
returns a new list in which the elements of @var{alist} and |
@code{(sorted? alist less?)} and @code{(sorted? blist less?)}, |
238 |
|
return a new list in which the elements of @var{alist} and |
239 |
@var{blist} have been stably interleaved so that |
@var{blist} have been stably interleaved so that |
240 |
@code{(sorted? (merge alist blist less?) less?)}. |
@code{(sorted? (merge alist blist less?) less?)}. |
241 |
|
Note: this does _not_ accept vectors. |
242 |
@end deffn |
@end deffn |
243 |
|
|
244 |
@deffn {Scheme Procedure} merge! alist blist less |
@deffn {Scheme Procedure} merge! alist blist less |
373 |
@end deffn |
@end deffn |
374 |
|
|
375 |
|
|
376 |
|
@node Hooks |
377 |
|
@section Hooks |
378 |
|
@tpindex Hooks |
379 |
|
|
380 |
|
@c FIXME::martin: Review me! |
381 |
|
|
382 |
|
A hook is basically a list of procedures to be called at well defined |
383 |
|
points in time. Hooks are used internally for several debugging |
384 |
|
facilities, but they can be used in user code, too. |
385 |
|
|
386 |
|
Hooks are created with @code{make-hook}, then procedures can be added to |
387 |
|
a hook with @code{add-hook!} or removed with @code{remove-hook!} or |
388 |
|
@code{reset-hook!}. The procedures stored in a hook can be invoked with |
389 |
|
@code{run-hook}. |
390 |
|
|
391 |
|
@menu |
392 |
|
* Hook Examples:: Hook usage by example. |
393 |
|
* Hook Reference:: Reference of all hook procedures. |
394 |
|
@end menu |
395 |
|
|
396 |
|
@node Hook Examples |
397 |
|
@subsection Hook Examples |
398 |
|
|
399 |
|
Hook usage is shown by some examples in this section. First, we will |
400 |
|
define a hook of arity 2 --- that is, the procedures stored in the hook |
401 |
|
will have to accept two arguments. |
402 |
|
|
403 |
|
@lisp |
404 |
|
(define hook (make-hook 2)) |
405 |
|
hook |
406 |
|
@result{} #<hook 2 40286c90> |
407 |
|
@end lisp |
408 |
|
|
409 |
|
Now we are ready to add some procedures to the newly created hook with |
410 |
|
@code{add-hook!}. In the following example, two procedures are added, |
411 |
|
which print different messages and do different things with their |
412 |
|
arguments. When the procedures have been added, we can invoke them |
413 |
|
using @code{run-hook}. |
414 |
|
|
415 |
|
@lisp |
416 |
|
(add-hook! hook (lambda (x y) |
417 |
|
(display "Foo: ") |
418 |
|
(display (+ x y)) |
419 |
|
(newline))) |
420 |
|
(add-hook! hook (lambda (x y) |
421 |
|
(display "Bar: ") |
422 |
|
(display (* x y)) |
423 |
|
(newline))) |
424 |
|
(run-hook hook 3 4) |
425 |
|
@print{} Bar: 12 |
426 |
|
@print{} Foo: 7 |
427 |
|
@end lisp |
428 |
|
|
429 |
|
Note that the procedures are called in reverse order than they were |
430 |
|
added. This can be changed by providing the optional third argument |
431 |
|
on the second call to @code{add-hook!}. |
432 |
|
|
433 |
|
@lisp |
434 |
|
(add-hook! hook (lambda (x y) |
435 |
|
(display "Foo: ") |
436 |
|
(display (+ x y)) |
437 |
|
(newline))) |
438 |
|
(add-hook! hook (lambda (x y) |
439 |
|
(display "Bar: ") |
440 |
|
(display (* x y)) |
441 |
|
(newline)) |
442 |
|
#t) ; @r{<- Change here!} |
443 |
|
(run-hook hook 3 4) |
444 |
|
@print{} Foo: 7 |
445 |
|
@print{} Bar: 12 |
446 |
|
@end lisp |
447 |
|
|
448 |
|
@node Hook Reference |
449 |
|
@subsection Hook Reference |
450 |
|
|
451 |
|
When a hook is created with @code{make-hook}, you can supply the arity |
452 |
|
of the procedures which can be added to the hook. The arity defaults to |
453 |
|
zero. All procedures of a hook must have the same arity, and when the |
454 |
|
procedures are invoked using @code{run-hook}, the number of arguments |
455 |
|
must match the arity of the procedures. |
456 |
|
|
457 |
|
The order in which procedures are added to a hook matters. If the third |
458 |
|
parameter to @var{add-hook!} is omitted or is equal to @code{#f}, the |
459 |
|
procedure is added in front of the procedures which might already be on |
460 |
|
that hook, otherwise the procedure is added at the end. The procedures |
461 |
|
are always called from first to last when they are invoked via |
462 |
|
@code{run-hook}. |
463 |
|
|
464 |
|
When calling @code{hook->list}, the procedures in the resulting list are |
465 |
|
in the same order as they would have been called by @code{run-hook}. |
466 |
|
|
467 |
|
@deffn {Scheme Procedure} make-hook [n_args] |
468 |
|
@deffnx {C Function} scm_make_hook (n_args) |
469 |
|
Create a hook for storing procedure of arity @var{n_args}. |
470 |
|
@var{n_args} defaults to zero. The returned value is a hook |
471 |
|
object to be used with the other hook procedures. |
472 |
|
@end deffn |
473 |
|
|
474 |
|
@deffn {Scheme Procedure} hook? x |
475 |
|
@deffnx {C Function} scm_hook_p (x) |
476 |
|
Return @code{#t} if @var{x} is a hook, @code{#f} otherwise. |
477 |
|
@end deffn |
478 |
|
|
479 |
|
@deffn {Scheme Procedure} hook-empty? hook |
480 |
|
@deffnx {C Function} scm_hook_empty_p (hook) |
481 |
|
Return @code{#t} if @var{hook} is an empty hook, @code{#f} |
482 |
|
otherwise. |
483 |
|
@end deffn |
484 |
|
|
485 |
|
@deffn {Scheme Procedure} add-hook! hook proc [append_p] |
486 |
|
@deffnx {C Function} scm_add_hook_x (hook, proc, append_p) |
487 |
|
Add the procedure @var{proc} to the hook @var{hook}. The |
488 |
|
procedure is added to the end if @var{append_p} is true, |
489 |
|
otherwise it is added to the front. The return value of this |
490 |
|
procedure is not specified. |
491 |
|
@end deffn |
492 |
|
|
493 |
|
@deffn {Scheme Procedure} remove-hook! hook proc |
494 |
|
@deffnx {C Function} scm_remove_hook_x (hook, proc) |
495 |
|
Remove the procedure @var{proc} from the hook @var{hook}. The |
496 |
|
return value of this procedure is not specified. |
497 |
|
@end deffn |
498 |
|
|
499 |
|
@deffn {Scheme Procedure} reset-hook! hook |
500 |
|
@deffnx {C Function} scm_reset_hook_x (hook) |
501 |
|
Remove all procedures from the hook @var{hook}. The return |
502 |
|
value of this procedure is not specified. |
503 |
|
@end deffn |
504 |
|
|
505 |
|
@deffn {Scheme Procedure} run-hook hook . args |
506 |
|
@deffnx {C Function} scm_run_hook (hook, args) |
507 |
|
Apply all procedures from the hook @var{hook} to the arguments |
508 |
|
@var{args}. The order of the procedure application is first to |
509 |
|
last. The return value of this procedure is not specified. |
510 |
|
@end deffn |
511 |
|
|
512 |
|
@deffn {Scheme Procedure} hook->list hook |
513 |
|
@deffnx {C Function} scm_hook_to_list (hook) |
514 |
|
Convert the procedure list of @var{hook} to a list. |
515 |
|
@end deffn |
516 |
|
|
517 |
|
|
518 |
@c Local Variables: |
@c Local Variables: |
519 |
@c TeX-master: "guile.texi" |
@c TeX-master: "guile.texi" |
520 |
@c End: |
@c End: |