diff options
Diffstat (limited to 'absl/container/internal/inlined_vector.h')
-rw-r--r-- | absl/container/internal/inlined_vector.h | 158 |
1 files changed, 88 insertions, 70 deletions
diff --git a/absl/container/internal/inlined_vector.h b/absl/container/internal/inlined_vector.h index 17e203e51f5e..61c4f6ebfccc 100644 --- a/absl/container/internal/inlined_vector.h +++ b/absl/container/internal/inlined_vector.h @@ -19,6 +19,7 @@ #include <cstddef> #include <cstring> #include <iterator> +#include <limits> #include <memory> #include <utility> @@ -270,6 +271,19 @@ class Storage { using ConstructionTransaction = inlined_vector_internal::ConstructionTransaction<allocator_type>; + static size_type NextCapacity(size_type current_capacity) { + return current_capacity * 2; + } + + static size_type ComputeCapacity(size_type current_capacity, + size_type requested_capacity) { + return (std::max)(NextCapacity(current_capacity), requested_capacity); + } + + // --------------------------------------------------------------------------- + // Storage Constructors and Destructor + // --------------------------------------------------------------------------- + Storage() : metadata_() {} explicit Storage(const allocator_type& alloc) @@ -281,10 +295,26 @@ class Storage { DeallocateIfAllocated(); } + // --------------------------------------------------------------------------- + // Storage Member Accessors + // --------------------------------------------------------------------------- + + size_type& GetSizeAndIsAllocated() { return metadata_.template get<1>(); } + + const size_type& GetSizeAndIsAllocated() const { + return metadata_.template get<1>(); + } + size_type GetSize() const { return GetSizeAndIsAllocated() >> 1; } bool GetIsAllocated() const { return GetSizeAndIsAllocated() & 1; } + pointer GetAllocatedData() { return data_.allocated.allocated_data; } + + const_pointer GetAllocatedData() const { + return data_.allocated.allocated_data; + } + pointer GetInlinedData() { return reinterpret_cast<pointer>( std::addressof(data_.inlined.inlined_data[0])); @@ -295,18 +325,12 @@ class Storage { std::addressof(data_.inlined.inlined_data[0])); } - pointer GetAllocatedData() { return data_.allocated.allocated_data; } - - const_pointer GetAllocatedData() const { - return data_.allocated.allocated_data; - } - - size_type GetInlinedCapacity() const { return static_cast<size_type>(N); } - size_type GetAllocatedCapacity() const { return data_.allocated.allocated_capacity; } + size_type GetInlinedCapacity() const { return static_cast<size_type>(N); } + StorageView MakeStorageView() { return GetIsAllocated() ? StorageView{GetAllocatedData(), GetSize(), @@ -322,30 +346,63 @@ class Storage { return std::addressof(metadata_.template get<0>()); } - void SetIsAllocated() { GetSizeAndIsAllocated() |= 1; } + // --------------------------------------------------------------------------- + // Storage Member Mutators + // --------------------------------------------------------------------------- - void UnsetIsAllocated() { - SetIsAllocated(); - GetSizeAndIsAllocated() -= 1; - } + template <typename ValueAdapter> + void Initialize(ValueAdapter values, size_type new_size); - void SetAllocatedSize(size_type size) { - GetSizeAndIsAllocated() = (size << 1) | static_cast<size_type>(1); + template <typename ValueAdapter> + void Assign(ValueAdapter values, size_type new_size); + + template <typename ValueAdapter> + void Resize(ValueAdapter values, size_type new_size); + + template <typename ValueAdapter> + iterator Insert(const_iterator pos, ValueAdapter values, + size_type insert_count); + + template <typename... Args> + reference EmplaceBack(Args&&... args); + + iterator Erase(const_iterator from, const_iterator to); + + void Reserve(size_type requested_capacity); + + void ShrinkToFit(); + + void Swap(Storage* other_storage_ptr); + + void SetIsAllocated() { + GetSizeAndIsAllocated() |= static_cast<size_type>(1); } - void SetInlinedSize(size_type size) { GetSizeAndIsAllocated() = size << 1; } + void UnsetIsAllocated() { + GetSizeAndIsAllocated() &= ((std::numeric_limits<size_type>::max)() - 1); + } void SetSize(size_type size) { GetSizeAndIsAllocated() = (size << 1) | static_cast<size_type>(GetIsAllocated()); } - void AddSize(size_type count) { GetSizeAndIsAllocated() += count << 1; } + void SetAllocatedSize(size_type size) { + GetSizeAndIsAllocated() = (size << 1) | static_cast<size_type>(1); + } + + void SetInlinedSize(size_type size) { + GetSizeAndIsAllocated() = size << static_cast<size_type>(1); + } + + void AddSize(size_type count) { + GetSizeAndIsAllocated() += count << static_cast<size_type>(1); + } void SubtractSize(size_type count) { assert(count <= GetSize()); - GetSizeAndIsAllocated() -= count << 1; + GetSizeAndIsAllocated() -= count << static_cast<size_type>(1); } void SetAllocatedData(pointer data, size_type capacity) { @@ -353,14 +410,7 @@ class Storage { data_.allocated.allocated_capacity = capacity; } - void DeallocateIfAllocated() { - if (GetIsAllocated()) { - AllocatorTraits::deallocate(*GetAllocPtr(), GetAllocatedData(), - GetAllocatedCapacity()); - } - } - - void AcquireAllocation(AllocationTransaction* allocation_tx_ptr) { + void AcquireAllocatedData(AllocationTransaction* allocation_tx_ptr) { SetAllocatedData(allocation_tx_ptr->GetData(), allocation_tx_ptr->GetCapacity()); allocation_tx_ptr->GetData() = nullptr; @@ -374,46 +424,14 @@ class Storage { data_ = other_storage.data_; } - template <typename ValueAdapter> - void Initialize(ValueAdapter values, size_type new_size); - - template <typename ValueAdapter> - void Assign(ValueAdapter values, size_type new_size); - - template <typename ValueAdapter> - void Resize(ValueAdapter values, size_type new_size); - - template <typename ValueAdapter> - iterator Insert(const_iterator pos, ValueAdapter values, - size_type insert_count); - - template <typename... Args> - reference EmplaceBack(Args&&... args); - - iterator Erase(const_iterator from, const_iterator to); - - void Reserve(size_type requested_capacity); - - void ShrinkToFit(); - - void Swap(Storage* other_storage_ptr); - - private: - size_type& GetSizeAndIsAllocated() { return metadata_.template get<1>(); } - - const size_type& GetSizeAndIsAllocated() const { - return metadata_.template get<1>(); - } - - static size_type NextCapacity(size_type current_capacity) { - return current_capacity * 2; - } - - static size_type ComputeCapacity(size_type current_capacity, - size_type requested_capacity) { - return (std::max)(NextCapacity(current_capacity), requested_capacity); + void DeallocateIfAllocated() { + if (GetIsAllocated()) { + AllocatorTraits::deallocate(*GetAllocPtr(), GetAllocatedData(), + GetAllocatedCapacity()); + } } + private: using Metadata = container_internal::CompressedTuple<allocator_type, size_type>; @@ -508,7 +526,7 @@ auto Storage<T, N, A>::Assign(ValueAdapter values, size_type new_size) -> void { if (allocation_tx.DidAllocate()) { DeallocateIfAllocated(); - AcquireAllocation(&allocation_tx); + AcquireAllocatedData(&allocation_tx); SetIsAllocated(); } @@ -557,7 +575,7 @@ auto Storage<T, N, A>::Resize(ValueAdapter values, size_type new_size) -> void { construction_tx.Commit(); if (allocation_tx.DidAllocate()) { DeallocateIfAllocated(); - AcquireAllocation(&allocation_tx); + AcquireAllocatedData(&allocation_tx); SetIsAllocated(); } @@ -600,7 +618,7 @@ auto Storage<T, N, A>::Insert(const_iterator pos, ValueAdapter values, construction_tx.Commit(); move_construciton_tx.Commit(); DeallocateIfAllocated(); - AcquireAllocation(&allocation_tx); + AcquireAllocatedData(&allocation_tx); SetAllocatedSize(new_size); return iterator(new_data + insert_index); @@ -697,7 +715,7 @@ auto Storage<T, N, A>::EmplaceBack(Args&&... args) -> reference { storage_view.size); DeallocateIfAllocated(); - AcquireAllocation(&allocation_tx); + AcquireAllocatedData(&allocation_tx); SetIsAllocated(); } @@ -754,7 +772,7 @@ auto Storage<T, N, A>::Reserve(size_type requested_capacity) -> void { storage_view.size); DeallocateIfAllocated(); - AcquireAllocation(&allocation_tx); + AcquireAllocatedData(&allocation_tx); SetIsAllocated(); } @@ -800,7 +818,7 @@ auto Storage<T, N, A>::ShrinkToFit() -> void { storage_view.capacity); if (allocation_tx.DidAllocate()) { - AcquireAllocation(&allocation_tx); + AcquireAllocatedData(&allocation_tx); } else { UnsetIsAllocated(); } |