diff --git a/src/include/operation/extensions/reg.cc.h b/src/include/operation/extensions/reg.cc.h index 3ff3596..73560b9 100644 --- a/src/include/operation/extensions/reg.cc.h +++ b/src/include/operation/extensions/reg.cc.h @@ -21,7 +21,7 @@ namespace CNORXZ constexpr SizeT N = epos_size::value; static_assert(is_epos_type::value, "got non-epos-type"); if constexpr(pos_type_is_consecutive::value){ - return *reinterpret_cast*>(d); + return *reinterpret_cast*>(d+pos.scal().val()); } else { return vregi(d, pos, std::make_index_sequence{}); @@ -35,7 +35,7 @@ namespace CNORXZ static_assert(is_epos_type::value, "got non-epos-type"); static_assert(pos_type_is_consecutive::value, "no write access for non-consecutive"); if constexpr(pos_type_is_consecutive::value){ - return *reinterpret_cast*>(d); + return *reinterpret_cast*>(d+pos.scal().val()); } else { return vregi(d, pos, std::make_index_sequence{}); diff --git a/src/include/ranges/crange.cc.h b/src/include/ranges/crange.cc.h index 3410ac7..279a456 100644 --- a/src/include/ranges/crange.cc.h +++ b/src/include/ranges/crange.cc.h @@ -8,9 +8,14 @@ namespace CNORXZ { template - UPos CIndex::stepSize(const IndexId& id) const + decltype(auto) CIndex::stepSize(const IndexId& id) const { - return UPos(id == this->id() ? 1 : 0); + if constexpr(I != 0){ + return SPos<0>(); + } + else { + return UPos(id == this->id() ? 1 : 0); + } } template diff --git a/src/include/ranges/crange.h b/src/include/ranges/crange.h index f9adbad..177c7b3 100644 --- a/src/include/ranges/crange.h +++ b/src/include/ranges/crange.h @@ -40,7 +40,7 @@ namespace CNORXZ Sptr range() const; template - UPos stepSize(const IndexId& id) const; + decltype(auto) stepSize(const IndexId& id) const; String stringMeta() const; SizeT meta() const; diff --git a/src/include/ranges/lindex.cc.h b/src/include/ranges/lindex.cc.h index 26046af..6fb8f8f 100644 --- a/src/include/ranges/lindex.cc.h +++ b/src/include/ranges/lindex.cc.h @@ -22,7 +22,7 @@ namespace CNORXZ template decltype(auto) LIndex::stepSize(const IndexId& id) const { - if constexpr(L == 0 or I == 0){ + if constexpr(L == 0 and I == 0){ return UPos(mI->id() == id ? 1 : 0); } else { @@ -35,6 +35,13 @@ namespace CNORXZ } } + template + template + decltype(auto) LIndex::ifor(const Xpr& xpr, F&& f) const + { + return For(this->pmax().val(), this->id(), xpr, std::forward(f)); + } + template decltype(auto) operator*(const Sptr>& a, const Sptr& b) { diff --git a/src/include/ranges/lindex.h b/src/include/ranges/lindex.h index aa66f0e..0c79971 100644 --- a/src/include/ranges/lindex.h +++ b/src/include/ranges/lindex.h @@ -25,6 +25,9 @@ namespace CNORXZ template decltype(auto) stepSize(const IndexId& id) const; + template + decltype(auto) ifor(const Xpr& xpr, F&& f) const; + private: Sptr mI; }; diff --git a/src/include/ranges/mrange.cc.h b/src/include/ranges/mrange.cc.h index 5d62a51..6e7ea24 100644 --- a/src/include/ranges/mrange.cc.h +++ b/src/include/ranges/mrange.cc.h @@ -506,9 +506,9 @@ namespace CNORXZ } template - constexpr decltype(auto) gmindexPtr(const FormatT& bs, const Sptr&... is) + constexpr decltype(auto) gmindexPtr(const FormatT& bs, const SPack& pack) { - return std::make_shared>(bs, is...); + return std::make_shared>(bs, pack); } template diff --git a/src/include/ranges/mrange.h b/src/include/ranges/mrange.h index 79661fc..2c3d7bd 100644 --- a/src/include/ranges/mrange.h +++ b/src/include/ranges/mrange.h @@ -147,7 +147,7 @@ namespace CNORXZ constexpr decltype(auto) mindexPtr(const SPack& pack); template - constexpr decltype(auto) gmindexPtr(const FormatT& bs, const Sptr&... is); + constexpr decltype(auto) gmindexPtr(const FormatT& bs, const SPack& pack); template decltype(auto) operator*(const Sptr>& a, const Sptr& b); diff --git a/src/include/ranges/urange.cc.h b/src/include/ranges/urange.cc.h index 2d9bc11..7860ca9 100644 --- a/src/include/ranges/urange.cc.h +++ b/src/include/ranges/urange.cc.h @@ -140,9 +140,14 @@ namespace CNORXZ template template - UPos UIndex::stepSize(const IndexId& id) const + decltype(auto) UIndex::stepSize(const IndexId& id) const { - return UPos(id == this->id() ? 1 : 0); + if constexpr(I != 0){ + return SPos<0>(); + } + else { + return UPos(id == this->id() ? 1 : 0); + } } template diff --git a/src/include/ranges/urange.h b/src/include/ranges/urange.h index 46293bb..af12824 100644 --- a/src/include/ranges/urange.h +++ b/src/include/ranges/urange.h @@ -48,7 +48,7 @@ namespace CNORXZ Sptr range() const; template - UPos stepSize(const IndexId& id) const; + decltype(auto) stepSize(const IndexId& id) const; String stringMeta() const; const MetaT& meta() const; diff --git a/src/include/xpr/index_id.cc.h b/src/include/xpr/index_id.cc.h index cd42bfd..09eaddb 100644 --- a/src/include/xpr/index_id.cc.h +++ b/src/include/xpr/index_id.cc.h @@ -22,7 +22,7 @@ namespace CNORXZ template constexpr decltype(auto) IndexId::operator==(const IndexId& a) const { - if constexpr(I != 0 and J != 0){ + if constexpr(I != 0 or J != 0){ if constexpr(I == J){ CXZ_ASSERT(mId == a.id(), "got different index ids for equal static index label"); diff --git a/src/include/xpr/pos_type.cc.h b/src/include/xpr/pos_type.cc.h index d11f4da..77f6b92 100644 --- a/src/include/xpr/pos_type.cc.h +++ b/src/include/xpr/pos_type.cc.h @@ -30,7 +30,14 @@ namespace CNORXZ { return SPos(); } - + + template + template + constexpr auto SPos::operator-(const SPos& a) const + { + return SPos(); + } + template template constexpr auto SPos::operator*(const SPos& a) const @@ -54,13 +61,23 @@ namespace CNORXZ template constexpr auto SPos::operator*(const UPos& a) const { - return UPos(N*a.val()); + if constexpr(N == 0){ + return SPos<0>(); + } + else { + return UPos(N*a.val()); + } } template constexpr auto SPos::operator()(const UPos& a) const { - return UPos(N*a.val()); + if constexpr(N == 0){ + return SPos<0>(); + } + else { + return UPos(N*a.val()); + } } template @@ -603,7 +620,7 @@ namespace CNORXZ return iter<0,sizeof...(OPosTs)> ( [&](auto i) { return std::get(mP); }, [&](const auto&... e) { return EPos - (BPosT::operator*(a),e...); } ); + (BPosT::operator*(a),e*a...); } ); } template @@ -613,7 +630,7 @@ namespace CNORXZ return iter<0,sizeof...(OPosTs)> ( [&](auto i) { return std::get(mP); }, [&](const auto&... e) { return EPos - (BPosT::operator()(a),e...); } ); + (BPosT::operator()(a),e*a...); } ); } @@ -629,11 +646,17 @@ namespace CNORXZ return inext(std::index_sequence_for{}); } + template + constexpr decltype(auto) EPos::scal() const + { + return static_cast(*this); + } + template template constexpr decltype(auto) EPos::get() const { - return std::get(mP); + return scal()+std::get(mP); } template @@ -644,7 +667,7 @@ namespace CNORXZ return std::index_sequence(mP).val()...>{}; } else { - return Arr { std::get(mP).val()... }; + return Arr { (BPosT::val()+std::get(mP).val())... }; } } @@ -653,7 +676,7 @@ namespace CNORXZ constexpr decltype(auto) EPos::inext(std::index_sequence is) const { typedef EPos(mP).next())...> OEPosT; - return OEPosT(next(), std::get(mP).next()...); + return OEPosT(BPosT::next(), std::get(mP).next()...); } /********************************* diff --git a/src/include/xpr/pos_type.h b/src/include/xpr/pos_type.h index 357eb4e..f82f27b 100644 --- a/src/include/xpr/pos_type.h +++ b/src/include/xpr/pos_type.h @@ -21,6 +21,8 @@ namespace CNORXZ template constexpr auto operator+(const SPos& a) const; template + constexpr auto operator-(const SPos& a) const; + template constexpr auto operator*(const SPos& a) const; template constexpr auto operator()(const SPos& a) const; @@ -288,6 +290,8 @@ namespace CNORXZ constexpr decltype(auto) val() const; constexpr decltype(auto) next() const; + constexpr decltype(auto) scal() const; + template constexpr decltype(auto) get() const; }; @@ -424,6 +428,12 @@ namespace CNORXZ static constexpr bool value = pos_types_consecutive::value; }; + template + struct pos_type_is_consecutive> + { + static constexpr bool value = pos_type_is_consecutive::value; + }; + } // end namespace CNORXZInternal diff --git a/src/tests/operation_unit_test.cc b/src/tests/operation_unit_test.cc index 2167c3d..0252c15 100644 --- a/src/tests/operation_unit_test.cc +++ b/src/tests/operation_unit_test.cc @@ -99,16 +99,17 @@ namespace protected: typedef MIndex,EIndex> MCCI1; + typedef GMIndex>,CIndex,LIndex,EIndex> MCCI1x; typedef MIndex,EIndex,CIndex> MCCI2; OpCont_CR_CR_Test2() { - mSize1 = 12; - mSize2 = 11; + mSize1 = 11; + mSize2 = 12; SizeT off = 20; - mData1 = Numbers::get(off, mSize1); - mData2 = Numbers::get(off += mSize1 , mSize2); - mData11 = Numbers::get(off += mSize2, mSize1*mSize2); + //mData1 = Numbers::get(off, mSize1); + //mData2 = Numbers::get(off += mSize1 , mSize2); + mData21 = Numbers::get(off += mSize2, mSize1*mSize2); mData12 = Numbers::get(off += mSize1*mSize2, mSize1*mSize2); auto cr1 = CRangeFactory(mSize1).create(); auto cr2 = CRangeFactory(mSize2).create(); @@ -116,28 +117,31 @@ namespace mCI1j = std::make_shared(cr1); mCI2i = std::make_shared(cr2); mCI2j = std::make_shared(cr2); - mCC1i1j = mindexPtr(mCI1i*eplex<4,1,2>(mCI1j)); - mCC1j1i = mindexPtr(eplex<4,1,2>(mCI1j)*mCI1i); - mOC1i1j.init(mCC1i1j); - mOR1j1i.init(mData11.data(), mCC1j1i); - mOR1i1j.init(mData12.data(), mCC1i1j); + auto ipack1 = mCI1i*eplex<4,1,2>(mCI2j); + auto iform1 = gmformat(UPos(mCI2j->lmax().val()),UPos(4),SPos<1>()); + mCC1i2j = gmindexPtr( iform1, ipack1 ); + //mCC1i2j = mindexPtr(mCI1i*eplex<4,1,2>(mCI2j)); + mCC2j1i = mindexPtr(eplex<4,1,2>(mCI2j)*mCI1i); + mOC1i2j.init(mCC1i2j); + mOR2j1i.init(mData21.data(), mCC2j1i); + mOR1i2j.init(mData12.data(), mCC1i2j); } SizeT mSize1; SizeT mSize2; - Vector mData1; - Vector mData2; - Vector mData11; Vector mData12; + Vector mData21; + Vector mData11_1; + Vector mData11_2; Sptr mCI1i; Sptr mCI1j; Sptr mCI2i; Sptr mCI2j; - Sptr mCC1i1j; - Sptr mCC1j1i; - OpCont mOC1i1j; - COpRoot mOR1j1i; - COpRoot mOR1i1j; + Sptr mCC1i2j; + Sptr mCC2j1i; + OpCont mOC1i2j; + COpRoot mOR2j1i; + COpRoot mOR1i2j; }; TEST_F(OpCont_CR_Test, Basics) @@ -233,24 +237,38 @@ namespace TEST_F(OpCont_CR_CR_Test2, Assignment) { - mOC1i1j = mOR1j1i; + EXPECT_EQ( mCC2j1i->stepSize( mCC1i2j->pack()[CSizeT<0>{}]->id() ).val(), 1u ); + EXPECT_EQ( mCC2j1i->stepSize( mCC1i2j->pack()[CSizeT<1>{}]->id() ).val(), 44u ); + EXPECT_EQ( mCC2j1i->stepSize( mCC1i2j->pack()[CSizeT<2>{}]->id() ).val(), 11u ); + + mOC1i2j = mOR2j1i; + for(SizeT i = 0; i != mCI1i->pmax().val(); ++i){ - for(SizeT j = 0; j != mCI1j->pmax().val(); ++j){ - const SizeT jS = mCI1j->pmax().val(); + for(SizeT j = 0; j != mCI2j->pmax().val(); ++j){ + const SizeT jS = mCI2j->pmax().val(); const SizeT iS = mCI1i->pmax().val(); - EXPECT_EQ(mOC1i1j.data()[i*jS+j], mOR1j1i.data()[j*iS+i]); + EXPECT_EQ(mOC1i2j.data()[i*jS+j], mOR2j1i.data()[j*iS+i]); } } + } TEST_F(OpCont_CR_CR_Test2, Multiply) { - mOC1i1j = mOR1j1i * mOR1i1j; + EXPECT_EQ( mCC2j1i->stepSize( mCC1i2j->pack()[CSizeT<0>{}]->id() ).val(), 1u ); + EXPECT_EQ( mCC2j1i->stepSize( mCC1i2j->pack()[CSizeT<1>{}]->id() ).val(), 44u ); + EXPECT_EQ( mCC2j1i->stepSize( mCC1i2j->pack()[CSizeT<2>{}]->id() ).val(), 11u ); + + EXPECT_EQ( mCC1i2j->stepSize( mCC1i2j->pack()[CSizeT<0>{}]->id() ).val(), 12u ); + EXPECT_EQ( mCC1i2j->stepSize( mCC1i2j->pack()[CSizeT<1>{}]->id() ).val(), 4u ); + EXPECT_EQ( mCC1i2j->stepSize( mCC1i2j->pack()[CSizeT<2>{}]->id() ).val(), 1u ); + + mOC1i2j = mOR2j1i * mOR1i2j; for(SizeT i = 0; i != mCI1i->pmax().val(); ++i){ - for(SizeT j = 0; j != mCI1j->pmax().val(); ++j){ - const SizeT jS = mCI1j->pmax().val(); + for(SizeT j = 0; j != mCI2j->pmax().val(); ++j){ + const SizeT jS = mCI2j->pmax().val(); const SizeT iS = mCI1i->pmax().val(); - EXPECT_EQ(mOC1i1j.data()[i*jS+j], mOR1j1i.data()[j*iS+i] * mOR1i1j.data()[i*jS+j]); + EXPECT_EQ(mOC1i2j.data()[i*jS+j], mOR2j1i.data()[j*iS+i] * mOR1i2j.data()[i*jS+j]); } } }