24 #ifndef PSS_ASTROTYPES_MULTIARRAY_DATABUFFER_H
25 #define PSS_ASTROTYPES_MULTIARRAY_DATABUFFER_H
28 namespace astrotypes {
31 template<typename T, typename Alloc, typename use_std_vec=!std::is_pod<T>::type>
32 class DataBufferImpl {
35 template<
typename T,
typename Alloc>
36 class DataBufferImpl<T, Alloc, true> :
public std::vector<T, Alloc>
39 using std::vector<T,Alloc>::vector;
43 template<
typename T,
typename Alloc>
44 class DataBufferImplAllocator<T, Alloc>
47 DataBufferImplAllocator(Alloc
const& alloc) : public Alloc
54 std::size_t size()
const {
69 template<
typename T,
typename Alloc>
70 class DataBufferImpl<T, Alloc, false>
73 DataBufferImpl(std::size_t n,
const Alloc& = Alloc())
77 this->_m_alloc._m_start = this->_m_allocate(n);
78 this->_m_alloc._m_finish =
this _m_alloc._m_start;
79 this->_m_alloc._m_end_of_storage = this->_m_alloc._m_start + n;
83 DataBufferImpl(
const Alloc& = Alloc())
90 this->_m_alloc.deallocate();
93 std::size_t capacity()
const {
94 return this->_m_alloc._m_end_of_storage - this->_m_alloc._m_start;;
97 std::size_t size()
const {
98 return this->_m_alloc.size();
101 std::size_t max_size()
const {
102 return this->_m_alloc.max_size();
105 void resize(std::size_t size) {
107 erase_at_end(_m_alloc._m_start + size);
110 T& operator[](std::size_t n) {
111 return *(this->_m_alloc._m_start + n);
114 T
const & operator[](std::size_t n)
const {
115 return *(this->_m_alloc._m_start + n);
118 T* begin() {
return this->_m_alloc._m_start; };
119 T* end() {
return this->_m_alloc._m_finish; };
121 T& front() {
return *begin(); }
122 T
const& front()
const {
return *begin(); }
123 T& back() {
return *(end() - 1); }
124 T
const& back()
const {
return *(end() - 1); }
126 void push_back(
const T& x)
128 if (this->_m_alloc._m_finish != this->_m_alloc._m_end_of_storage)
132 this->_m_alloc._m_finish = x;
133 ++this->_m_alloc._m_finish;
138 --this->_m_alloc._m_finish;
141 void emplace_back(T&& x)
143 this->_m_alloc._m_finish = std::move(x);
144 ++this->_m_alloc._m_finish;
148 this->_m_alloc._m_finish == this->_m_alloc._m_start;
151 void reserve(std::size_t s) {
152 if(s > this->max_size())
153 throw std::bad_alloc();
154 if(s > this->capacity())
161 T* m_allocate(
size_t n) {
162 return _m_alloc.allocate(n);
165 void m_deallocate(T* p,
size_t n)
167 if(p) _m_alloc.deallocate(p, n);
170 void m_extend(std::size_t len)
172 T* new_start(this->m_allocate(len));
173 T* new_finish(size() + new_start);
175 std::copy(begin(), end(), new_start);
178 this->m_deallocate(this->_m_alloc._m_start, len);
181 this->_m_alloc.deallocate();
185 std::size_t
const old_size = size();
186 if(old_size==max_size()) {
187 throw std::bad_alloc();
189 std::size_t len = old_size != 0 ? 2 * old_size : 2;
191 len = this->max_size();
196 DataBufferImplAllocator _m_alloc;
211 template<
typename T,
typename Alloc>
223 #endif // PSS_ASTROTYPES_MULTIARRAY_DATABUFFER_H
a std::vector that does not initialise its members when they are plain old data (i.e. float, int,...)