PageRenderTime 33ms CodeModel.GetById 13ms RepoModel.GetById 1ms app.codeStats 0ms

/indra/llcommon/lldqueueptr.h

https://bitbucket.org/lindenlab/viewer-beta/
C++ Header | 352 lines | 244 code | 53 blank | 55 comment | 36 complexity | d9be9724e285a91ede0d77d7d47902e2 MD5 | raw file
Possible License(s): LGPL-2.1
  1. /**
  2. * @file lldqueueptr.h
  3. * @brief LLDynamicQueuePtr declaration
  4. *
  5. * $LicenseInfo:firstyear=2001&license=viewerlgpl$
  6. * Second Life Viewer Source Code
  7. * Copyright (C) 2010, Linden Research, Inc.
  8. *
  9. * This library is free software; you can redistribute it and/or
  10. * modify it under the terms of the GNU Lesser General Public
  11. * License as published by the Free Software Foundation;
  12. * version 2.1 of the License only.
  13. *
  14. * This library is distributed in the hope that it will be useful,
  15. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  16. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
  17. * Lesser General Public License for more details.
  18. *
  19. * You should have received a copy of the GNU Lesser General Public
  20. * License along with this library; if not, write to the Free Software
  21. * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
  22. *
  23. * Linden Research, Inc., 945 Battery Street, San Francisco, CA 94111 USA
  24. * $/LicenseInfo$
  25. */
  26. #ifndef LL_LLDQUEUEPTR_H
  27. #define LL_LLDQUEUEPTR_H
  28. template <class Type>
  29. class LLDynamicQueuePtr
  30. {
  31. public:
  32. enum
  33. {
  34. OKAY = 0,
  35. FAIL = -1
  36. };
  37. LLDynamicQueuePtr(const S32 size=8);
  38. ~LLDynamicQueuePtr();
  39. void init();
  40. void destroy();
  41. void reset();
  42. void reallocate(U32 newsize);
  43. // ACCESSORS
  44. const Type& get(const S32 index) const; // no bounds checking
  45. Type& get(const S32 index); // no bounds checking
  46. const Type& operator [] (const S32 index) const { return get(index); }
  47. Type& operator [] (const S32 index) { return get(index); }
  48. S32 find(const Type &obj) const;
  49. S32 count() const { return (mLastObj >= mFirstObj ? mLastObj - mFirstObj : mLastObj + mMaxObj - mFirstObj); }
  50. S32 getMax() const { return mMaxObj; }
  51. S32 getFirst() const { return mFirstObj; }
  52. S32 getLast () const { return mLastObj; }
  53. // MANIPULATE
  54. S32 push(const Type &obj); // add to end of Queue, returns index from start
  55. S32 pull( Type &obj); // pull from Queue, returns index from start
  56. S32 remove (S32 index); // remove by index
  57. S32 removeObj(const Type &obj); // remove by object
  58. protected:
  59. S32 mFirstObj, mLastObj, mMaxObj;
  60. Type* mMemory;
  61. public:
  62. void print()
  63. {
  64. /*
  65. Convert this to llinfos if it's intended to be used - djs 08/30/02
  66. printf("Printing from %d to %d (of %d): ",mFirstObj, mLastObj, mMaxObj);
  67. if (mFirstObj <= mLastObj)
  68. {
  69. for (S32 i=mFirstObj;i<mLastObj;i++)
  70. {
  71. printf("%d ",mMemory[i]);
  72. }
  73. }
  74. else
  75. {
  76. for (S32 i=mFirstObj;i<mMaxObj;i++)
  77. {
  78. printf("%d ",mMemory[i]);
  79. }
  80. for (i=0;i<mLastObj;i++)
  81. {
  82. printf("%d ",mMemory[i]);
  83. }
  84. }
  85. printf("\n");
  86. */
  87. }
  88. };
  89. //--------------------------------------------------------
  90. // LLDynamicQueuePtrPtr implementation
  91. //--------------------------------------------------------
  92. template <class Type>
  93. inline LLDynamicQueuePtr<Type>::LLDynamicQueuePtr(const S32 size)
  94. {
  95. init();
  96. reallocate(size);
  97. }
  98. template <class Type>
  99. inline LLDynamicQueuePtr<Type>::~LLDynamicQueuePtr()
  100. {
  101. destroy();
  102. }
  103. template <class Type>
  104. inline void LLDynamicQueuePtr<Type>::init()
  105. {
  106. mFirstObj = 0;
  107. mLastObj = 0;
  108. mMaxObj = 0;
  109. mMemory = NULL;
  110. }
  111. template <class Type>
  112. inline void LLDynamicQueuePtr<Type>::reallocate(U32 newsize)
  113. {
  114. if (newsize)
  115. {
  116. if (mFirstObj > mLastObj && newsize > mMaxObj)
  117. {
  118. Type* new_memory = new Type[newsize];
  119. llassert(new_memory);
  120. S32 _count = count();
  121. S32 i, m = 0;
  122. for (i=mFirstObj; i < mMaxObj; i++)
  123. {
  124. new_memory[m++] = mMemory[i];
  125. }
  126. for (i=0; i <=mLastObj; i++)
  127. {
  128. new_memory[m++] = mMemory[i];
  129. }
  130. delete[] mMemory;
  131. mMemory = new_memory;
  132. mFirstObj = 0;
  133. mLastObj = _count;
  134. }
  135. else
  136. {
  137. Type* new_memory = new Type[newsize];
  138. llassert(new_memory);
  139. S32 i, m = 0;
  140. for (i=0; i < mLastObj; i++)
  141. {
  142. new_memory[m++] = mMemory[i];
  143. }
  144. delete[] mMemory;
  145. mMemory = new_memory;
  146. }
  147. }
  148. else if (mMemory)
  149. {
  150. delete[] mMemory;
  151. mMemory = NULL;
  152. }
  153. mMaxObj = newsize;
  154. }
  155. template <class Type>
  156. inline void LLDynamicQueuePtr<Type>::destroy()
  157. {
  158. reset();
  159. delete[] mMemory;
  160. mMemory = NULL;
  161. }
  162. template <class Type>
  163. void LLDynamicQueuePtr<Type>::reset()
  164. {
  165. for (S32 i=0; i < mMaxObj; i++)
  166. {
  167. get(i) = NULL; // unrefs for pointers
  168. }
  169. mFirstObj = 0;
  170. mLastObj = 0;
  171. }
  172. template <class Type>
  173. inline S32 LLDynamicQueuePtr<Type>::find(const Type &obj) const
  174. {
  175. S32 i;
  176. if (mFirstObj <= mLastObj)
  177. {
  178. for ( i = mFirstObj; i < mLastObj; i++ )
  179. {
  180. if (mMemory[i] == obj)
  181. {
  182. return i;
  183. }
  184. }
  185. }
  186. else
  187. {
  188. for ( i = mFirstObj; i < mMaxObj; i++ )
  189. {
  190. if (mMemory[i] == obj)
  191. {
  192. return i;
  193. }
  194. }
  195. for ( i = 0; i < mLastObj; i++ )
  196. {
  197. if (mMemory[i] == obj)
  198. {
  199. return i;
  200. }
  201. }
  202. }
  203. return FAIL;
  204. }
  205. template <class Type>
  206. inline S32 LLDynamicQueuePtr<Type>::remove(S32 i)
  207. {
  208. if (mFirstObj > mLastObj)
  209. {
  210. if (i >= mFirstObj && i < mMaxObj)
  211. {
  212. while( i > mFirstObj)
  213. {
  214. mMemory[i] = mMemory[i-1];
  215. i--;
  216. }
  217. mMemory[mFirstObj] = NULL;
  218. mFirstObj++;
  219. if (mFirstObj >= mMaxObj) mFirstObj = 0;
  220. return count();
  221. }
  222. else if (i < mLastObj && i >= 0)
  223. {
  224. while(i < mLastObj)
  225. {
  226. mMemory[i] = mMemory[i+1];
  227. i++;
  228. }
  229. mMemory[mLastObj] = NULL;
  230. mLastObj--;
  231. if (mLastObj < 0) mLastObj = mMaxObj-1;
  232. return count();
  233. }
  234. }
  235. else if (i <= mLastObj && i >= mFirstObj)
  236. {
  237. while(i < mLastObj)
  238. {
  239. mMemory[i] = mMemory[i+1];
  240. i++;
  241. }
  242. mMemory[mLastObj] = NULL;
  243. mLastObj--;
  244. if (mLastObj < 0) mLastObj = mMaxObj-1;
  245. return count();
  246. }
  247. return FAIL;
  248. }
  249. template <class Type>
  250. inline S32 LLDynamicQueuePtr<Type>::removeObj(const Type& obj)
  251. {
  252. S32 ind = find(obj);
  253. if (ind >= 0)
  254. {
  255. return remove(ind);
  256. }
  257. return FAIL;
  258. }
  259. template <class Type>
  260. inline S32 LLDynamicQueuePtr<Type>::push(const Type &obj)
  261. {
  262. if (mMaxObj - count() <= 1)
  263. {
  264. reallocate(mMaxObj * 2);
  265. }
  266. mMemory[mLastObj++] = obj;
  267. if (mLastObj >= mMaxObj)
  268. {
  269. mLastObj = 0;
  270. }
  271. return count();
  272. }
  273. template <class Type>
  274. inline S32 LLDynamicQueuePtr<Type>::pull(Type &obj)
  275. {
  276. obj = NULL;
  277. if (count() < 1) return -1;
  278. obj = mMemory[mFirstObj];
  279. mMemory[mFirstObj] = NULL;
  280. mFirstObj++;
  281. if (mFirstObj >= mMaxObj)
  282. {
  283. mFirstObj = 0;
  284. }
  285. return count();
  286. }
  287. template <class Type>
  288. inline const Type& LLDynamicQueuePtr<Type>::get(const S32 i) const
  289. {
  290. return mMemory[i];
  291. }
  292. template <class Type>
  293. inline Type& LLDynamicQueuePtr<Type>::get(const S32 i)
  294. {
  295. return mMemory[i];
  296. }
  297. #endif // LL_LLDQUEUEPTR_H