List.m 5.9 KB

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