]> git.saurik.com Git - apple/objc4.git/blob - runtime/OldClasses.subproj/List.m
43cc3cbb9fc891fd872056cc4ad21eb8bdeae0ee
[apple/objc4.git] / runtime / OldClasses.subproj / List.m
1 /*
2 * Copyright (c) 1999 Apple Computer, Inc. All rights reserved.
3 *
4 * @APPLE_LICENSE_HEADER_START@
5 *
6 * Portions Copyright (c) 1999 Apple Computer, Inc. All Rights
7 * Reserved. This file contains Original Code and/or Modifications of
8 * Original Code as defined in and that are subject to the Apple Public
9 * Source License Version 1.1 (the "License"). You may not use this file
10 * except in compliance with the License. Please obtain a copy of the
11 * License at http://www.apple.com/publicsource and read it before using
12 * this file.
13 *
14 * The Original Code and all software distributed under the License are
15 * distributed on an "AS IS" basis, WITHOUT WARRANTY OF ANY KIND, EITHER
16 * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
17 * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
18 * FITNESS FOR A PARTICULAR PURPOSE OR NON- INFRINGEMENT. Please see the
19 * License for the specific language governing rights and limitations
20 * under the License.
21 *
22 * @APPLE_LICENSE_HEADER_END@
23 */
24 /*
25 List.m
26 Copyright 1988-1996 NeXT Software, Inc.
27 Written by: Bryan Yamamoto
28 Responsibility: Bertrand Serlet
29 */
30
31
32 #import <stdlib.h>
33 #import <stdio.h>
34 #import <string.h>
35 #import <objc/List.h>
36
37 #define DATASIZE(count) ((count) * sizeof(id))
38
39 @implementation List
40
41 + initialize
42 {
43 [self setVersion: 1];
44 return self;
45 }
46
47 - initCount:(unsigned)numSlots
48 {
49 maxElements = numSlots;
50 if (maxElements)
51 dataPtr = (id *)malloc(DATASIZE(maxElements));
52 return self;
53 }
54
55 + newCount:(unsigned)numSlots
56 {
57 return [[self alloc] initCount:numSlots];
58 }
59
60 + new
61 {
62 return [self newCount:0];
63 }
64
65 - init
66 {
67 return [self initCount:0];
68 }
69
70 - free
71 {
72 free(dataPtr);
73 return [super free];
74 }
75
76 - freeObjects
77 {
78 id element;
79 while ((element = [self removeLastObject]))
80 [element free];
81 return self;
82 }
83
84 - copyFromZone:(void *)z
85 {
86 List *new = [[[self class] alloc] initCount: numElements];
87 new->numElements = numElements;
88 bcopy ((const char*)dataPtr, (char*)new->dataPtr, DATASIZE(numElements));
89 return new;
90 }
91
92 - (BOOL) isEqual: anObject
93 {
94 List *other;
95 if (! [anObject isKindOf: [self class]]) return NO;
96 other = (List *) anObject;
97 return (numElements == other->numElements)
98 && (bcmp ((const char*)dataPtr, (const char*)other->dataPtr, DATASIZE(numElements)) == 0);
99 }
100
101 - (unsigned)capacity
102 {
103 return maxElements;
104 }
105
106 - (unsigned)count
107 {
108 return numElements;
109 }
110
111 - objectAt:(unsigned)index
112 {
113 if (index >= numElements)
114 return nil;
115 return dataPtr[index];
116 }
117
118 - (unsigned)indexOf:anObject
119 {
120 register id *this = dataPtr;
121 register id *last = this + numElements;
122 while (this < last) {
123 if (*this == anObject)
124 return this - dataPtr;
125 this++;
126 }
127 return NX_NOT_IN_LIST;
128 }
129
130 - lastObject
131 {
132 if (! numElements)
133 return nil;
134 return dataPtr[numElements - 1];
135 }
136
137 - setAvailableCapacity:(unsigned)numSlots
138 {
139 volatile id *tempDataPtr;
140 if (numSlots < numElements) return nil;
141 tempDataPtr = (id *) realloc (dataPtr, DATASIZE(numSlots));
142 dataPtr = (id *)tempDataPtr;
143 maxElements = numSlots;
144 return self;
145 }
146
147 - insertObject:anObject at:(unsigned)index
148 {
149 register id *this, *last, *prev;
150 if (! anObject) return nil;
151 if (index > numElements)
152 return nil;
153 if ((numElements + 1) > maxElements) {
154 volatile id *tempDataPtr;
155 /* we double the capacity, also a good size for malloc */
156 maxElements += maxElements + 1;
157 tempDataPtr = (id *) realloc (dataPtr, DATASIZE(maxElements));
158 dataPtr = (id*)tempDataPtr;
159 }
160 this = dataPtr + numElements;
161 prev = this - 1;
162 last = dataPtr + index;
163 while (this > last)
164 *this-- = *prev--;
165 *last = anObject;
166 numElements++;
167 return self;
168 }
169
170 - addObject:anObject
171 {
172 return [self insertObject:anObject at:numElements];
173
174 }
175
176
177 - addObjectIfAbsent:anObject
178 {
179 register id *this, *last;
180 if (! anObject) return nil;
181 this = dataPtr;
182 last = dataPtr + numElements;
183 while (this < last) {
184 if (*this == anObject)
185 return self;
186 this++;
187 }
188 return [self insertObject:anObject at:numElements];
189
190 }
191
192
193 - removeObjectAt:(unsigned)index
194 {
195 register id *this, *last, *next;
196 id retval;
197 if (index >= numElements)
198 return nil;
199 this = dataPtr + index;
200 last = dataPtr + numElements;
201 next = this + 1;
202 retval = *this;
203 while (next < last)
204 *this++ = *next++;
205 numElements--;
206 return retval;
207 }
208
209 - removeObject:anObject
210 {
211 register id *this, *last;
212 this = dataPtr;
213 last = dataPtr + numElements;
214 while (this < last) {
215 if (*this == anObject)
216 return [self removeObjectAt:this - dataPtr];
217 this++;
218 }
219 return nil;
220 }
221
222 - removeLastObject
223 {
224 if (! numElements)
225 return nil;
226 return [self removeObjectAt: numElements - 1];
227 }
228
229 - empty
230 {
231 numElements = 0;
232 return self;
233 }
234
235 - replaceObject:anObject with:newObject
236 {
237 register id *this, *last;
238 if (! newObject)
239 return nil;
240 this = dataPtr;
241 last = dataPtr + numElements;
242 while (this < last) {
243 if (*this == anObject) {
244 *this = newObject;
245 return anObject;
246 }
247 this++;
248 }
249 return nil;
250 }
251
252 - replaceObjectAt:(unsigned)index with:newObject
253 {
254 register id *this;
255 id retval;
256 if (! newObject)
257 return nil;
258 if (index >= numElements)
259 return nil;
260 this = dataPtr + index;
261 retval = *this;
262 *this = newObject;
263 return retval;
264 }
265
266 - makeObjectsPerform:(SEL)aSelector
267 {
268 unsigned count = numElements;
269 while (count--)
270 [dataPtr[count] perform: aSelector];
271 return self;
272 }
273
274 - makeObjectsPerform:(SEL)aSelector with:anObject
275 {
276 unsigned count = numElements;
277 while (count--)
278 [dataPtr[count] perform: aSelector with: anObject];
279 return self;
280 }
281
282 -appendList: (List *)otherList
283 {
284 unsigned i, count;
285
286 for (i = 0, count = [otherList count]; i < count; i++)
287 [self addObject: [otherList objectAt: i]];
288 return self;
289 }
290
291 @end