OpenVDB  4.0.2
PagedArray.h
Go to the documentation of this file.
1 //
3 // Copyright (c) 2012-2017 DreamWorks Animation LLC
4 //
5 // All rights reserved. This software is distributed under the
6 // Mozilla Public License 2.0 ( http://www.mozilla.org/MPL/2.0/ )
7 //
8 // Redistributions of source code must retain the above copyright
9 // and license notice and the following restrictions and disclaimer.
10 //
11 // * Neither the name of DreamWorks Animation nor the names of
12 // its contributors may be used to endorse or promote products derived
13 // from this software without specific prior written permission.
14 //
15 // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
16 // "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
17 // LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
18 // A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
19 // OWNER OR CONTRIBUTORS BE LIABLE FOR ANY INDIRECT, INCIDENTAL,
20 // SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
21 // LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
22 // DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
23 // THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
24 // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
25 // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26 // IN NO EVENT SHALL THE COPYRIGHT HOLDERS' AND CONTRIBUTORS' AGGREGATE
27 // LIABILITY FOR ALL CLAIMS REGARDLESS OF THEIR BASIS EXCEED US$250.00.
28 //
41 
42 #ifndef OPENVDB_UTIL_PAGED_ARRAY_HAS_BEEN_INCLUDED
43 #define OPENVDB_UTIL_PAGED_ARRAY_HAS_BEEN_INCLUDED
44 
45 #include <vector>
46 #include <cassert>
47 #include <iostream>
48 #include <algorithm>// std::swap
49 #include <tbb/atomic.h>
50 #include <tbb/spin_mutex.h>
51 #include <tbb/parallel_for.h>
52 #include <tbb/parallel_sort.h>
53 
54 namespace openvdb {
56 namespace OPENVDB_VERSION_NAME {
57 namespace util {
58 
60 
61 
184 
185 template<typename ValueT,
186  size_t Log2PageSize = 10UL,
187  template<typename ...> class TableT = std::vector>
189 {
190 private:
191  class Page;
192 
193 #if defined(__INTEL_COMPILER) && __INTEL_COMPILER < 1700
194  // Workaround for ICC 15/16 "too few arguments to template" bug (fixed in ICC 17)
195  using PageTableT = TableT<Page*, std::allocator<Page*>>;
196 #else
197  using PageTableT = TableT<Page*>;
198 #endif
199 
200 public:
201  typedef ValueT ValueType;
202 
204  PagedArray() = default;
205 
207  ~PagedArray() { this->clear(); }
208 
209  // Disallow copy construction and assignment
210  PagedArray(const PagedArray&) = delete;
211  PagedArray& operator=(const PagedArray&) = delete;
212 
221  class ValueBuffer;
222 
224  class ConstIterator;
225 
227  class Iterator;
228 
236  size_t push_back(const ValueType& value)
237  {
238  const size_t index = mSize.fetch_and_increment();
239  if (index >= mCapacity) this->grow(index);
240  (*mPageTable[index >> Log2PageSize])[index] = value;
241  return index;
242  }
243 
251  size_t push_back_unsafe(const ValueType& value)
252  {
253  const size_t index = mSize.fetch_and_increment();
254  if (index >= mCapacity) {
255  mPageTable.push_back( new Page() );
256  mCapacity += Page::Size;
257  }
258  (*mPageTable[index >> Log2PageSize])[index] = value;
259  return index;
260  }
261 
283  {
284  assert(mSize>0);
285  --mSize;
286  return (*mPageTable[mSize >> Log2PageSize])[mSize];
287  }
288 
289 
293  void shrink_to_fit();
294 
303  {
304  assert(i<mCapacity);
305  return (*mPageTable[i>>Log2PageSize])[i];
306  }
307 
315  const ValueType& operator[](size_t i) const
316  {
317  assert(i<mCapacity);
318  return (*mPageTable[i>>Log2PageSize])[i];
319  }
320 
326  void fill(const ValueType& v)
327  {
328  auto op = [&](const tbb::blocked_range<size_t>& r){
329  for(size_t i=r.begin(); i!=r.end(); ++i) mPageTable[i]->fill(v);
330  };
331  tbb::parallel_for(tbb::blocked_range<size_t>(0, this->pageCount()), op);
332  }
333 
341  bool copy(ValueType *p, size_t count) const
342  {
343  size_t last_page = count >> Log2PageSize;
344  if (last_page >= this->pageCount()) return false;
345  auto op = [&](const tbb::blocked_range<size_t>& r){
346  for (size_t i=r.begin(); i!=r.end(); ++i) {
347  mPageTable[i]->copy(p+i*Page::Size, Page::Size);
348  }
349  };
350  if (size_t m = count & Page::Mask) {//count is not divisible by page size
351  tbb::parallel_for(tbb::blocked_range<size_t>(0, last_page, 32), op);
352  mPageTable[last_page]->copy(p+last_page*Page::Size, m);
353  } else {
354  tbb::parallel_for(tbb::blocked_range<size_t>(0, last_page+1, 32), op);
355  }
356  return true;
357  }
358  void copy(ValueType *p) const { this->copy(p, mSize); }
359 
374  void resize(size_t size)
375  {
376  mSize = size;
377  if (size > mCapacity) {
378  this->grow(size-1);
379  } else {
380  this->shrink_to_fit();
381  }
382  }
383 
399  void resize(size_t size, const ValueType& v)
400  {
401  this->resize(size);
402  this->fill(v);
403  }
404 
406  size_t size() const { return mSize; }
407 
410  size_t capacity() const { return mCapacity; }
411 
414  size_t freeCount() const { return mCapacity - mSize; }
415 
417  size_t pageCount() const { return mPageTable.size(); }
418 
420  static size_t pageSize() { return Page::Size; }
421 
423  static size_t log2PageSize() { return Log2PageSize; }
424 
426  size_t memUsage() const
427  {
428  return sizeof(*this) + mPageTable.size() * Page::memUsage();
429  }
430 
432  bool isEmpty() const { return mSize == 0; }
433 
440  bool isPartiallyFull() const { return (mSize & Page::Mask) > 0; }
441 
445  void clear()
446  {
447  for (size_t i=0, n=mPageTable.size(); i<n; ++i) delete mPageTable[i];
448  PageTableT().swap(mPageTable);
449  mSize = 0;
450  mCapacity = 0;
451  }
452 
454  Iterator begin() { return Iterator(*this, 0); }
455 
461  Iterator end() { return Iterator(*this, mSize); }
462 
464  ConstIterator cbegin() const { return ConstIterator(*this, 0); }
466  ConstIterator begin() const { return ConstIterator(*this, 0); }
468 
470  ConstIterator cend() const { return ConstIterator(*this, mSize); }
476  ConstIterator end() const { return ConstIterator(*this, mSize); }
478 
480  void sort() { tbb::parallel_sort(this->begin(), this->end(), std::less<ValueT>() ); }
481 
483  void invSort() { tbb::parallel_sort(this->begin(), this->end(), std::greater<ValueT>()); }
484 
486  template <typename Functor>
491  void sort(Functor func) { tbb::parallel_sort(this->begin(), this->end(), func ); }
493 
501  void merge(PagedArray& other);
502 
504  void print(std::ostream& os = std::cout) const
505  {
506  os << "PagedArray:\n"
507  << "\tSize: " << this->size() << " elements\n"
508  << "\tPage table: " << this->pageCount() << " pages\n"
509  << "\tPage size: " << this->pageSize() << " elements\n"
510  << "\tCapacity: " << this->capacity() << " elements\n"
511  << "\tFootprint: " << this->memUsage() << " bytes\n";
512  }
513 
514 private:
515 
516  friend class ValueBuffer;
517 
518  void grow(size_t index)
519  {
520  tbb::spin_mutex::scoped_lock lock(mGrowthMutex);
521  while(index >= mCapacity) {
522  mPageTable.push_back( new Page() );
523  mCapacity += Page::Size;
524  }
525  }
526 
527  void add_full(Page*& page, size_t size);
528 
529  void add_partially_full(Page*& page, size_t size);
530 
531  void add(Page*& page, size_t size) {
532  tbb::spin_mutex::scoped_lock lock(mGrowthMutex);
533  if (size == Page::Size) {//page is full
534  this->add_full(page, size);
535  } else if (size>0) {//page is only partially full
536  this->add_partially_full(page, size);
537  }
538  }
539  PageTableT mPageTable;//holds points to allocated pages
540  tbb::atomic<size_t> mSize{0};// current number of elements in array
541  size_t mCapacity = 0;//capacity of array given the current page count
542  tbb::spin_mutex mGrowthMutex;//Mutex-lock required to grow pages
543 }; // Public class PagedArray
544 
546 
547 template <typename ValueT, size_t Log2PageSize, template<typename ...> class TableT>
549 {
550  if (mPageTable.size() > (mSize >> Log2PageSize) + 1) {
551  tbb::spin_mutex::scoped_lock lock(mGrowthMutex);
552  const size_t pageCount = (mSize >> Log2PageSize) + 1;
553  if (mPageTable.size() > pageCount) {
554  delete mPageTable.back();
555  mPageTable.pop_back();
556  mCapacity -= Page::Size;
557  }
558  }
559 }
560 
561 template <typename ValueT, size_t Log2PageSize, template<typename ...> class TableT>
563 {
564  if (&other != this && !other.isEmpty()) {
565  tbb::spin_mutex::scoped_lock lock(mGrowthMutex);
566  // extract last partially full page if it exists
567  Page* page = nullptr;
568  const size_t size = mSize & Page::Mask; //number of elements in the last page
569  if ( size > 0 ) {
570  page = mPageTable.back();
571  mPageTable.pop_back();
572  mSize -= size;
573  }
574  // transfer all pages from the other page table
575  mPageTable.insert(mPageTable.end(), other.mPageTable.begin(), other.mPageTable.end());
576  mSize += other.mSize;
577  mCapacity = Page::Size*mPageTable.size();
578  other.mSize = 0;
579  other.mCapacity = 0;
580  PageTableT().swap(other.mPageTable);
581  // add back last partially full page
582  if (page) this->add_partially_full(page, size);
583  }
584 }
585 
586 template <typename ValueT, size_t Log2PageSize, template<typename ...> class TableT>
588 {
589  assert(size == Page::Size);//page must be full
590  if (mSize & Page::Mask) {//page-table is partially full
591  Page*& tmp = mPageTable.back();
592  std::swap(tmp, page);//swap last table entry with page
593  }
594  mPageTable.push_back(page);
595  mCapacity += Page::Size;
596  mSize += size;
597  page = nullptr;
598 }
599 
600 template <typename ValueT, size_t Log2PageSize, template<typename ...> class TableT>
601 void PagedArray<ValueT, Log2PageSize, TableT>::add_partially_full(Page*& page, size_t size)
602 {
603  assert(size > 0 && size < Page::Size);//page must be partially full
604  if (size_t m = mSize & Page::Mask) {//page table is also partially full
605  ValueT *s = page->data(), *t = mPageTable.back()->data() + m;
606  for (size_t i=std::min(mSize+size, mCapacity)-mSize; i; --i) *t++ = *s++;
607  if (mSize+size > mCapacity) {//grow page table
608  mPageTable.push_back( new Page() );
609  t = mPageTable.back()->data();
610  for (size_t i=mSize+size-mCapacity; i; --i) *t++ = *s++;
611  mCapacity += Page::Size;
612  }
613  } else {//page table is full so simply append page
614  mPageTable.push_back( page );
615  mCapacity += Page::Size;
616  page = nullptr;
617  }
618  mSize += size;
619 }
620 
622 
623 // Public member-class of PagedArray
624 template <typename ValueT, size_t Log2PageSize, template<typename ...> class TableT>
625 class PagedArray<ValueT, Log2PageSize, TableT>::
627 {
628 public:
631  ValueBuffer(PagedArray& parent) : mParent(&parent), mPage(new Page()), mSize(0) {}
634  ValueBuffer(const ValueBuffer& other) : mParent(other.mParent), mPage(new Page()), mSize(0) {}
636  ~ValueBuffer() { mParent->add(mPage, mSize); delete mPage; }
637 
638  ValueBuffer& operator=(const ValueBuffer&) = delete;// disallow copy assignment
639 
644  void push_back(const ValueT& v) {
645  (*mPage)[mSize++] = v;
646  if (mSize == Page::Size) this->flush();
647  }
653  void flush() {
654  mParent->add(mPage, mSize);
655  if (mPage == nullptr) mPage = new Page();
656  mSize = 0;
657  }
659  PagedArrayType& parent() const { return *mParent; }
661  size_t size() const { return mSize; }
662 private:
663  PagedArray* mParent;
664  Page* mPage;
665  size_t mSize;
666 };// Public class PagedArray::ValueBuffer
667 
669 
670 // Const std-compliant iterator
671 // Public member-class of PagedArray
672 template <typename ValueT, size_t Log2PageSize, template<typename ...> class TableT>
673 class PagedArray<ValueT, Log2PageSize, TableT>::
674 ConstIterator : public std::iterator<std::random_access_iterator_tag, ValueT>
675 {
676 public:
677  typedef std::iterator<std::random_access_iterator_tag, ValueT> BaseT;
678  typedef typename BaseT::difference_type difference_type;
679  // constructors and assignment
680  ConstIterator() : mPos(0), mParent(nullptr) {}
681  ConstIterator(const PagedArray& parent, size_t pos=0) : mPos(pos), mParent(&parent) {}
682  ConstIterator(const ConstIterator& other) : mPos(other.mPos), mParent(other.mParent) {}
684  mPos=other.mPos;
685  mParent=other.mParent;
686  return *this;
687  }
688  // prefix
689  ConstIterator& operator++() { ++mPos; return *this; }
690  ConstIterator& operator--() { --mPos; return *this; }
691  // postfix
692  ConstIterator operator++(int) { ConstIterator tmp(*this); ++mPos; return tmp; }
693  ConstIterator operator--(int) { ConstIterator tmp(*this); --mPos; return tmp; }
694  // value access
695  const ValueT& operator*() const { return (*mParent)[mPos]; }
696  const ValueT* operator->() const { return &(this->operator*()); }
697  const ValueT& operator[](const difference_type& pos) const { return (*mParent)[mPos+pos]; }
698  // offset
699  ConstIterator& operator+=(const difference_type& pos) { mPos += pos; return *this; }
700  ConstIterator& operator-=(const difference_type& pos) { mPos -= pos; return *this; }
701  ConstIterator operator+(const difference_type &pos) const { return Iterator(*mParent,mPos+pos); }
702  ConstIterator operator-(const difference_type &pos) const { return Iterator(*mParent,mPos-pos); }
703  difference_type operator-(const ConstIterator& other) const { return mPos - other.pos(); }
704  // comparisons
705  bool operator==(const ConstIterator& other) const { return mPos == other.mPos; }
706  bool operator!=(const ConstIterator& other) const { return mPos != other.mPos; }
707  bool operator>=(const ConstIterator& other) const { return mPos >= other.mPos; }
708  bool operator<=(const ConstIterator& other) const { return mPos <= other.mPos; }
709  bool operator< (const ConstIterator& other) const { return mPos < other.mPos; }
710  bool operator> (const ConstIterator& other) const { return mPos > other.mPos; }
711  // non-std methods
712  bool isValid() const { return mParent != nullptr && mPos < mParent->size(); }
713  size_t pos() const { return mPos; }
714 private:
715  size_t mPos;
716  const PagedArray* mParent;
717 };// Public class PagedArray::ConstIterator
718 
720 
721 // Non-const std-compliant iterator
722 // Public member-class of PagedArray
723 template <typename ValueT, size_t Log2PageSize, template<typename ...> class TableT>
724 class PagedArray<ValueT, Log2PageSize, TableT>::
725 Iterator : public std::iterator<std::random_access_iterator_tag, ValueT>
726 {
727 public:
728  typedef std::iterator<std::random_access_iterator_tag, ValueT> BaseT;
729  typedef typename BaseT::difference_type difference_type;
730  // constructors and assignment
731  Iterator() : mPos(0), mParent(nullptr) {}
732  Iterator(PagedArray& parent, size_t pos=0) : mPos(pos), mParent(&parent) {}
733  Iterator(const Iterator& other) : mPos(other.mPos), mParent(other.mParent) {}
734  Iterator& operator=(const Iterator& other) {
735  mPos=other.mPos;
736  mParent=other.mParent;
737  return *this;
738  }
739  // prefix
740  Iterator& operator++() { ++mPos; return *this; }
741  Iterator& operator--() { --mPos; return *this; }
742  // postfix
743  Iterator operator++(int) { Iterator tmp(*this); ++mPos; return tmp; }
744  Iterator operator--(int) { Iterator tmp(*this); --mPos; return tmp; }
745  // value access
746  ValueT& operator*() const { return (*mParent)[mPos]; }
747  ValueT* operator->() const { return &(this->operator*()); }
748  ValueT& operator[](const difference_type& pos) const { return (*mParent)[mPos+pos]; }
749  // offset
750  Iterator& operator+=(const difference_type& pos) { mPos += pos; return *this; }
751  Iterator& operator-=(const difference_type& pos) { mPos -= pos; return *this; }
752  Iterator operator+(const difference_type &pos) const { return Iterator(*mParent, mPos+pos); }
753  Iterator operator-(const difference_type &pos) const { return Iterator(*mParent, mPos-pos); }
754  difference_type operator-(const Iterator& other) const { return mPos - other.pos(); }
755  // comparisons
756  bool operator==(const Iterator& other) const { return mPos == other.mPos; }
757  bool operator!=(const Iterator& other) const { return mPos != other.mPos; }
758  bool operator>=(const Iterator& other) const { return mPos >= other.mPos; }
759  bool operator<=(const Iterator& other) const { return mPos <= other.mPos; }
760  bool operator< (const Iterator& other) const { return mPos < other.mPos; }
761  bool operator> (const Iterator& other) const { return mPos > other.mPos; }
762  // non-std methods
763  bool isValid() const { return mParent != nullptr && mPos < mParent->size(); }
764  size_t pos() const { return mPos; }
765  private:
766  size_t mPos;
767  PagedArray* mParent;
768 };// Public class PagedArray::Iterator
769 
771 
772 // Private member-class of PagedArray implementing a memory page
773 template <typename ValueT, size_t Log2PageSize, template<typename ...> class TableT>
774 class PagedArray<ValueT, Log2PageSize, TableT>::
775 Page
776 {
777 public:
778  static const size_t Size = 1UL << Log2PageSize;
779  static const size_t Mask = Size - 1UL;
780  static size_t memUsage() { return sizeof(ValueT)*Size; }
781  // Raw memory allocation without any initialization
782  Page() : mData(reinterpret_cast<ValueT*>(new char[sizeof(ValueT)*Size])) {}
783  ~Page() { delete [] mData; }
784  Page(const Page&) = delete;//copy construction is not implemented
785  Page& operator=(const Page&) = delete;//copy assignment is not implemented
786  ValueT& operator[](const size_t i) { return mData[i & Mask]; }
787  const ValueT& operator[](const size_t i) const { return mData[i & Mask]; }
788  void fill(const ValueT& v) {
789  ValueT* dst = mData;
790  for (size_t i=Size; i; --i) *dst++ = v;
791  }
792  ValueT* data() { return mData; }
793  // Copy the first n elements of this Page to dst (which is assumed to large
794  // enough to hold the n elements).
795  void copy(ValueType *dst, size_t n) const {
796  const ValueT* src = mData;
797  for (size_t i=n; i; --i) *dst++ = *src++;
798  }
799 protected:
800  ValueT* mData;
801 };// Private class PagedArray::Page
802 
804 
805 } // namespace util
806 } // namespace OPENVDB_VERSION_NAME
807 } // namespace openvdb
808 
809 #endif // OPENVDB_UTIL_PAGED_ARRAY_HAS_BEEN_INCLUDED
810 
811 // Copyright (c) 2012-2017 DreamWorks Animation LLC
812 // All rights reserved. This software is distributed under the
813 // Mozilla Public License 2.0 ( http://www.mozilla.org/MPL/2.0/ )
~PagedArray()
Destructor removed all allocated pages.
Definition: PagedArray.h:207
bool operator>(const Tuple< SIZE, T0 > &t0, const Tuple< SIZE, T1 > &t1)
Definition: Tuple.h:218
ConstIterator & operator=(const ConstIterator &other)
Definition: PagedArray.h:683
size_t pos() const
Definition: PagedArray.h:713
Definition: PagedArray.h:774
bool isValid() const
Definition: PagedArray.h:763
#define OPENVDB_DEPRECATED
Definition: Platform.h:49
size_t push_back(const ValueType &value)
Thread safe insertion, adds a new element at the end and increases the container size by one and retu...
Definition: PagedArray.h:236
bool copy(ValueType *p, size_t count) const
Copy the first count values in this PageArray into a raw c-style array, assuming it to be at least co...
Definition: PagedArray.h:341
void sort()
Parallel sort of all the elements in ascending order.
Definition: PagedArray.h:480
Iterator begin()
Return a non-const iterator pointing to the first element.
Definition: PagedArray.h:454
ValueT & operator[](const size_t i)
Definition: PagedArray.h:786
void fill(const ValueT &v)
Definition: PagedArray.h:788
ValueBuffer(const ValueBuffer &other)
Definition: PagedArray.h:634
ConstIterator & operator--()
Definition: PagedArray.h:690
const ValueT & operator[](const size_t i) const
Definition: PagedArray.h:787
ConstIterator end() const
Return a const iterator pointing to the past-the-last element.
Definition: PagedArray.h:476
BaseT::difference_type difference_type
Definition: PagedArray.h:678
size_t freeCount() const
Return the number of additional elements that can be added to this array without allocating more memo...
Definition: PagedArray.h:414
tbb::atomic< Index32 > i
Definition: LeafBuffer.h:71
void print(std::ostream &os=std::cout) const
Print information for debugging.
Definition: PagedArray.h:504
Iterator operator--(int)
Definition: PagedArray.h:744
std::iterator< std::random_access_iterator_tag, ValueT > BaseT
Definition: PagedArray.h:677
size_t size() const
Return the current number of elements cached in this buffer.
Definition: PagedArray.h:661
bool operator>=(const ConstIterator &other) const
Definition: PagedArray.h:707
Iterator operator++(int)
Definition: PagedArray.h:743
void push_back(const ValueT &v)
Add a value to the buffer and increment the size.
Definition: PagedArray.h:644
const ValueType & operator[](size_t i) const
Return a const-reference to the value at the specified offset.
Definition: PagedArray.h:315
bool operator==(const Iterator &other) const
Definition: PagedArray.h:756
size_t push_back_unsafe(const ValueType &value)
Slightly faster than the thread-safe push_back above.
Definition: PagedArray.h:251
ValueT * operator->() const
Definition: PagedArray.h:747
size_t pos() const
Definition: PagedArray.h:764
ValueT & operator*() const
Definition: PagedArray.h:746
Iterator(const Iterator &other)
Definition: PagedArray.h:733
ConstIterator begin() const
Return a const iterator pointing to the first element.
Definition: PagedArray.h:466
ConstIterator(const ConstIterator &other)
Definition: PagedArray.h:682
bool operator==(const ConstIterator &other) const
Definition: PagedArray.h:705
bool operator<=(const ConstIterator &other) const
Definition: PagedArray.h:708
ConstIterator & operator++()
Definition: PagedArray.h:689
PagedArray< ValueT, Log2PageSize, TableT > PagedArrayType
Definition: PagedArray.h:629
const std::enable_if<!VecTraits< T >::IsVec, T >::type & min(const T &a, const T &b)
Definition: Composite.h:129
ConstIterator operator--(int)
Definition: PagedArray.h:693
size_t size() const
Return the number of elements in this array.
Definition: PagedArray.h:406
void copy(ValueType *p) const
Definition: PagedArray.h:358
const ValueT & operator*() const
Definition: PagedArray.h:695
ConstIterator & operator+=(const difference_type &pos)
Definition: PagedArray.h:699
difference_type operator-(const ConstIterator &other) const
Definition: PagedArray.h:703
Iterator & operator=(const Iterator &other)
Definition: PagedArray.h:734
size_t capacity() const
Return the maximum number of elements that this array can contain without allocating more memory page...
Definition: PagedArray.h:410
Iterator operator+(const difference_type &pos) const
Definition: PagedArray.h:752
#define OPENVDB_VERSION_NAME
Definition: version.h:43
std::iterator< std::random_access_iterator_tag, ValueT > BaseT
Definition: PagedArray.h:728
OPENVDB_DEPRECATED ValueType pop_back()
Returns the last element, decrements the size by one.
Definition: PagedArray.h:282
ConstIterator()
Definition: PagedArray.h:680
bool isValid() const
Definition: PagedArray.h:712
bool isPartiallyFull() const
Return true if the page table is partially full, i.e. the last non-empty page contains less than page...
Definition: PagedArray.h:440
ConstIterator & operator-=(const difference_type &pos)
Definition: PagedArray.h:700
void copy(ValueType *dst, size_t n) const
Definition: PagedArray.h:795
Iterator()
Definition: PagedArray.h:731
bool operator<(const Tuple< SIZE, T0 > &t0, const Tuple< SIZE, T1 > &t1)
Definition: Tuple.h:206
void clear()
Removes all elements from the array and delete all pages.
Definition: PagedArray.h:445
Definition: Exceptions.h:39
ValueType & operator[](size_t i)
Return a reference to the value at the specified offset.
Definition: PagedArray.h:302
ConstIterator(const PagedArray &parent, size_t pos=0)
Definition: PagedArray.h:681
Concurrent, page-based, dynamically-sized linear data structure with O(1) random access and STL-compl...
Definition: PagedArray.h:188
~Page()
Definition: PagedArray.h:783
bool operator>=(const Iterator &other) const
Definition: PagedArray.h:758
size_t pageCount() const
Return the number of allocated memory pages.
Definition: PagedArray.h:417
const ValueT & operator[](const difference_type &pos) const
Definition: PagedArray.h:697
bool operator<=(const Iterator &other) const
Definition: PagedArray.h:759
ValueT ValueType
Definition: PagedArray.h:201
void fill(const ValueType &v)
Set all elements in the page table to the specified value.
Definition: PagedArray.h:326
Iterator(PagedArray &parent, size_t pos=0)
Definition: PagedArray.h:732
void resize(size_t size)
Resize this array to the specified size.
Definition: PagedArray.h:374
static size_t log2PageSize()
Return log2 of the number of elements per memory page.
Definition: PagedArray.h:423
ConstIterator operator++(int)
Definition: PagedArray.h:692
PagedArrayType & parent() const
Return a reference to the parent PagedArray.
Definition: PagedArray.h:659
Iterator & operator+=(const difference_type &pos)
Definition: PagedArray.h:750
ConstIterator operator-(const difference_type &pos) const
Definition: PagedArray.h:702
static size_t pageSize()
Return the number of elements per memory page.
Definition: PagedArray.h:420
ConstIterator operator+(const difference_type &pos) const
Definition: PagedArray.h:701
bool operator!=(const ConstIterator &other) const
Definition: PagedArray.h:706
difference_type operator-(const Iterator &other) const
Definition: PagedArray.h:754
Mat3< typename promote< T0, T1 >::type > operator*(const Mat3< T0 > &m0, const Mat3< T1 > &m1)
Matrix multiplication.
Definition: Mat3.h:654
Iterator & operator-=(const difference_type &pos)
Definition: PagedArray.h:751
bool isEmpty() const
Return true if the container contains no elements.
Definition: PagedArray.h:432
~ValueBuffer()
Destructor that transfers an buffered values to the parent PagedArray.
Definition: PagedArray.h:636
ValueBuffer(PagedArray &parent)
Constructor from a PageArray.
Definition: PagedArray.h:631
ValueT * mData
Definition: PagedArray.h:800
void resize(size_t size, const ValueType &v)
Resize this array to the specified size and initialize all values to v.
Definition: PagedArray.h:399
void invSort()
Parallel sort of all the elements in descending order.
Definition: PagedArray.h:483
#define OPENVDB_USE_VERSION_NAMESPACE
Definition: version.h:71
Iterator end()
Return a non-const iterator pointing to the past-the-last element.
Definition: PagedArray.h:461
ValueT * data()
Definition: PagedArray.h:792
size_t memUsage() const
Return the memory footprint of this array in bytes.
Definition: PagedArray.h:426
static size_t memUsage()
Definition: PagedArray.h:780
const ValueT * operator->() const
Definition: PagedArray.h:696
ValueT & operator[](const difference_type &pos) const
Definition: PagedArray.h:748
void sort(Functor func)
Parallel sort of all the elements based on a custom functor with the api:
Definition: PagedArray.h:491
static constexpr size_t size
The size of a LeafBuffer when LeafBuffer::mOutOfCore is atomic.
Definition: LeafBuffer.h:85
BaseT::difference_type difference_type
Definition: PagedArray.h:729
Page()
Definition: PagedArray.h:782
Iterator & operator++()
Definition: PagedArray.h:740
void flush()
Manually transfers the values in this buffer to the parent PagedArray.
Definition: PagedArray.h:653
Iterator & operator--()
Definition: PagedArray.h:741
bool operator!=(const Iterator &other) const
Definition: PagedArray.h:757
Iterator operator-(const difference_type &pos) const
Definition: PagedArray.h:753