7#include <initializer_list>
17#define ADD_DEBUG_TENSOR( X, Y ) \
18 if ( Y != nullptr ) for( unsigned i = 0 ; i < Tensor(X).size(); ++i ) \
19 Y->emplace_back( std::string(#X) + Tensor::coordinates_to_string( Tensor(X).coords(i) ) , Tensor(X)[i] );
21#define ADD_DEBUG_TENSOR_NAMED( X, Y, Z ) \
22 if ( Y != nullptr ) for( unsigned i = 0 ; i < X.size(); ++i ) \
23 Y->emplace_back( Z + Tensor::coordinates_to_string( X.coords(i) ) , X[i] );
35 std::shared_ptr<int> m_ptr;
40 bool isUpper()
const {
return m_isUpper; };
45 uint64_t
ptr()
const {
return uint64_t(m_ptr.get()); }
47 struct Dim :
public std::vector<unsigned> {
48 Dim(
unsigned a ) : std::vector<unsigned>({a}) {}
49 Dim(
unsigned a ,
unsigned b) : std::vector<unsigned>({a,b}) {}
50 Dim(
unsigned a ,
unsigned b,
unsigned c) : std::vector<unsigned>({a,b,c}) {}
51 Dim(
unsigned a ,
unsigned b,
unsigned c,
unsigned d ) : std::vector<unsigned>({a,b,c,d}) {}
56 explicit Tensor(
const std::vector<Expression>& elements);
60 template <
class TYPE>
Tensor(
const std::initializer_list<TYPE>& elements,
61 const std::vector<unsigned>&
dim) : m_dim(
dim)
64 for (
auto& x : elements )
append( x );
67 template <
class TYPE>
Tensor(
const std::vector<TYPE>& elements,
68 const std::vector<unsigned>&
dim) : m_dim(
dim)
71 for (
auto& x : elements )
append( x );
101 void st(
const bool simplify=
false);
110 int metricSgn(
const std::vector<unsigned>& coordinates )
const;
121 unsigned index(
const std::vector<unsigned>& _co )
const;
125 const std::vector<unsigned>
coords(
const unsigned&
index )
const;
126 const std::vector<unsigned>&
dims()
const {
return m_dim; }
129 void print(
const bool& eval =
false)
const;
139 template <
class... ARGS>
140 static std::vector<unsigned>
dim(
const ARGS&... args ){
141 std::vector<unsigned> rt;
142 auto up = std::tuple<ARGS...>(args...);
143 for_each(up, [&rt](
const unsigned& f ) { rt.emplace_back(f); } );
147 std::vector<unsigned> m_dim;
148 std::vector<unsigned> m_symmetrisedCoordinates;
149 std::vector<unsigned> m_uniqueElements;
150 std::vector<Expression> m_elements;
173 std::vector<Tensor::Index> m_indices;
185 unsigned size()
const {
return m_tensor.size(); }
(Internal) class to aide in the resolution of the dependencies of expression trees.
Wrapper class for shared_ptrs to virtual expressions for use in conjunction with operators to build e...
Virtual base class for other expression tree components.
Index(bool isUpper=false)
bool operator!=(const Tensor::Index &other) const
bool operator==(const Tensor::Index &other) const
Index(const std::shared_ptr< int > &index, bool isUpper=false)
friend std::ostream & operator<<(std::ostream &out, const Index &index)
void resolve(ASTResolver &resolver) const override
Resolve the dependencies of a tree using an ASTResolver, which keeps track of parameters,...
std::string to_string(const ASTResolver *resolver) const override
Called to convert the Expression tree into source code.
complex_t operator()() const override
Evaluate the expression using the tree, will generally be very slow but ocassionally useful for debug...
TensorExpression(const Tensor &tensor)
Tensor(const Tensor::Dim &dim)
unsigned nElements() const
Expression get(const unsigned &co) const
const Expression & operator()(const unsigned &a, const unsigned &b) const
const std::vector< unsigned > coords(const unsigned &index) const
int metricSgn(const unsigned &index) const
void append(const real_t &value)
void append(const std::string &value)
std::string to_string(const ASTResolver *resolver=nullptr) const
Tensor(const std::vector< TYPE > &elements, const std::vector< unsigned > &dim)
void append(const Expression &expression)
unsigned symmetrisedIndex(const std::vector< unsigned > &_co) const
const Expression operator()(const unsigned &a) const
void append(const complex_t &value)
const std::vector< unsigned > & uniqueElements() const
Tensor(const std::vector< Expression > &elements)
Expression & operator()(const unsigned &a)
TensorProxy access to class members High level access is done via these commands, i....
void st(const bool simplify=false)
const Expression & operator[](const unsigned &i) const
Expression & operator[](const unsigned &i)
Low level access of elements, either by coordinates or by index ///.
void operator+=(const Tensor &rhs)
static std::vector< unsigned > index_to_coordinates(const unsigned &index, const std::vector< unsigned > &dim)
Expression & operator[](const std::vector< unsigned > &co)
Expression get(const std::vector< unsigned > &_co) const
const Expression & operator[](const std::vector< unsigned > &co) const
Tensor(const std::vector< unsigned > &dim)
TensorProxy operator()(const Tensor::Index &a, const Tensor::Index &b) const
TensorProxy operator()(const Tensor::Index &a, const Tensor::Index &b, const Tensor::Index &c) const
unsigned index(const std::vector< unsigned > &_co) const
Tensor(const std::initializer_list< TYPE > &elements, const std::vector< unsigned > &dim)
static unsigned coordinates_to_index(const std::vector< unsigned > &coords, const std::vector< unsigned > &dim)
void imposeSymmetry(std::vector< unsigned > indices)
void operator-=(const Tensor &rhs)
int metricSgn(const std::vector< unsigned > &coordinates) const
void print(const bool &eval=false) const
bool rankMatches(const Tensor &other)
const std::string dimString() const
TensorProxy operator()(const Tensor::Index &a, const Tensor::Index &b, const Tensor::Index &c, const Tensor::Index &d) const
TensorProxy operator()(const std::vector< Tensor::Index > &indices) const
Expression get(const unsigned &co)
void imposeSymmetry(unsigned indexA, unsigned indexB)
TensorProxy operator()(const Tensor::Index &a) const
Expression & operator()(const unsigned &a, const unsigned &b)
static std::vector< unsigned > dim(const ARGS &... args)
const std::vector< unsigned > & dims() const
static std::string coordinates_to_string(const std::vector< unsigned > &coordinates)
Utility class that wraps a tensor and a set of indices such that tensor operations can be performed.
const Tensor & tensor() const
TensorProxy reorder(const std::vector< Tensor::Index > &indices)
TensorProxy(const Tensor &tensor, const std::vector< Tensor::Index > &indices)
std::vector< Tensor::Index > indices() const
Complex< real_t > operator/(const Complex< real_t > &lhs, const R2_t &rhs)
Complex< real_t > operator*(const Complex< real_t > &lhs, const R2_t &rhs)
std::complex< real_t > complex_t
Expression dot(const Tensor &A, const Tensor &B)
std::ostream & operator<<(std::ostream &os, const CompiledExpressionBase &expression)
const Tensor LeviCivita(const unsigned &rank=4)
Complex< real_t > operator+(const Complex< real_t > &lhs, const R2_t &rhs)
Complex< real_t > operator-(const Complex< real_t > &lhs, const R2_t &rhs)
Tensor Identity(const unsigned &rank=4)
std::enable_if_t< I==sizeof...(Tp), void > for_each(std::tuple< Tp... > &, FuncT)
Dim(unsigned a, unsigned b)
Dim(unsigned a, unsigned b, unsigned c, unsigned d)
Dim(unsigned a, unsigned b, unsigned c)