263
272 void destruct_(Size startPos, Size count=1) {
273 if constexpr(std::is_destructible_v<T>) {
274 for(Size i = startPos; i < count; ++i) {
275 this->data()[i].~T();
281 using VectorType = Vector<T>;
283 using ViewType = VectorViewBaseType;
284 using MoveValues = std::tuple<
void*, Size, Size>;
285 using iterator =
typename VectorViewBaseType::iterator;
286 using const_iterator =
typename VectorViewBaseType::const_iterator;
287 using difference_type =
typename VectorViewBaseType::difference_type;
300 explicit Vector(std::nullptr_t, Size allocSize=
sizeof(VectorType)):
301 Vector(
nullptr, 0,
nullptr, allocSize) {}
304 explicit Vector(Context* pCtx=
nullptr, Size allocSize=
sizeof(VectorType)):
305 Vector(
nullptr, 0, pCtx, allocSize) {}
308 explicit Vector(
const T* pInitialData, Size elementCount, Context* pCtx=
nullptr, Size allocSize=
sizeof(VectorType), Size elementSize=
sizeof(T)) {
309 Exception::checkThrow(
GblArrayList_construct(
this, elementSize, elementCount, pInitialData, allocSize, pCtx));
313 explicit Vector(Size count,
const T& value=T(), Context* pCtx=
nullptr, Size allocSize=
sizeof(VectorType)) {
314 T* pTempArray =
static_cast<T*>(
GBL_ALLOCA(count *
sizeof(T)));
315 std::fill(pTempArray, pTempArray+count, value);
320 Vector(std::initializer_list<T> c, Context* pCtx=
nullptr, Size allocSize=
sizeof(VectorType)):
321 Vector(pCtx, allocSize)
323 insert(
this->begin(), c.begin(), c.end());
328 explicit Vector(type_compatible_container_readable<T>
auto&& c, Context* pCtx=
nullptr, Size allocSize=
sizeof(VectorType)):
329 Vector(pCtx, allocSize)
331 *
this = std::forward<
decltype(c)>(c);
335 explicit Vector(
const type_compatible_iterator_readable<T>
auto& first,
const type_compatible_iterator_readable<T>
auto& last, Context* pCtx=
nullptr, Size allocSize=
sizeof(VectorType)):
336 Vector(pCtx, allocSize)
338 insert(
this->end(), first, last);
344 Vector(
const VectorType& other, Context* pCtx=
nullptr, Size allocSize=
sizeof(VectorType)):
345 Vector(VectorView(other), pCtx, allocSize) {}
348 Vector(VectorView<T> other, Context* pCtx=
nullptr, Size allocSize=
sizeof(VectorType)):
349 Vector(other.data(), other.size(), pCtx, allocSize) {}
355 Vector(VectorType&& rhs, Context* pCtx=
nullptr, Size allocSize=
sizeof(VectorType)):
356 Vector(
static_cast<GblArrayList&&>(rhs), pCtx, allocSize) {}
359 Vector(GblArrayList&& rhs, Context* pCtx=
nullptr, Size allocSize=
sizeof(VectorType)):
360 Vector(pCtx, allocSize)
362 *
this = std::move(rhs);
365 static MoveValues take(GblArrayList* pVec) {
366 auto moveValues = MoveValues(
nullptr, 0, 0);
367 auto& [pData, size, capacity] = moveValues;
368 Exception::checkThrow(GblArrayList_release(pVec, &pData, &size, &capacity));
376 void give(MoveValues moveValues) {
377 auto& [pData, size, capacity] = moveValues;
378 Exception::checkThrow(GblArrayList_acquire(
this, pData, size, capacity));
382 destruct_(0, size());
383 Exception::checkThrow(GblArrayList_destruct(
this));
386 using VectorViewBaseType::size;
387 using VectorViewBaseType::capacity;
389 void reserve(Size count) {
390 Exception::checkThrow(GblArrayList_reserve(
this, count));
393 void resize(Size newSize) {
394 if(newSize < size()) {
395 destruct_(newSize, size() - newSize);
397 Exception::checkThrow(GblArrayList_resize(
this, newSize));
400 void shrink_to_fit(
void) {
401 Exception::checkThrow(GblArrayList_shrinkToFit(
this));
404 void pushBack(T value) {
405 Exception::checkThrow(GblArrayList_pushBack(
this, &value));
408 void push_back(T value) {
409 pushBack(std::move(value));
412 template<
typename... Args>
413 T& emplace_back(Args&&... args) {
415 void* pData =
this->at_(size()-1);
416 T* pObj =
new (pData) T(std::forward<Args>(args)...);
420 void pushFront(T value) {
421 Exception::checkThrow(GblArrayList_pushFront(
this, &value));
424 void push_front(T value) {
425 pushFront(std::move(value));
428 iterator insert(const_iterator position,
const T* pValue, Size count) {
429 const auto index = std::distance(
this->cbegin(), position);
430 Exception::checkThrow([&]() {
431 GblArrayList_insert(
this, index, count, pValue);
433 return iterator(*
this, index);
436 iterator insert(const_iterator position,
const T& val) {
437 return insert(std::move(position), &val, 1);
440 iterator insert(const_iterator position, gimbal::Size size,
const T& val) {
441 T* pTempArray =
static_cast<T*>(
GBL_ALLOCA(size *
sizeof(T)));
442 std::fill(pTempArray, pTempArray+size, val);
443 return insert(std::move(position), pTempArray, size);
446 iterator insert(const_iterator position,
const type_compatible_iterator_readable<T>
auto& first,
const type_compatible_iterator_readable<T>
auto& last) {
447 const auto size = std::distance(first, last);
448 T* pTempArray =
static_cast<T*>(
GBL_ALLOCA(size *
sizeof(T)));
449 std::copy(first, last, pTempArray);
450 return insert(std::move(position), pTempArray, size);
453 template<type_compatible_iterator_readable<T> It>
454 requires contiguous_iterator<It>
455 iterator insert(const_iterator position,
const It& first,
const It& last) {
456 return insert(std::move(position), &first[0], std::distance(first, last));
459 iterator insert(const_iterator position,
const type_compatible_container_readable<T>
auto &c) {
460 return insert(std::move(position), std::cbegin(c), std::cend(c));
463 iterator insert(const_iterator position,
const type_compatible_contiguous_container_readable<T>
auto &c) {
464 return insert(std::move(position), c.data(), std::size(c));
467 template<
typename... Args>
468 iterator emplace(const_iterator position, Args&&... args) {
469 const auto index = std::distance(
this->cbegin(), position);
470 void* pData =
nullptr;
471 Exception::checkThrow([&]() {
472 pData = GblArrayList_insert(
this, index, 1,
nullptr);
474 T* pObj =
new (pData) T(std::forward<Args>(args)...);
475 return iterator(*
this, index);
479 destruct_(
this->getSize()-1, 1);
480 erase(
this->end()-1);
483 void pop_back(
void) {
487 iterator erase(const_iterator pos) {
488 return erase(pos, pos+1);
491 iterator erase(const_iterator first, const_iterator last) {
492 const auto index = std::distance<const_iterator>(
this->begin(), first);
493 const auto count = std::distance(first, last);
494 destruct_(index, count);
495 Exception::checkThrow(GblArrayList_erase(
this, index, count));
496 return iterator(*
this, index+count);
500 destruct_(0,
this->getSize());
501 Exception::checkThrow(GblArrayList_clear(
this));
504 void assign(
const T* pData, Size elementCount) {
505 Exception::checkThrow(GblArrayList_assign(
this, pData, elementCount));
508 void assign(gimbal::Size size,
const T& value) {
509 T* pTempArray =
static_cast<T*>(
GBL_ALLOCA(size *
sizeof(T)));
510 std::fill(pTempArray, pTempArray+size, value);
511 assign(pTempArray, size);
514 void assign(
const type_compatible_contiguous_container_readable<T>
auto &c) {
515 assign(c.data(), std::size(c));
518 void assign(
const type_compatible_container_readable<T>
auto& c) {
519 T* pTempArray =
static_cast<T*>(
GBL_ALLOCA(std::size(c) *
sizeof(T)));
520 std::copy(begin(c), end(c), pTempArray);
521 Exception::checkThrow(GblArrayList_assign(
this, pTempArray, std::size(c)));
524 void assign(
const type_compatible_iterator_readable<T>
auto& first,
const type_compatible_iterator_readable<T>
auto& last) {
525 const auto size = std::distance(first, last);
526 T* pTempArray =
static_cast<T*>(
GBL_ALLOCA(size *
sizeof(T)));
527 std::copy(first, last, pTempArray);
528 assign(pTempArray, size);
531 template<type_compatible_iterator_readable<T> It>
532 requires contiguous_iterator<It>
533 void assign(
const It& first,
const It& last) {
535 const T* pData = &first[0];
536 const auto dist = std::distance(first, last);
541 const VectorType& operator=(VectorView<T> rhs) {
542 Exception::checkThrow(GblArrayList_assign(
this, rhs.data(), rhs.size()));
546 const VectorType& operator=(
const VectorType& rhs) {
547 return *
this = VectorView<T>(rhs);
550 const VectorType& operator=(VectorType&& rhs) {
551 return *
this =
static_cast<GblArrayList&&>(rhs);
554 const VectorType& operator=(GblArrayList&& rhs) {
555 VectorView<T> rhsView(rhs);
557 if(
this->getContext() == rhsView.getContext() && rhsView.isHeap()) {
565 const VectorType& operator=(
const type_compatible_container<T>
auto&& c) {
568 if constexpr(std::same_as<
decltype(c), gimbal::pmr::vector<T>&&>) {
569 if(
this->get_allocator() == c.get_allocator()) {
579 const VectorType& operator+=(
const type_compatible_container_readable<T>
auto& view) {
580 insert(
this->end(), view);
584 const VectorType& operator+=(
const type_compatible_iterator_readable<T>
auto& it) {
585 insert(
this->end(), it);