im com (block index locking)

This commit is contained in:
Christian Zimmermann 2017-08-29 17:52:08 +02:00
parent fbcdfd7580
commit b985b9c35c
7 changed files with 116 additions and 17 deletions

View file

@ -34,6 +34,18 @@ namespace MultiArrayTools
return mRangePtr->size();
}
bool IndexBase::locked() const
{
return mLocked;
}
IndexBase& IndexBase::lock(std::shared_ptr<const IndexBase>& idx)
{
mLocked = (idx.get() == this);
return *this;
}
IndexBase::operator size_t() const
{
return pos();

View file

@ -54,6 +54,9 @@ namespace MultiArrayTools
virtual bool last() const = 0;
virtual bool first() const = 0;
virtual bool locked() const;
virtual IndexBase& lock(std::shared_ptr<const IndexBase>& idx);
virtual std::shared_ptr<const IndexBase> getPtr(size_t n) const = 0;
virtual operator size_t() const;
@ -64,6 +67,7 @@ namespace MultiArrayTools
std::shared_ptr<RangeBase> mRangePtr;
size_t mPos;
size_t mId;
bool mLocked = false;
};
template <typename MetaType>

View file

@ -106,6 +106,8 @@ namespace MultiArrayTools
std::dynamic_pointer_cast<MultiRange<Ranges...> >( mrf.create() );
mIndex = std::make_shared<IndexType>( mr->begin() );
(*mIndex) = *index;
// -> find optimal block index !!!
// -> lock this index !!!
for(*mIndex = 0; mIndex->pos() != mIndex->max(); ++(*mIndex)){
get() = mSecond.get();
}
@ -114,13 +116,15 @@ namespace MultiArrayTools
template <typename T, class... Ranges>
BlockBase<T>& OperationMaster<T,Ranges...>::get()
{
return mArrayRef.data()[ mIndex->pos() ];
block();
return *mBlockPtr;
}
template <typename T, class... Ranges>
const BlockBase<T>& OperationMaster<T,Ranges...>::get() const
{
return mArrayRef.data()[ mIndex->pos() ];
block();
return *mBlockPtr;
}
template <typename T, class... Ranges>

View file

@ -35,6 +35,7 @@ namespace MultiArrayTools
BlockType getBlockType(std::shared_ptr<const IndexBase> i,
std::shared_ptr<const IndexBase> j, bool first);
template <typename T>
class OperationBase
{
@ -120,6 +121,7 @@ namespace MultiArrayTools
OperationBase<T> const& mSecond;
MutableMultiArrayBase<T,Ranges...>& mArrayRef;
std::shared_ptr<IndexType> mIndex;
};

View file

