Commit | Line | Data |
---|---|---|
e87b4ac1 PR |
1 | // This may look like C code, but it is really -*- C++ -*- |
2 | /* | |
3 | Copyright (C) 1988 Free Software Foundation | |
4 | written by Doug Lea (dl@rocky.oswego.edu) | |
5 | based on code by Marc Shapiro (shapiro@sor.inria.fr) | |
6 | ||
7 | This file is part of the GNU C++ Library. This library is free | |
8 | software; you can redistribute it and/or modify it under the terms of | |
9 | the GNU Library General Public License as published by the Free | |
10 | Software Foundation; either version 2 of the License, or (at your | |
11 | option) any later version. This library is distributed in the hope | |
12 | that it will be useful, but WITHOUT ANY WARRANTY; without even the | |
13 | implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR | |
14 | PURPOSE. See the GNU Library General Public License for more details. | |
15 | You should have received a copy of the GNU Library General Public | |
16 | License along with this library; if not, write to the Free Software | |
17 | Foundation, 675 Mass Ave, Cambridge, MA 02139, USA. | |
18 | */ | |
19 | ||
20 | #ifndef _<T>RPlex_h | |
21 | #ifdef __GNUG__ | |
22 | #pragma interface | |
23 | #endif | |
24 | #define _<T>RPlex_h 1 | |
25 | ||
26 | #include "<T>.Plex.h" | |
27 | ||
28 | // minimum number of chunks to index | |
29 | ||
30 | #ifndef MIN_NCHUNKS | |
31 | #define MIN_NCHUNKS 16 | |
32 | #endif | |
33 | ||
34 | class <T>RPlex: public <T>Plex | |
35 | { | |
36 | int base; // base index of lowest chunk | |
37 | int lch; // index of lowest used chunk | |
38 | int fch; // 1 + index of highest used chunk | |
39 | int maxch; // max chunks in array | |
40 | <T>IChunk** chunks; // array of chunks | |
41 | <T>IChunk* ch; // cached chunk | |
42 | ||
43 | void make_initial_chunks(int up = 1); | |
44 | ||
45 | void cache(int idx) const; | |
46 | void cache(const <T>* p) const; | |
47 | <T>* dopred(const <T>* p) const; | |
48 | <T>* dosucc(const <T>* p) const; | |
49 | ||
50 | void set_cache(const <T>IChunk* t) const; // logically, | |
51 | // not physically const | |
52 | ||
53 | public: | |
54 | <T>RPlex(); // set low = 0; | |
55 | // fence = 0; | |
56 | // csize = default | |
57 | ||
58 | <T>RPlex(int ch_size); // low = 0; | |
59 | // fence = 0; | |
60 | // csize = ch_size | |
61 | ||
62 | <T>RPlex(int lo, // low = lo; | |
63 | int ch_size); // fence=lo | |
64 | // csize = ch_size | |
65 | ||
66 | <T>RPlex(int lo, // low = lo | |
67 | int hi, // fence = hi+1 | |
68 | const <T&> initval,// fill with initval, | |
69 | int ch_size = 0); // csize= ch_size | |
70 | // or fence-lo if 0 | |
71 | ||
72 | <T>RPlex(const <T>RPlex&); | |
73 | ||
74 | ~<T>RPlex(); | |
75 | ||
76 | void operator= (const <T>RPlex&); | |
77 | ||
78 | // virtuals | |
79 | ||
80 | <T>& high_element (); | |
81 | <T>& low_element (); | |
82 | ||
83 | const <T>& high_element () const; | |
84 | const <T>& low_element () const; | |
85 | ||
86 | Pix first() const; | |
87 | Pix last() const; | |
88 | void prev(Pix& ptr) const; | |
89 | void next(Pix& ptr) const; | |
90 | int owns(Pix p) const; | |
91 | <T>& operator () (Pix p); | |
92 | const <T>& operator () (Pix p) const; | |
93 | ||
94 | int low() const; | |
95 | int high() const; | |
96 | int valid(int idx) const; | |
97 | void prev(int& idx) const; | |
98 | void next(int& x) const; | |
99 | <T>& operator [] (int index); | |
100 | const <T>& operator [] (int index) const; | |
101 | ||
102 | int Pix_to_index(Pix p) const; | |
103 | Pix index_to_Pix(int idx) const; | |
104 | ||
105 | int can_add_high() const; | |
106 | int can_add_low() const; | |
107 | int full() const; | |
108 | ||
109 | int add_high(const <T&> elem); | |
110 | int del_high (); | |
111 | int add_low (const <T&> elem); | |
112 | int del_low (); | |
113 | ||
114 | void fill(const <T&> x); | |
115 | void fill(const <T&> x, int from, int to); | |
116 | void clear(); | |
117 | void reverse(); | |
118 | ||
119 | int reset_low(int newlow); | |
120 | ||
121 | int OK () const; | |
122 | }; | |
123 | ||
124 | ||
125 | inline void <T>RPlex::prev(int& idx) const | |
126 | { | |
127 | --idx; | |
128 | } | |
129 | ||
130 | inline void <T>RPlex::next(int& idx) const | |
131 | { | |
132 | ++idx; | |
133 | } | |
134 | ||
135 | inline int <T>RPlex::full () const | |
136 | { | |
137 | return 0; | |
138 | } | |
139 | ||
140 | inline int <T>RPlex::can_add_high() const | |
141 | { | |
142 | return 1; | |
143 | } | |
144 | ||
145 | inline int <T>RPlex::can_add_low() const | |
146 | { | |
147 | return 1; | |
148 | } | |
149 | ||
150 | inline int <T>RPlex::valid (int idx) const | |
151 | { | |
152 | return idx >= lo && idx < fnc; | |
153 | } | |
154 | ||
155 | inline int <T>RPlex::low() const | |
156 | { | |
157 | return lo; | |
158 | } | |
159 | ||
160 | inline int <T>RPlex::high() const | |
161 | { | |
162 | return fnc - 1; | |
163 | } | |
164 | ||
165 | inline void <T>RPlex::set_cache(const <T>IChunk* t) const | |
166 | { | |
167 | ((<T>RPlex*)(this))->ch = (<T>IChunk*)t; | |
168 | } | |
169 | ||
170 | inline void <T>RPlex::cache(int idx) const | |
171 | { | |
172 | if (idx < lo || idx >= fnc) index_error(); | |
173 | set_cache(chunks[(idx - base) / csize]); | |
174 | } | |
175 | ||
176 | inline <T>& <T>RPlex::low_element () | |
177 | { | |
178 | cache(lo); return *(ch->pointer_to(lo)); | |
179 | } | |
180 | ||
181 | inline <T>& <T>RPlex::high_element () | |
182 | { | |
183 | cache(fnc-1); return *(ch->pointer_to(fnc - 1)); | |
184 | } | |
185 | ||
186 | inline const <T>& <T>RPlex::low_element () const | |
187 | { | |
188 | cache(lo); return *((const <T>*)(ch->pointer_to(lo))); | |
189 | } | |
190 | ||
191 | inline const <T>& <T>RPlex::high_element () const | |
192 | { | |
193 | cache(fnc-1); return *((const <T>*)(ch->pointer_to(fnc - 1))); | |
194 | } | |
195 | ||
196 | inline int <T>RPlex::Pix_to_index(Pix px) const | |
197 | { | |
198 | <T>* p = (<T>*)px; | |
199 | if (!ch->actual_pointer(p)) cache(p); | |
200 | return ch->index_of(p); | |
201 | } | |
202 | ||
203 | inline Pix <T>RPlex::index_to_Pix(int idx) const | |
204 | { | |
205 | if (!ch->actual_index(idx)) cache(idx); | |
206 | return (Pix)(ch->pointer_to(idx)); | |
207 | } | |
208 | ||
209 | inline Pix <T>RPlex::first() const | |
210 | { | |
211 | return Pix(hd-><T>IChunk::first_pointer()); | |
212 | } | |
213 | ||
214 | inline Pix <T>RPlex::last() const | |
215 | { | |
216 | return Pix(tl()-><T>IChunk::last_pointer()); | |
217 | } | |
218 | ||
219 | inline void <T>RPlex::prev(Pix& p) const | |
220 | { | |
221 | Pix q = Pix(ch-><T>IChunk::pred((<T>*)p)); | |
222 | p = (q == 0)? Pix(dopred((<T>*)p)) : q; | |
223 | } | |
224 | ||
225 | inline void <T>RPlex::next(Pix& p) const | |
226 | { | |
227 | Pix q = Pix(ch-><T>IChunk::succ((<T>*)p)); | |
228 | p = (q == 0)? Pix(dosucc((<T>*)p)) : q; | |
229 | } | |
230 | ||
231 | inline <T>& <T>RPlex:: operator () (Pix p) | |
232 | { | |
233 | return *((<T>*)p); | |
234 | } | |
235 | ||
236 | ||
237 | inline <T>& <T>RPlex:: operator [] (int idx) | |
238 | { | |
239 | cache(idx); return *(ch->pointer_to(idx)); | |
240 | } | |
241 | ||
242 | inline const <T>& <T>RPlex:: operator () (Pix p) const | |
243 | { | |
244 | return *((const <T>*)p); | |
245 | } | |
246 | ||
247 | inline const <T>& <T>RPlex:: operator [] (int idx) const | |
248 | { | |
249 | cache(idx); return *((const <T>*)(ch->pointer_to(idx))); | |
250 | } | |
251 | ||
252 | inline <T>RPlex::~<T>RPlex() | |
253 | { | |
254 | delete chunks; | |
255 | } | |
256 | ||
257 | #endif |