Vector.h 7.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325
  1. /*
  2. Copyright (c) 2013 Daniele Bartolini, Michele Rossi
  3. Copyright (c) 2012 Daniele Bartolini, Simone Boscaratto
  4. Permission is hereby granted, free of charge, to any person
  5. obtaining a copy of this software and associated documentation
  6. files (the "Software"), to deal in the Software without
  7. restriction, including without limitation the rights to use,
  8. copy, modify, merge, publish, distribute, sublicense, and/or sell
  9. copies of the Software, and to permit persons to whom the
  10. Software is furnished to do so, subject to the following
  11. conditions:
  12. The above copyright notice and this permission notice shall be
  13. included in all copies or substantial portions of the Software.
  14. THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
  15. EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
  16. OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
  17. NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
  18. HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
  19. WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
  20. FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
  21. OTHER DEALINGS IN THE SOFTWARE.
  22. */
  23. #pragma once
  24. #include "Types.h"
  25. #include "Assert.h"
  26. #include "Array.h"
  27. namespace crown
  28. {
  29. /// Functions to manipulate Vector.
  30. ///
  31. /// @ingroup Containers
  32. namespace vector
  33. {
  34. /// Returns whether the vector @a v is empty.
  35. template <typename T> bool empty(const Vector<T>& v);
  36. /// Returns the number of items in the vector @a v.
  37. template <typename T> uint32_t size(const Vector<T>& v);
  38. /// Returns the maximum number of items the vector @a v can hold.
  39. template <typename T> uint32_t capacity(const Vector<T>& v);
  40. /// Resizes the vector @a v to the given @a size.
  41. /// @note
  42. /// Old items will be copied to the newly created vector.
  43. /// If the new capacity is smaller than the previous one, the
  44. /// vector will be truncated.
  45. template <typename T> void resize(Vector<T>& v, uint32_t size);
  46. /// Reserves space in the vector @a v for at least @a capacity items.
  47. template <typename T> void reserve(Vector<T>& v, uint32_t capacity);
  48. /// Sets the capacity of vector @a v.
  49. template <typename T> void set_capacity(Vector<T>& v, uint32_t capacity);
  50. /// Grows the vector @a v to contain at least @a min_capacity items.
  51. template <typename T> void grow(Vector<T>& v, uint32_t min_capacity);
  52. /// Condenses the vector @a v so that its capacity matches the actual number
  53. /// of items in the vector.
  54. template <typename T> void condense(Vector<T>& v);
  55. /// Appends an item to the vector @a v and returns its index.
  56. template <typename T> uint32_t push_back(Vector<T>& v, const T& item);
  57. /// Removes the last item from the vector @a v.
  58. template <typename T> void pop_back(Vector<T>& v);
  59. /// Appends @a count @a items to the vector @a v and returns the number
  60. /// of items in the vector after the append operation.
  61. template <typename T> uint32_t push(Vector<T>& v, const T* items, uint32_t count);
  62. /// Clears the content of the vector @a v.
  63. /// @note
  64. /// Calls destructor on the items.
  65. template <typename T> void clear(Vector<T>& v);
  66. template <typename T> T* begin(Vector<T>& v);
  67. template <typename T> const T* begin(const Vector<T>& v);
  68. template <typename T> T* end(Vector<T>& v);
  69. template <typename T> const T* end(const Vector<T>& v);
  70. template <typename T> T& front(Vector<T>& v);
  71. template <typename T> const T& front(const Vector<T>& v);
  72. template <typename T> T& back(Vector<T>& v);
  73. template <typename T> const T& back(const Vector<T>& v);
  74. } // namespace vector
  75. namespace vector
  76. {
  77. template <typename T>
  78. bool empty(const Vector<T>& v)
  79. {
  80. return array::empty(v.m_array);
  81. }
  82. template <typename T>
  83. uint32_t size(const Vector<T>& v)
  84. {
  85. return array::size(v.m_array);
  86. }
  87. template <typename T>
  88. uint32_t capacity(const Vector<T>& v)
  89. {
  90. return array::capacity(v.m_array);
  91. }
  92. template <typename T>
  93. void resize(Vector<T>& v, uint32_t size)
  94. {
  95. array::resize(v.m_array, size);
  96. }
  97. template <typename T>
  98. void reserve(Vector<T>& v, uint32_t capacity)
  99. {
  100. array::reserve(v.m_array, capacity);
  101. }
  102. template <typename T>
  103. void set_capacity(Vector<T>& v, uint32_t capacity)
  104. {
  105. if (capacity == v.m_array.m_capacity)
  106. return;
  107. if (capacity < v.m_array.m_size)
  108. resize(v, capacity);
  109. if (capacity > 0)
  110. {
  111. Array<T> arr = v.m_array;
  112. T* tmp = arr.m_array;
  113. arr.m_capacity = capacity;
  114. arr.m_array = (T*)arr.m_allocator->allocate(capacity * sizeof(T));
  115. for (uint32_t i = 0; i < arr.m_size; i++)
  116. {
  117. new (arr.m_array + i) T(tmp[i]);
  118. }
  119. if (tmp)
  120. {
  121. for (uint32_t i = 0; i < arr.m_size; i++)
  122. {
  123. tmp[i].~T();
  124. }
  125. arr.m_allocator->deallocate(tmp);
  126. }
  127. }
  128. }
  129. template <typename T>
  130. void grow(Vector<T>& v, uint32_t min_capacity)
  131. {
  132. return array::grow(v.m_array, min_capacity);
  133. }
  134. template <typename T>
  135. void condense(Vector<T>& v)
  136. {
  137. return array::condense(v.m_array);
  138. }
  139. template <typename T>
  140. uint32_t push_back(Vector<T>& v, const T& item)
  141. {
  142. if (v.m_array.m_capacity == v.m_array.m_size)
  143. grow(v, 0);
  144. new (v.m_array.m_array + v.m_array.m_size) T(item);
  145. return v.m_array.m_size++;
  146. }
  147. template <typename T>
  148. void pop_back(Vector<T>& v)
  149. {
  150. CE_ASSERT(vector::size(v) > 0, "The vector is empty");
  151. v.m_array.m_array[v.m_array.m_size - 1].~T();
  152. v.m_array.m_size--;
  153. }
  154. template <typename T>
  155. uint32_t push(Vector<T>& v, const T* items, uint32_t count)
  156. {
  157. if (v.m_array.m_capacity <= v.m_array.m_size + count)
  158. grow(v, v.m_array.m_size + count);
  159. T* arr = &v.m_array.m_array[v.m_array.m_size];
  160. for (uint32_t i = 0; i < count; i++)
  161. {
  162. arr[i] = items[i];
  163. }
  164. v.m_array.m_size += count;
  165. return v.m_array.m_size;
  166. }
  167. template <typename T>
  168. void clear(Vector<T>& v)
  169. {
  170. for (uint32_t i = 0; i < v.m_array.m_size; i++)
  171. {
  172. v.m_array.m_array[i].~T();
  173. }
  174. v.m_array.m_size = 0;
  175. }
  176. template <typename T>
  177. T* begin(Vector<T>& v)
  178. {
  179. return array::begin(v.m_array);
  180. }
  181. template <typename T>
  182. const T* begin(const Vector<T>& v)
  183. {
  184. return array::begin(v.m_array);
  185. }
  186. template <typename T>
  187. T* end(Vector<T>& v)
  188. {
  189. return array::end(v.m_array);
  190. }
  191. template <typename T>
  192. const T* end(const Vector<T>& v)
  193. {
  194. return array::end(v.m_array);
  195. }
  196. template <typename T>
  197. T& front(Vector<T>& v)
  198. {
  199. return array::front(v.m_array);
  200. }
  201. template <typename T>
  202. const T& front(const Vector<T>& v)
  203. {
  204. return array::front(v.m_array);
  205. }
  206. template <typename T>
  207. T& back(Vector<T>& v)
  208. {
  209. return array::back(v.m_array);
  210. }
  211. template <typename T>
  212. const T& back(const Vector<T>& v)
  213. {
  214. return array::back(v.m_array);
  215. }
  216. } // namespace vector
  217. //-----------------------------------------------------------------------------
  218. template <typename T>
  219. inline Vector<T>::Vector(Allocator& allocator)
  220. : m_array(allocator)
  221. {
  222. }
  223. //-----------------------------------------------------------------------------
  224. template <typename T>
  225. inline Vector<T>::Vector(Allocator& allocator, uint32_t capacity)
  226. : m_array(allocator)
  227. {
  228. }
  229. //-----------------------------------------------------------------------------
  230. template <typename T>
  231. inline Vector<T>::Vector(const Vector<T>& other)
  232. : m_array(other.m_array)
  233. {
  234. *this = other;
  235. }
  236. //-----------------------------------------------------------------------------
  237. template <typename T>
  238. inline Vector<T>::~Vector()
  239. {
  240. for (uint32_t i = 0; i < array::size(m_array); i++)
  241. {
  242. m_array[i].~T();
  243. }
  244. }
  245. //-----------------------------------------------------------------------------
  246. template <typename T>
  247. inline T& Vector<T>::operator[](uint32_t index)
  248. {
  249. return m_array[index];
  250. }
  251. //-----------------------------------------------------------------------------
  252. template <typename T>
  253. inline const T& Vector<T>::operator[](uint32_t index) const
  254. {
  255. return m_array[index];
  256. }
  257. //-----------------------------------------------------------------------------
  258. template <typename T>
  259. inline const Vector<T>& Vector<T>::operator=(const Vector<T>& other)
  260. {
  261. const uint32_t size = vector::size(other);
  262. vector::resize(*this, size);
  263. for (uint32_t i = 0; i < size; i++)
  264. {
  265. m_array[i] = other.m_array[i];
  266. }
  267. return *this;
  268. }
  269. } // namespace crown