]> git.donarmstrong.com Git - lilypond.git/blob - flower/include/list.tcc
release: 0.1.51
[lilypond.git] / flower / include / list.tcc
1 /*
2   list.tcc -- implement List<T>
3
4   source file of the Flower Library
5
6   (c) 1997 Han-Wen Nienhuys <hanwen@stack.nl>
7 */
8 #ifndef LIST_CC
9 #define LIST_CC
10
11
12 #include "list.hh"
13
14 template<class T>
15 List<T>::List (List const&src)
16 {
17   set_empty();
18   // probably el stupido
19   for (Cursor<T> c (src); c.ok(); c++)
20         bottom().add (c);
21 }
22
23 template<class T>
24 void
25 List<T>::OK() const
26 {
27   int i = size_;
28   Link<T> *lp = top_;
29   while (i--) 
30     {
31         assert (lp);
32         lp->OK();
33         lp = lp->next();
34     }
35   assert (!lp);
36    i = size_;
37   lp = bottom_;
38   while (i--) 
39     {
40         assert (lp);
41         lp->OK();
42         lp = lp->previous();
43     }
44   assert (!lp);
45 }
46
47 template<class T>
48 void
49 List<T>::junk_links()
50 {
51   Cursor<T> c (*this);
52   while (c.ok())
53         c.del();
54 }
55
56 template<class T>
57 List<T>::~List()
58 {
59   junk_links();
60 }
61
62 /** 
63
64   add after after_me.
65
66   Procedure:
67   \begin{itemize}
68   \item if #after_me# is #ok()#, add after #after_me#, else
69   \item if list !empty simply add to bottom, else
70   \item list is empty: create first \Ref{Link} and initialize 
71   #bottom_# and #top_#.
72   \end{itemize}
73 */
74 template<class T>
75 void
76 List<T>::add (T const & thing, Cursor<T> &after_me)
77 {
78   if (!size_) {         // not much choice if list is empty
79       bottom_ = top_ = new Link<T>(thing);
80         if (!after_me.ok())
81             after_me = bottom();
82     }
83   else {                        // add at aprioprate place
84         if (!after_me.ok())
85             after_me = bottom();
86         Link<T> *p =after_me.pointer();
87         p->add (thing);
88         if (p == bottom_)       // adjust bottom_ if necessary.
89             bottom_ = p->next();
90     }
91
92   size_++;
93 }
94
95 template<class T>
96 void
97 List<T>::insert (T const & thing, Cursor<T> &before_me)
98 {
99   if (!size_) 
100     {
101         bottom_ = top_ = new Link<T>(thing);
102         if (!before_me.ok())
103             before_me = top();
104         
105     }
106   else 
107     {
108         if (!before_me.ok())
109             before_me = top();
110         
111         Link<T> *p = before_me.pointer() ;
112
113         p->insert (thing);
114         if (p == top_)
115             top_ = p->previous();
116     }
117
118   size_++;
119 }
120
121
122 template<class T>
123 void
124 List<T>::concatenate (List<T> const&s)
125 {
126   Cursor<T> b (bottom());
127   for (Cursor<T> c (s); c.ok(); c++) 
128     {
129         b.add (c);
130         b++;
131     }
132 }
133
134 #ifndef __CYGWIN32__ // ugh should check for some gcc/egcs version
135
136 // instantiate a template:  explicit instantiation.
137 #define LIST_INSTANTIATE(a)  template class List<a>; \
138   template class Cursor<a>; template class Link<a>
139
140 #else
141
142 #define LIST_INSTANTIATE(T)\
143     static void force_list_members ()\
144     {\
145     List<T> bla;\
146     bla.top().add ((void*)0);\
147     }
148 #endif
149
150 #endif
151