blob: 85b821e880b3774421dfad80abc48fa3c392ba30 (
plain)
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
|
(defstruct list-builder ()
head tail
(:postinit (bc)
(set bc.head (cons nil bc.head)
bc.tail (last bc.head)))
(:method add (self . items)
(set self.tail (last (rplacd self.tail (copy items)))))
(:method add* (self . items)
(let ((ic (copy items))
(h self.head))
(rplacd (last ic) (cdr h))
(rplacd h ic)))
(:method pend (self . lists)
(while lists
(set self.tail (last (rplacd self.tail (copy (car lists)))))
(set lists (cdr lists))))
(:method pend* (self . lists)
(let* ((h self.head)
(nh (cons nil nil))
(tl nh))
(while lists
(set tl (last (rplacd tl (copy (car lists)))))
(set lists (cdr lists)))
(rplacd tl (cdr h))
(set self.head nh)))
(:method ncon (self . lists)
(set self.tail (last (rplacd self.tail (nconc . lists)))))
(:method ncon* (self . lists)
(let ((h self.head))
(set (cdr h) (nconc (nconc . lists) (cdr h)))
(if (eq self.tail h)
(set self.tail (last h)))))
(:method get (self)
(cdr self.head)))
(defun sys:list-builder-macrolets (lb-form)
(nconc
(collect-each ((op '(add add* pend pend* ncon ncon*)))
^(,op (. forms)
^(qref ,',lb-form (,',op ,*forms))))
^((get ()
^(qref ,',lb-form (get))))))
(defun build-list (: init)
(new list-builder head init))
(defmacro build (. forms)
(with-gensyms (name)
^(let ((,name (new list-builder)))
(macrolet ,(sys:list-builder-macrolets name)
,*forms
(qref ,name (get))))))
|