60 template <
class IDX>
const T&
getRef(
const IDX& index,
int val)
const;
63 template <
class IDX> T&
getRef(
const IDX& index,
int val);
66 template <
class V,
class POS,
class IDX>
67 bool add(
const V& vals,
const POS& pos,
70 template <
class V,
class POS>
bool add(
const V& vals,
const POS& pos);
73 template <
class IDX>
void remove(
const IDX& index);
77 template <
class POS,
class IDX>
bool findFirst(
const POS&,IDX&)
const;
78 template <
class IDX>
bool getIndex(
int global_pos,IDX&)
const;
79 template <
class IDX,
class POS>
bool getPos(
const IDX&,POS&)
const;
80 template <
class IDX>
bool next(IDX&,
bool skipdups=
false)
const;
81 template <
class IDX>
bool prev(IDX&,
bool skipdups=
false)
const;
118 template <
class T>
inline
122 , allowduplicates_( false )
126 template <
class T>
inline
146 template <
class T>
inline
153 template <
class T>
inline
158 if ( !positions_.arr() )
161 return !nrvals_ || onedimstorage_.arr();
164 for (
int idx=lowerdimstorage_.size()-1; idx>=0; idx-- )
166 if ( !lowerdimstorage_[idx]->isOK() )
174 template <
class T>
inline
178 onedimstorage_.erase();
183 template <
class T>
inline
189 for (
int idx=0; idx<b.
size(); idx++ )
191 const int pos = b.
getPos( idx );
192 int index = findFirstPos( pos );
194 const bool match = positions_.validIdx(index) && positions_[index]==pos;
201 if ( index==lowerdimstorage_.size() )
203 lowerdimstorage_ += newstorage;
211 lowerdimstorage_.insertAt( newstorage, index );
212 positions_.insert( index, pos );
217 if ( !lowerdimstorage_[index]->
append( *b[idx] ) )
232 template <
class T>
inline
234 {
return allowduplicates_; }
237 template <
class T>
inline
240 const bool res = allowduplicates_;
241 allowduplicates_ = nv;
242 for (
int idx=lowerdimstorage_.size()-1; idx>=0; idx-- )
243 lowerdimstorage_[idx]->allowDuplicates( nv );
252 template <
class T>
inline
256 return positions_.isEmpty();
258 for (
int idx=lowerdimstorage_.size()-1; idx>=0; idx-- )
259 if ( !lowerdimstorage_[idx]->
isEmpty() )
266 template <
class T>
inline
270 return positions_.size();
273 for (
int idx=lowerdimstorage_.size()-1; idx>=0; idx-- )
274 sum += lowerdimstorage_[idx]->totalSize();
280 template <
class T>
inline
283 return positions_.size();
287 template <
class T>
inline
290 if ( nrdims_==1 )
return 0;
291 return lowerdimstorage_[idx];
295 template <
class T>
inline
298 if ( nrdims_==1 )
return 0;
299 return lowerdimstorage_[idx];
303 template <
class T>
inline
305 {
return positions_.indexOf( pos ); }
308 template <
class T>
inline
310 {
return positions_[idx]; }
314 template <
class T>
inline
323 getRangeI( dim, rg );
329 template <
class T>
inline
335 if ( dim==nrdims_-1 )
337 const int sz = positions_.size();
338 rg.include( positions_[0],
false );
340 rg.include( positions_[sz-1],
false );
344 for (
int idx=0; idx<lowerdimstorage_.size(); idx++ )
345 lowerdimstorage_[idx]->getRangeI( dim, rg );
350 template <
class T>
inline
354 template <
class T>
inline
358 template <
class T>
inline
366 for (
int idx=lowerdimstorage_.size()-1; idx>=0; idx-- )
367 lowerdimstorage_[idx]->setNrVals( nn );
373 const int nrvalstocp =
mMIN( nn, nrvals_ );
374 const int nrpos = size();
378 for (
int idx=0; idx<nrpos; idx++ )
380 for (
int idy=0; idy<nrvalstocp; idy++ )
381 newstorage[idx*nn+idy] = onedimstorage_[idx*nrvals_+idy];
385 onedimstorage_ = newstorage;
390 template <
class T>
template <
class IDX>
inline
393 const int index = indexarr[nrdims_-1];
395 ? onedimstorage_[index*nrvals_+val]
396 : lowerdimstorage_[index]->getRef( indexarr, val );
400 template <
class T>
template <
class IDX>
inline
406 template <
class T>
template <
class V,
class POS,
class IDX>
inline
410 const int dim = nrdims_-1;
411 const int pos =
mCast(
int, posarr[dim] );
412 int index = findFirstPos( pos );
414 const bool match = positions_.validIdx(index) && positions_[index]==pos;
415 if ( !match ) index++;
417 if ( indexarr ) (*indexarr)[dim] = index;
426 if ( index==lowerdimstorage_.size() )
428 lowerdimstorage_ += newstorage;
436 lowerdimstorage_.insertAt( newstorage, index );
437 positions_.insert( index, pos );
441 if ( !lowerdimstorage_[index]->add( vals, posarr, indexarr ) )
446 if ( !match || (match && allowduplicates_) )
448 for (
int idx=0; idx<nrvals_; idx++ )
450 const int arrpos = index*nrvals_+idx;
451 if ( arrpos>onedimstorage_.size() || arrpos<0 )
453 else if ( arrpos==onedimstorage_.size() )
454 onedimstorage_ += vals[idx];
456 onedimstorage_.insert( index*nrvals_+idx, vals[idx] );
459 if ( index==positions_.size() )
462 positions_.insert( index, pos );
466 for (
int idx=0; idx<nrvals_; idx++ )
467 onedimstorage_[index*nrvals_+idx] = vals[idx];
475 template <
class T>
template <
class V,
class POS>
inline
478 return add<V,POS,int*>( vals, posarr, 0 );
482 template <
class T>
template<
class IDX>
inline
485 const int dim = nrdims_-1;
486 const int index = indexarr[dim];
490 lowerdimstorage_[index]->remove( indexarr );
491 if ( lowerdimstorage_[index]->size() )
494 delete lowerdimstorage_[index];
495 lowerdimstorage_.removeSingle( index );
496 positions_.removeSingle( index );
500 onedimstorage_.removeRange( index*nrvals_, index*nrvals_+nrvals_-1 );
501 positions_.removeSingle( index );
505 template <
class T>
template <
class POS,
class IDX>
inline
508 const int dim = nrdims_-1;
509 const int pos = posarr[dim];
510 const int index = findFirstPos( pos );
512 if ( index==-1 || positions_[index]!=pos )
515 indexarr[dim] = index;
517 return dim ? lowerdimstorage_[index]->findFirst( posarr, indexarr ) :
true;
521 template <
class T>
template <
class IDX,
class POS>
inline
524 const int dim = nrdims_-1;
525 int index = indexarr[dim];
526 if ( index>=positions_.size() )
529 pos[dim] = positions_[index];
530 return dim ? lowerdimstorage_[index]->getPos( indexarr, pos ) :
true;
534 template <
class T>
template <
class IDX>
inline
537 const int dim = nrdims_-1;
538 int& index = indexarr[dim];
542 for (
int idx=0; idx<lowerdimstorage_.size(); idx++ )
544 const int localsum = lowerdimstorage_[idx]->totalSize();
545 if ( globalpos<localsum )
548 return lowerdimstorage_[idx]->getIndex( globalpos, indexarr );
551 globalpos -= localsum;
557 if ( globalpos<positions_.size() )
567 template <
class T>
template <
class IDX>
inline
570 const int dim = nrdims_-1;
571 int& index = indexarr[dim];
577 if ( lowerdimstorage_.size() )
583 while ( !lowerdimstorage_[index]->next( indexarr, skipduplicate ) )
586 if ( index>=lowerdimstorage_.size() )
598 if ( positions_.size() )
607 const int oldpos = positions_[index];
611 if ( index>=positions_.size() )
616 }
while ( skipduplicate && positions_[index]==oldpos );
622 template <
class T>
template <
class IDX>
inline
625 const int dim = nrdims_-1;
626 int& index = indexarr[dim];
629 if ( lowerdimstorage_[index]->prev( indexarr, skipduplicate ) )
636 lowerdimstorage_[index]->setToLastPos( indexarr );
644 template <
class T>
template<
class IDX>
inline
647 const int dim = nrdims_-1;
648 const int index = indexarr[dim];
654 return index<lowerdimstorage_.size() &&
655 lowerdimstorage_[index]->isValidPos( indexarr );
657 return index<positions_.size();
661 template <
class T>
inline
664 const bool mayhaveduplicates = allowduplicates_ && nrdims_==1;
669 while ( res && positions_[res-1]==index )
685 template <
class T>
template <
class POS>
inline
690 getIndicesInRangeI( start, stop, curpos, res );
694 template <
class T>
template <
class POS>
inline
698 const int dim = nrdims_-1;
699 const int start = startarr[dim];
700 const int stop = stoparr[dim];
701 const int sz = positions_.size();
702 if ( !sz || stop<positions_[0] || start>positions_[sz-1] )
705 int idx = findFirstPos(start);
706 if ( idx<0 ) idx = 0;
707 if ( positions_[idx]<start ) idx++;
708 for ( ; idx<sz; idx++ )
710 if ( positions_[idx]>stop )
715 res.append( curpos );
717 lowerdimstorage_[idx]->getIndicesInRangeI(startarr,stoparr,
723 template <
class T>
template <
class IDX>
inline
726 const int dim = nrdims_-1;
727 const int index = indexarr[dim] = size()-1;
729 lowerdimstorage_[index]->setToLastPos( indexarr );
733 template <
class T>
inline
736 if ( nrdims_!=1 )
return;
738 for (
int idx=1; idx<positions_.size(); idx++ )
740 if ( positions_[idx-1]==positions_[idx] )
742 positions_.removeSingle( idx );
743 for (
int idy=0; idy<nrvals_; idy++ )
744 onedimstorage_.removeSingle( idx );
750 template <
class T>
inline
753 const int nrchunks = res.
size();
758 const int totalsize = totalSize();
763 const int nrperchunk =
mNINT32((
float) totalsize / nrchunks );
765 int allocidx[nrdims_];
766 int* idxs = allocidx;
767 for (
int idx=0; idx<nrdims_; idx++ )
774 int chunk = idx/nrperchunk;
775 if ( chunk>=nrchunks )
780 if ( chunk==prevchunk )
783 for (
int idy=0; idy<nrdims_; idy++ )
784 res[chunk][idy] = idxs[idy];
793 template <
class T>
template <
class IDXS>
inline
801 long long multiplicator = 1;
802 for (
int dim=0; dim<nrdims_; dim++ )
804 dimsizes += multiplicator;
807 if ( getRange( dim, rg ) )
808 multiplicator *= ( rg.width()+1 );
814 for (
int idx=0; idx<indices.size(); idx++ )
816 long long sortkey = 0;
817 for (
int dim=0; dim<nrdims_; dim++ )
818 sortkey += indices[idx][dim] * dimsizes[dim];
824 sort_coupled( sortkeys.arr(), idxs.arr(), idxs.size() );
827 for (
int idx=
mCast(
int,idxs.size()-1); idx>=0; idx-- )
828 indices[idx] =
copy[(int)idxs[idx]];