13#ifndef __cxz_mrange_cc_h__
14#define __cxz_mrange_cc_h__
29 template <SizeT...
Is>
32 static_assert(
sizeof...(Is) == NI,
33 "sequence sioze does not match number of indices");
35 "subranges not available" );
36 return std::make_tuple( std::make_shared<Indices>( mRange->sub(
Is) )... );
43 [](
auto...
e) {
return (
e * ...); });
47 constexpr decltype(
auto) GMIndex<FormatT,Indices...>::mkPMax(
const SPack<Indices...>&
ipack,
const FormatT& format)
49 if constexpr(std::is_same<FormatT,None>::value){
56 [](
auto...
e) {
return (
e + ...); }) +
SPos<1>();
61 inline void GMIndex<FormatT,Indices...>::mkPos()
64 ([&](
auto i) {
return mIPack[
i]->lex() * mLexFormat[
i].val(); },
65 [](
const auto&...
e) {
return (
e + ...); });
66 if constexpr(
not std::is_same<FormatT,None>::value){
68 ([&](
auto i) {
return mIPack[
i]->pos() * mFormat[
i].val(); },
69 [](
const auto&...
e) {
return (
e + ...); });
77 template <SizeT...
Is>
82 ( [&](
auto i) {
return ipack[
i]->pmax(); },
83 [](
const auto&...
as) {
return (
as * ...); } )...,
92 auto&
ind = mIPack[
i];
94 if(
ind->lex() ==
ind->lmax().val()-1){
95 IB::mPos -= format()[
i].val() *
ind->
pos();
96 if constexpr(
not std::is_same<FormatT,None>::value){
97 mLex -= lexFormat()[
i].val() *
ind->lex();
104 IB::mPos += format()[
i].val();
105 if constexpr(
not std::is_same<FormatT,None>::value){
106 mLex += lexFormat()[
i].val();
113 inline void GMIndex<FormatT,Indices...>::down()
116 auto&
ind = mIPack[
i];
117 if constexpr(I != 0){
119 (*ind) =
ind->lmax().val()-1;
120 IB::mPos += format()[
i].val() *
ind->pos();
121 if constexpr(
not std::is_same<FormatT,None>::value){
122 mLex += lexFormat()[
i].val() *
ind->lex();
128 IB::mPos -= format()[
i].val();
129 if constexpr(
not std::is_same<FormatT,None>::value){
130 mLex -= lexFormat()[
i].val();
136 template <SizeT I,
class Xpr,
class F>
140 if constexpr(I ==
sizeof...(Indices)-1){
141 return mIPack[
i]->
ifor(
xpr,std::forward<F>(
f));
158 mIPack(mkIPack(
Isqr<0,NI>{})),
161 mLMax(mkLMax(mIPack)),
162 mPMax(mkPMax(mIPack,mFormat))
173 mLexFormat = mkLexFormat(mIPack,
Isqr<1,NI>{});
175 mLMax = mkLMax(mIPack);
176 mPMax = mkPMax(mIPack,mFormat);
177 return *
this =
i.lex();
185 mLexFormat(mkLexFormat(mIPack,
Isqr<1,NI>{})),
187 mLMax(mkLMax(mIPack)),
188 mPMax(mkPMax(mIPack,mFormat))
190 if constexpr(
not std::is_same<None,FormatT>::value){
191 mFormat = mLexFormat;
201 mLexFormat(mkLexFormat(mIPack,
Isqr<1,NI>{})),
203 mLMax(mkLMax(mIPack)),
204 mPMax(mkPMax(mIPack,mFormat))
214 mLexFormat(mkLexFormat(mIPack,
Isqr<1,NI>{})),
216 mLMax(mkLMax(mIPack)),
217 mPMax(mkPMax(mIPack,mFormat))
219 if constexpr(
not std::is_same<None,FormatT>::value){
220 mFormat = mLexFormat;
231 mLexFormat(mkLexFormat(mIPack,
Isqr<1,NI>{})),
233 mLMax(mkLMax(mIPack)),
234 mPMax(mkPMax(mIPack,mFormat))
243 mIPack(mkIPack(
Isqr<0,NI>{})),
246 mLMax(mkLMax(mIPack)),
247 mPMax(mkPMax(mIPack,mFormat))
249 if constexpr(
not std::is_same<None,FormatT>::value){
250 mFormat = mLexFormat;
259 mIPack(mkIPack(
Isqr<0,NI>{})),
262 mLMax(mkLMax(mIPack)),
263 mPMax(mkPMax(mIPack,mFormat))
271 if(
lexpos >= lmax().val()){
272 if constexpr(
not std::is_same<FormatT,None>::value){ mLex = lmax().val(); }
273 IB::mPos = pmax().val();
276 if constexpr(
not std::is_same<FormatT,None>::value){ mLex =
lexpos; }
278 *mIPack[
i] = (
lexpos / lexFormat()[
i].val()) % mIPack[
i]->lmax().val();
279 return format()[
i].val() * mIPack[
i]->pos();
280 }, [](
const auto&...
e) {
return (
e + ...); } );
287 if(lex() == lmax().val()-1){
288 return *
this = lmax().val();
290 if(lex() != lmax().val()){
299 if(lex() == lmax().val()){
300 return *
this = lmax().val()-1;
325 return lex() -
i.
lex();
331 if(-
n >
static_cast<long int>(lex())){
335 if(
p > lmax().val()){
336 (*this) = lmax().val();
345 if(
n >
static_cast<long int>(lex())){
349 if(
p > lmax().val()){
350 (*this) = lmax().val();
359 if constexpr(std::is_same<FormatT,None>::value){
408 ( [&](
auto i) {
return mIPack[
i]->stepSize(
id) * format()[
i]; },
409 [](
const auto&...
ss) {
return (
ss + ... ); });
419 ( [&](
auto i) {
return mIPack[
i]->stringMeta(); },
420 [&](
const auto&...
xs) {
428 return iter<0,NI>( [&](
auto i) {
return mIPack[
i]->meta(); },
429 [](
const auto&...
xs) {
return std::make_tuple(
xs...); } );
437 ( [&](
auto i) {
return mIPack[
i]->pos()*format()[
i].val(); },
438 [](
const auto&...
xs) {
return (
xs + ...); });
446 [](
const auto&... x) {
448 return std::make_tuple(
e...);
454 template <
class Xpr,
class F>
463 if constexpr(std::is_same<FormatT,None>::value){
468 ( [&](
auto i) {
return mIPack[
i]->formatIsTrivial(); },
469 [](
const auto&... x) {
return (x
and ...); } );
475 [](
const auto&... x) {
return (x
and ...); });
509 if constexpr(std::is_same<FormatT,None>::value){
528 typedef typename std::remove_reference<
decltype(*mIPack[
i])>::type::RangeType
RangeT;
529 return std::dynamic_pointer_cast<RangeT>( mIPack[
i]->
prange( *
last.pack()[
i] ) );
531 [](
const auto&...
e) {
return mrange(
e...); }
539 return iter<0,NI>( [&](
auto i) {
return mul(mIPack[
i]->deepFormat(), format()[
i].val()); },
540 [&](
const auto&...
e) {
return concat(
e...); } );
546 return iter<0,NI>( [&](
auto i) {
return mIPack[
i]->deepMax(); },
547 [&](
const auto&...
e) {
return concat(
e...); } );
556 CXZ_ASSERT(
f.size() ==
s.size(),
"input error: f.size() != s.size()");
558 CXZ_ASSERT(
s[0] == lmax().val(),
"got inconsistent size; expeected "
559 << lmax().val() <<
", got " <<
s[0]);
563 if constexpr(std::is_same<FormatT,None>::value){
565 "cannot reformat MIndex with format type = None");
572 typename FormatT::InputType
nformat;
575 xi *= mIPack[
i]->lmax().val();
590 std::copy(
f.begin()+
j0,
f.begin()+
j,
nf.begin());
591 std::get<i>(
nformat) = *std::min_element(
nf.begin(),
nf.end());
592 std::for_each(
nf.begin(),
nf.end(), [&](
SizeT& x)
593 { CXZ_ASSERT(x % std::get<i>(nformat).val() == 0,
"incompatible");
594 x /= std::get<i>(nformat).val(); } );
595 std::copy(
s.begin()+
j0,
s.begin()+
j,
ns.begin());
596 mIPack[
i]->reformat(
nf,
ns);
599 CXZ_ERROR(
"reformating with lower-dimensional formats is not possible; use sub-indices instead");
610 if constexpr(
not std::is_same<FormatT,None>::value){
650 template <
class...
Ranges>
655 template <
class...
Ranges>
662 template <
class...
Ranges>
666 ( [&](
auto i) {
return std::get<i>( mRs ); },
669 mProd = this->fromCreated(
info, key);
670 if(mProd ==
nullptr) {
671 mProd = std::shared_ptr<MRange<
Ranges...>>
672 (
new MRange<
Ranges...>( mRs ) );
673 this->addToCreated(
info, key, mProd);
681 template <
class...
Ranges>
687 template <
class...
Ranges>
694 template <
class...
Ranges>
697 if constexpr(NR == 0) {
703 ( [](
auto i) {
return i; },
704 [](
auto... x) {
return Arr<SizeT,NR> { x... }; } ) ).create();
707 ( [&](
auto i) {
return std::get<i>(mRs); },
712 template <
class...
Ranges>
715 return iter<0,NR>( [&](
auto i) {
return std::get<i>(mRs)->size(); },
716 [](
const auto&...
xs) {
return (
xs * ...); } );
719 template <
class...
Ranges>
725 template <
class...
Ranges>
728 return (this->begin()+pos).stringMeta();
731 template <
class...
Ranges>
737 template <
class...
Ranges>
743 template <
class...
Ranges>
749 template <
class...
Ranges>
752 return (this->begin()+pos)->meta();
755 template <
class...
Ranges>
758 auto i = this->begin();
762 template <
class...
Ranges>
765 CXZ_ASSERT( r->dim() ==
this->dim(),
"cannot extend range of dimension "
766 <<
this->dim() <<
" by range of dimension " << r->dim());
768 typedef typename std::remove_reference<decltype(*std::get<i>(mRs))>::type
RType;
769 return std::dynamic_pointer_cast<RType>( std::get<i>(mRs)->extend(r->sub(
i)) ); },
770 [](
const auto&...
e) {
return std::make_tuple(
e...); }
775 template <
class...
Ranges>
779 ( [&](
auto i) {
return std::get<i>( mRs ); },
788 template <
class...
Ranges>
791 return iter<0,NR>([&](
auto i) {
return std::get<i>(mRs); },
799 template <
class...
Ranges>
805 template <
class...
Ranges>
808 CXZ_ASSERT(r->dim() ==
sizeof...(Ranges),
"expect range of dimension "
809 <<
sizeof...(Ranges) <<
", got " << r->dim());
814 [](
const auto&...
e){
return std::make_tuple(
e... ); } ) ).
create() );
#define CXZ_ERROR(errmsg)
#define CXZ_ASSERT(statement, errmsg)
GMIndex & setFormat(const FormatT &bs)
bool formatIsTrivial() const
MetaType operator*() const
Tuple< typename Indices::MetaType... > MetaType
constexpr GMIndex()=default
RangePtr prange(const GMIndex< FormatT, Indices... > &last) const
GMIndex & operator-=(Int n)
GMIndex & reformat(const Vector< SizeT > &f, const Vector< SizeT > &s)
const SPack< Indices... > & pack() const
GMIndex operator-(Int n) const
GMIndex operator+(Int n) const
constexpr SizeT dim() const
String stringMeta() const
GMIndex & at(const MetaType &metaPos)
Sptr< RangeType > range() const
constexpr GMIndex & operator=(GMIndex &&i)=default
GMIndex & operator+=(Int n)
constexpr decltype(auto) ifor(const Xpr &xpr, F &&f) const
const auto & lexFormat() const
const auto & format() const
virtual RangePtr extend(const RangePtr &r) const override final
virtual String stringMeta(SizeT pos) const override final
virtual SizeT size() const override final
virtual const TypeInfo & metaType() const override final
SizeT getMeta(const MetaType &metaPos) const
virtual const TypeInfo & type() const override final
virtual Vector< Uuid > key() const override final
const MetaType get(SizeT pos) const
virtual SizeT dim() const override final
virtual MArray< RangePtr > sub() const override final
Tuple< typename Ranges::IndexType::MetaType... > MetaType
MRange, GMIndex and MIndex declaration.
typename MkIsq< B, E >::type Isqr
decltype(auto) concat(const T1 &a1, const T2 &a2, const Ts &... as)
constexpr decltype(auto) gmindexPtr(const FormatT &bs, const SPack< Indices... > &pack)
constexpr decltype(auto) mindex(const Sptr< Indices > &... is)
Sptr< RangeBase > RangePtr
std::vector< T, Allocator< T > > Vector
RangePtr mrange(const Sptr< Ranges > &... rs)
decltype(auto) xpr(const Sptr< I > &i)
std::integral_constant< SizeT, N > CSizeT
Sptr< Range > rangeCast(const RangePtr r)
constexpr decltype(auto) gmformat(const PosT &... ps)
constexpr Arr< T, N > mul(const Arr< T, N > &a, const T &b)
std::index_sequence< Is... > Isq
decltype(auto) iptrMul(const Sptr< I1 > &a, const Sptr< I2 > &b)
bool formatIsTrivial(const Vector< SizeT > &f, const Vector< SizeT > &s)
RangePtr prange(const Sptr< RangeT > &range, const Vector< SizeT > &parts)
constexpr decltype(auto) operation(F &&f, const Ops &... ops)
constexpr decltype(auto) mindexPtr(const SPack< Indices... > &pack)
std::shared_ptr< T > Sptr
constexpr decltype(auto) iter(const G &g, const F &f)
Operation types template implementations.
Operation types declarations.
Operation utilities template implementations.