1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
|
(((name . "after")
(signature syntax-rules (when let =>) (after (clause ...) body ...))
(subsigs
(clause (pattern
((when conditional))
((let value => formal))
((on-error! expr)))))
(desc "
For each clause,
* If `clause` is `when conditional`, then `conditional` is evaluated. If
`conditional` is false, then the `after` expression returns `#f`.
Otherwise the rest of the clauses are executed.
* If `clause` is `let value => formal`, then `value` is evaluated. If
`value` returns no values, then the `after` expression returns `#f`.
Otherwise, the values returned are bound to `formal` in the next clauses
and in the body.
* If `clause` is `on-error! expr`, then the next failed clause will execute
`expr`. The expression will be executed in the scope of all previous
declarations.
The `on-error!` clause works by returning the result thunk to any
enclosing `cond-thunk` expression before the next clauses are evaluated.
The execution of the rest of the clauses continues in the returned thunk,
with failures tail-calling a thunk that executes `expr`. The `on-error!`
clause is simliar to `cut` in logic programming languages, because it
prevents backtracking to an enclosing `cond-thunk`. It was originally
called `cut!`.
Once all clauses succeed, the `after` clause returns a thunk containing
body. The free variables bound in and surrounding the `after` expression
are captured in the thunk."))
((name . "receive-ct")
(signature syntax-rules () (_ formal generator body ...))
(desc "
If `generator` returns no values, the whole expression returns no values.
Otherwise bind the values made by `generator` to `formal` and return
`body ...` as a thunk."))
((name . "cond-values")
(signature syntax-rules () (cond-values clauses ...))
(desc "
A wrapper around `cond-thunk` that returns no values instead of `#f`
when all clauses are exhausted. This is intended for destructuring
procedures used by `after`. See `cond-thunk` for more details."))
((name . "pair=>")
(signature lambda (x) => (or (values * *) (values)))
(tags destructuring)
(desc "
If `x` is a pair, return its car and cdr. Otherwise return no values."))
((name . "length-at-least=>")
(signature lambda (whole-list (integer? num)) *)
(tags destructuring)
(desc "
* It is an error if `num` is not a positive integer.
If `whole-list` is a proper or improper list of length at least `num`,
then `num + 1` values are delivered: the first `num` elements and a
final element with the rest of the list."))
((name. "length=>")
(signature lambda (whole-list (integer? num)) *)
(tags destructuring)
(desc "
* It is an error if `num` is not a positive integer.
If `whole-list` is a proper list of length `num`, then each element of the
list is returned as values."))
((name . "apply-after")
(signature syntax-rules () ((_ producer consumer)))
(desc "
Evaluates `producer`. If `producer` evaluates to at least one value, then
return a thunk that, when called, tail-calls `consumer` with the values
that `producer` produced. Otherwise, return `#f~."))
((name . "define-record-type/destructor")
(signature syntax-rules () ((_ type-name
(cstr fields ...)
predicate?
destructor=>
field-spec ...)))
(desc "
Creates a record type using `define-record-type`, and also creates a
destructor procedure of a single argument named `destructor=>`. When
`destructor=>` is called with a record of this type, it returns as values
each field of the record as declared in the `field-spec`. Otherwise it
returns no values.
Note that the destructor will always return no values for a record type
that has no fields."))
((name "evaluate-destructor-to-boolean")
(signature syntax-rules () ((_ expr)))
(desc "
Evaluates the destructor `expr`. If `expr` returns no values, return `#f`.
Otherwise return `#t`.")))
|