@ -47,6 +47,7 @@ namespace MultiArrayTools
{
PackNum<sizeof...(Indices)-1>::construct(mIPack, *range);
IB::mPos = PackNum<sizeof...(Indices)-1>::makePos(mIPack);
PackNum<sizeof...(Indices)>::initBlockSizes(mBlockSizes, mIPack); // has one more element!
}
template <class... Indices>
@ -58,16 +59,15 @@ namespace MultiArrayTools
template <class... Indices>
MultiIndex<Indices...>& MultiIndex<Indices...>::operator++()
{
PackNum<sizeof...(Indices)-1>::pp( mIPack );
++IB::mPos;
// return step size -> add to IB::mPos
IB::mPos += PackNum<sizeof...(Indices)-1>::pp( mIPack, mBlockSizes );
return *this;
}
template <class... Indices>
MultiIndex<Indices...>& MultiIndex<Indices...>::operator--()
{
PackNum<sizeof...(Indices)-1>::mm( mIPack );
--IB::mPos;
IB::mPos -= PackNum<sizeof...(Indices)-1>::mm( mIPack, mBlockSizes );
return *this;
}
@ -175,6 +175,14 @@ namespace MultiArrayTools
return std::dynamic_pointer_cast<RangeType>( IB::mRangePtr );
}
template <class... Indices>
MultiIndex<Indices...>& MultiIndex<Indices...>::lock(std::shared_ptr<const IndexBase>& idx)
{
IB::mLocked = (idx.get() == this);
PackNum<sizeof...(Indices)-1>::lock(mIPack, idx);
return *this;
}
template <class... Indices>
MultiIndex<Indices...>& MultiIndex<Indices...>::operator()(std::shared_ptr<Indices>&... indices)
{

View file

@ -27,6 +27,7 @@ namespace MultiArrayTools
protected:
IndexPack mIPack;
std::array<size_t,sizeof...(Indices)+1> mBlockSizes;
public:
MultiIndex() = delete;
@ -70,6 +71,8 @@ namespace MultiArrayTools
std::shared_ptr<RangeType> range() const;
virtual MultiIndex& lock(std::shared_ptr<const IndexBase>& idx) override;
// raplace instances (in contrast to its analogon in ContainerIndex
// MultiIndices CANNOT be influences be its subindices, so there is
// NO foreign/external controll)

View file

@ -51,29 +51,64 @@ namespace MultiArrayHelper
}
template <class... Indices>
static inline void pp(std::tuple<std::shared_ptr<Indices>...>& ip)
static void lock(std::tuple<std::shared_ptr<Indices>...>& ip,
std::shared_ptr<const IndexBase>& toLock)
{
std::get<N>(ip)->lock(toLock);
PackNum<N-1>::lock(ip, toLock);
}
template <class... Indices>
static void initBlockSizes(std::array<size_t,sizeof...(Indices)+1>& bs,
std::tuple<std::shared_ptr<Indices>...>& ip)
{
if(N == sizeof...(Indices)){
std::get<N>(bs) = 1;
}
else {
std::get<N>(bs) = PackNum<sizeof...(Indices)-N-1>::blockSize(ip);
PackNum<N-1>::initBlockSizes(bs, ip);
}
}
template <class... Indices>
static inline size_t pp(std::tuple<std::shared_ptr<Indices>...>& ip,
std::array<size_t,sizeof...(Indices)>& bs)
{
auto& si = *std::get<N>(ip);
if(si.last()){
if(si.last() or si.locked()){
si = 0;
PackNum<N-1>::pp(ip);
}
else {
++si;
}
if(si.locked()){
return std::get<N-1>(bs) - std::get<N>(bs) + 1;
}
else {
return 1;
}
}
template <class... Indices>
static inline void mm(std::tuple<std::shared_ptr<Indices>...>& ip)
static inline size_t mm(std::tuple<std::shared_ptr<Indices>...>& ip,
std::array<size_t,sizeof...(Indices)>& bs)
{
auto& si = *std::get<N>(ip);
if(si.first()){
if(si.first() or si.locked()){
si = si.max();
PackNum<N-1>::mm(ip);
}
else {
--si;
}
if(si.locked()){
return std::get<N-1>(bs) - std::get<N>(bs) + 1;
}
else {
return 1;
}
}
template <class RangeTuple>
@ -190,17 +225,48 @@ namespace MultiArrayHelper
}
template <class... Indices>
static inline void pp(std::tuple<std::shared_ptr<Indices>...>& ip)
static void lock(std::tuple<std::shared_ptr<Indices>...>& ip,
std::shared_ptr<const IndexBase>& toLock)
{
auto& si = *std::get<0>(ip);
++si;
std::get<0>(ip)->lock(toLock);
}
template <class... Indices>
static inline void mm(std::tuple<std::shared_ptr<Indices>...>& ip)
static void initBlockSizes(std::array<size_t,sizeof...(Indices)+1>& bs,
std::tuple<std::shared_ptr<Indices>...>& ip)
{
std::get<0>(bs) = PackNum<sizeof...(Indices)-1>::blockSize(ip);
}
template <class... Indices>
static inline size_t pp(std::tuple<std::shared_ptr<Indices>...>& ip,
std::array<size_t,sizeof...(Indices)+1>& bs)
{
auto& si = *std::get<0>(ip);
--si;
if(si.locked()){
si = si.max()+1;
return std::get<0>(bs) - std::get<1>(bs) + 1;
}
else {
++si;
return 1;
}
}
template <class... Indices>
static inline size_t mm(std::tuple<std::shared_ptr<Indices>...>& ip,
std::array<size_t,sizeof...(Indices)>& bs)
{
auto& si = *std::get<0>(ip);
if(si.locked()){
si = 0;
--si;
return std::get<0>(bs) - std::get<1>(bs) + 1;
}
else {
--si;
return 1;
}
}
template <class RangeTuple>