// -*- C++ -*- #ifndef __multi_array_operation_h__ #define __multi_array_operation_h__ #include #include #include #include "base_def.h" namespace MultiArrayTools { namespace { using namespace MultiArrayHelper; } /* * OperationBase * MutableOperationBase * * OperationMaster : MutableOperationBase * * OperationTemplate<...> * ConstOperationRoot : OperationBase, OperationTemplate<...> * OperationRoot : MutableOperationBase, * OperationTemplate<...> * */ template class OperationBase { public: typedef T value_type; OperationBase() = default; virtual ~OperationBase() = default; virtual OperationBase& block(const std::shared_ptr& blockIndex) = 0; //virtual size_t argNum() const = 0; virtual const BlockBase& get() const = 0; protected: mutable std::shared_ptr mBlockPtr; }; template class MutableOperationBase : public OperationBase { public: typedef T value_type; MutableOperationBase() = default; virtual BlockBase& get() = 0; }; template class OperationTemplate { public: typedef typename OperationClass::value_type value_type; OperationTemplate(OperationClass* oc); template auto operator+(const Second& in) const -> Operation,OperationClass,Second>; template auto operator-(const Second& in) const -> Operation,OperationClass,Second>; template auto operator*(const Second& in) const -> Operation,OperationClass,Second>; template auto operator/(const Second& in) const -> Operation,OperationClass,Second>; private: OperationClass* mOc; }; template class OperationMaster : public MutableOperationBase { public: typedef T value_type; typedef OperationBase OB; typedef ContainerRange CRange; typedef typename MultiRange::IndexType IndexType; OperationMaster(MutableMultiArrayBase& ma, const OperationBase& second, std::shared_ptr& index); virtual BlockBase& get() override; virtual const BlockBase& get() const override; protected: //void performAssignment(const OperationBase& in); OperationBase const& mSecond; MutableMultiArrayBase& mArrayRef; std::shared_ptr mIndex; }; template class ConstOperationRoot : public OperationBase, public OperationTemplate > { public: typedef T value_type; typedef OperationBase OB; typedef OperationTemplate > OT; typedef ContainerRange CRange; typedef typename CRange::IndexType IndexType; ConstOperationRoot(const MultiArrayBase& ma, const std::shared_ptr&... indices); virtual const BlockBase& get() const override; protected: MultiArrayBase const& mArrayRef; std::shared_ptr mIndex; }; template class OperationRoot : public MutableOperationBase, public OperationTemplate > { public: typedef T value_type; typedef OperationBase OB; typedef OperationTemplate > OT; typedef ContainerRange CRange; typedef typename CRange::IndexType IndexType; OperationRoot(MutableMultiArrayBase& ma, const std::shared_ptr&... indices); OperationMaster operator=(const OperationBase& in); virtual const BlockBase& get() const override; virtual BlockBase& get() override; protected: MutableMultiArrayBase& mArrayRef; std::shared_ptr mIndex; }; template class Operation : public OperationBase, public OperationTemplate > { public: typedef T value_type; typedef OperationBase OB; typedef OperationTemplate > OT; typedef OpFunction F; Operation(const Ops&... ops); virtual const BlockBase& get() const override; protected: std::tuple mOps; mutable BlockResult mRes; }; } #include "multi_array_operation.cc" #endif