cnorxz/src/container_range.cc
2017-08-07 11:22:42 +02:00

200 lines
5.4 KiB
C++

// -*- C++ -*-
#include "container_range.h"
#include "pack_num.h"
namespace MultiArrayTools
{
namespace
{
using namespace MultiArrayHelper;
}
/**********************
* ContainerIndex *
**********************/
template <class... Indices>
ContainerIndex<Indices...>::ContainerIndex(const ContainerIndex& in) :
IndexInterface<std::tuple<decltype(Indices().meta())...> >(in)
{
PackNum<sizeof...(Indices)-1>::copy(mIPack, in);
IB::mPos = PackNum<sizeof...(Indices)-1>::makePos(mIPack);
}
template <class... Indices>
ContainerIndex<Indices...>& ContainerIndex<Indices...>::operator=(const ContainerIndex& in)
{
IndexI::operator=(in);
PackNum<sizeof...(Indices)-1>::copy(mIPack, in);
IB::mPos = PackNum<sizeof...(Indices)-1>::makePos(mIPack);
return *this;
}
template <class... Indices>
template <class MRange>
ContainerIndex<Indices...>::ContainerIndex(const std::shared_ptr<MRange>& range)
{
PackNum<sizeof...(Indices)-1>::construct(mIPack, *range);
IB::mPos = PackNum<sizeof...(Indices)-1>::makePos(mIPack);
}
template <class... Indices>
ContainerIndex<Indices...>& ContainerIndex<Indices...>::operator++()
{
if(mExternControl){
IB::mPos = PackNum<sizeof...(Indices)-1>::makePos(mIPack);
}
PackNum<sizeof...(Indices)-1>::pp( mIPack );
++IB::mPos;
return *this;
}
template <class... Indices>
ContainerIndex<Indices...>& ContainerIndex<Indices...>::operator--()
{
if(mExternControl){
IB::mPos = PackNum<sizeof...(Indices)-1>::makePos(mIPack);
}
PackNum<sizeof...(Indices)-1>::mm( mIPack );
--IB::mPos;
return *this;
}
template <class... Indices>
ContainerIndex<Indices...>& ContainerIndex<Indices...>::operator=(size_t pos)
{
IB::mPos = pos;
PackNum<sizeof...(Indices)-1>::setIndexPack(mIPack, pos);
return *this;
}
template <class... Indices>
typename ContainerIndex<Indices...>::MetaType ContainerIndex<Indices...>::meta() const
{
MetaType metaTuple;
PackNum<sizeof...(Indices)-1>::getMetaPos(metaTuple, mIPack);
return metaTuple;
}
template <class... Indices>
ContainerIndex<Indices...>& ContainerIndex<Indices...>::at(const MetaType& metaPos)
{
PackNum<sizeof...(Indices)-1>::setMeta(mIPack, metaPos);
return *this;
}
template <class... Indices>
size_t ContainerIndex<Indices...>::dim() const
{
return sizeof...(Indices);
}
template <class... Indices>
size_t ContainerIndex<Indices...>::pos() const
{
if(mExternControl){
IB::mPos = PackNum<sizeof...(Indices)-1>::makePos(mIPack);
}
return IB::mPos;
}
template <class... Indices>
bool ContainerIndex<Indices...>::first() const
{
return pos() == 0;
}
template <class... Indices>
bool ContainerIndex<Indices...>::last() const
{
return pos() == IB::mRangePtr->size() - 1;
}
template <class... Indices>
ContainerIndex<Indices...>& ContainerIndex<Indices...>::operator()(const std::shared_ptr<Indices>&... inds)
{
PackNum<sizeof...(Indices)-1>::swapIndices(mIPack, inds...);
mExternControl = true;
return *this;
}
/*****************************
* ContainerRangeFactory *
*****************************/
template <class... Ranges>
ContainerRangeFactory<Ranges...>::ContainerRangeFactory(const std::shared_ptr<Ranges>&... rs)
{
mProd = std::shared_ptr<ContainerRange<Ranges...> >( new ContainerRange<Ranges...>( rs... ) );
}
template <class... Ranges>
ContainerRangeFactory<Ranges...>::
ContainerRangeFactory(const typename ContainerRange<Ranges...>::SpaceType& space)
{
mProd = std::shared_ptr<ContainerRange<Ranges...> >( new ContainerRange<Ranges...>( space ) );
}
template <class... Ranges>
std::shared_ptr<RangeBase> ContainerRangeFactory<Ranges...>::create()
{
setSelf();
return mProd;
}
/**********************
* ContainerRange *
**********************/
template <class... Ranges>
ContainerRange<Ranges...>::ContainerRange(const std::shared_ptr<Ranges>&... rs) :
mSpace( std::make_tuple( rs... ) ) {}
template <class... Ranges>
ContainerRange<Ranges...>::ContainerRange(const SpaceType& space) : mSpace( space ) {}
template <class... Ranges>
size_t ContainerRange<Ranges...>::dim() const
{
return sizeof...(Ranges);
}
template <class... Ranges>
size_t ContainerRange<Ranges...>::size() const
{
return PackNum<sizeof...(Ranges)-1>::getSize(mSpace);
}
template <class... Ranges>
typename ContainerRange<Ranges...>::IndexType ContainerRange<Ranges...>::begin() const
{
ContainerIndex<typename Ranges::IndexType...>
i( std::dynamic_pointer_cast<ContainerRange<Ranges...> >
( std::shared_ptr<RangeBase>( RB::mThis ) ) );
i = 0;
return i;
}
template <class... Ranges>
typename ContainerRange<Ranges...>::IndexType ContainerRange<Ranges...>::end() const
{
ContainerIndex<typename Ranges::IndexType...>
i( std::dynamic_pointer_cast<ContainerRange<Ranges...> >
( std::shared_ptr<RangeBase>( RB::mThis ) ) );
i = size();
return i;
}
template <class... Ranges>
std::shared_ptr<IndexBase> ContainerRange<Ranges...>::index() const
{
return std::make_shared<ContainerIndex<typename Ranges::IndexType...> >
( std::dynamic_pointer_cast<ContainerRange<Ranges...> >
( std::shared_ptr<RangeBase>( RB::mThis ) ) );
}
} // end namespace MultiArrayTools