2 * CDE - Common Desktop Environment
4 * Copyright (c) 1993-2012, The Open Group. All rights reserved.
6 * These libraries and programs are free software; you can
7 * redistribute them and/or modify them under the terms of the GNU
8 * Lesser General Public License as published by the Free Software
9 * Foundation; either version 2 of the License, or (at your option)
12 * These libraries and programs are distributed in the hope that
13 * they will be useful, but WITHOUT ANY WARRANTY; without even the
14 * implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
15 * PURPOSE. See the GNU Lesser General Public License for more
18 * You should have received a copy of the GNU Lesser General Public
19 * License along with these libraries and programs; if not, write
20 * to the Free Software Foundation, Inc., 51 Franklin Street, Fifth
21 * Floor, Boston, MA 02110-1301 USA
24 * $XConsortium: List.cc /main/4 1996/08/06 09:18:55 rcs $
26 * Copyright (c) 1992 HaL Computer Systems, Inc. All rights reserved.
27 * UNPUBLISHED -- rights reserved under the Copyright Laws of the United
28 * States. Use of a copyright notice is precautionary only and does not
29 * imply publication or disclosure.
31 * This software contains confidential information and trade secrets of HaL
32 * Computer Systems, Inc. Use, disclosure, or reproduction is prohibited
33 * without the prior express written permission of HaL Computer Systems, Inc.
35 * RESTRICTED RIGHTS LEGEND
36 * Use, duplication, or disclosure by the Government is subject to
37 * restrictions as set forth in subparagraph (c)(l)(ii) of the Rights in
38 * Technical Data and Computer Software clause at DFARS 252.227-7013.
39 * HaL Computer Systems, Inc.
40 * 1315 Dell Avenue, Campbell, CA 95008
49 // /////////////////////////////////////////////////////////////////
51 // /////////////////////////////////////////////////////////////////
53 List::List (int initial_size, int increment, grow_method_t method,
55 : f_dtor_delete_elements (delete_elements)
57 assert (initial_size >= 0);
59 f_internal_length = initial_size;
60 f_grow_method = method;
62 f_increment = initial_size;
64 f_increment = increment;
65 assert (f_increment > 0);
66 f_list_element = (FolioObject **)
67 malloc (sizeof (FolioObject *) * initial_size);
71 // /////////////////////////////////////////////////////////////////
73 // /////////////////////////////////////////////////////////////////
77 if (f_dtor_delete_elements)
79 free ((char *) f_list_element);
82 // /////////////////////////////////////////////////////////////////
83 // check_space - create more space for elements if necessary
84 // /////////////////////////////////////////////////////////////////
87 List::check_space (int num_additions)
89 if (f_length + num_additions > f_internal_length)
91 // Loop until internal_length has grown large enough.
92 while (f_length + num_additions > f_internal_length)
94 switch (f_grow_method)
97 f_internal_length = f_internal_length + f_increment;
100 f_internal_length = f_internal_length * f_increment;
108 (FolioObject **) realloc ((char *) f_list_element,
109 sizeof (FolioObject *) * f_internal_length);
114 // /////////////////////////////////////////////////////////////////
115 // append - append an element to the list
116 // /////////////////////////////////////////////////////////////////
119 List::append (FolioObject &element)
123 /* -------- Add the element. -------- */
124 if (&element == NULL)
126 f_list_element[f_length] = &element;
128 notify (APPENDED, (void *)(size_t) (f_length - 1));
132 // /////////////////////////////////////////////////////////////////
133 // remove - remove an element from the list
134 // /////////////////////////////////////////////////////////////////
137 List::remove (FolioObject &element)
139 /* -------- Look for the element in the list -------- */
140 int location = find (element);
147 // /////////////////////////////////////////////////////////////////
148 // remove - remove an element from the list
149 // /////////////////////////////////////////////////////////////////
152 List::remove (unsigned int location)
154 // NOTE: check bounds
155 // Shift the array back and overwrite deleted element.
157 for (int i = location; i < f_length; i++)
158 f_list_element[i] = f_list_element[i+1];
162 // /////////////////////////////////////////////////////////////////
163 // insert - insert an element in the list
164 // /////////////////////////////////////////////////////////////////
167 List::insert (unsigned int location, FolioObject *element)
171 if (location > f_length)
174 // Shift the array forward to make room for new insertion.
175 for (unsigned int i = f_length; i > location; i--)
176 f_list_element[i] = f_list_element[i-1];
178 // Insert the new element in the list.
179 f_list_element[location] = element;
181 notify (INSERTED, (void *)(size_t) location);
185 // /////////////////////////////////////////////////////////////////
186 // find - find an element in a list
187 // /////////////////////////////////////////////////////////////////
190 List::find (FolioObject &element)
192 /* -------- Search through the list, looking for element. -------- */
195 for (i = 0; i < f_length; i++)
196 if (f_list_element[i] == &element)
203 // /////////////////////////////////////////////////////////////////
205 // /////////////////////////////////////////////////////////////////
210 // copy the contents of the list into a new one
212 // NOTE: use length() instead of f_length because it may be more general
213 List *retlist = new List(length());
214 for (unsigned int i = 0 ; i < length(); i++)
215 retlist->append((*this)[i]);
221 // /////////////////////////////////////////////////////////////////
222 // remove_all - remove all the elements from the list
223 // /////////////////////////////////////////////////////////////////
226 List::remove_all (bool)
228 unsigned short length = f_length;
229 // Set length to 0, in case object dtor tries to mess with the list.
231 // Reverse order delete is important for Long_Lived objects!!
233 delete f_list_element[--length];
239 NOTE: Here's how to make the list use less space per list:
241 Make length an internal_length shorts.
243 change grow_method to a bit field of length 1.
244 change increment to a bit field of length 7.
246 if grow_method is multiple, use the increment as a literal.
247 if grow_method is add, use a static lookup table based on