glucat  0.8.4
framed_multi.h
Go to the documentation of this file.
1 #ifndef _GLUCAT_FRAMED_MULTI_H
2 #define _GLUCAT_FRAMED_MULTI_H
3 /***************************************************************************
4  GluCat : Generic library of universal Clifford algebra templates
5  framed_multi.h : Declare a class for the framed representation of a multivector
6  -------------------
7  begin : Sun 2001-12-09
8  copyright : (C) 2001-2016 by Paul C. Leopardi
9  ***************************************************************************
10 
11  This library is free software: you can redistribute it and/or modify
12  it under the terms of the GNU Lesser General Public License as published
13  by the Free Software Foundation, either version 3 of the License, or
14  (at your option) any later version.
15 
16  This library is distributed in the hope that it will be useful,
17  but WITHOUT ANY WARRANTY; without even the implied warranty of
18  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
19  GNU Lesser General Public License for more details.
20 
21  You should have received a copy of the GNU Lesser General Public License
22  along with this library. If not, see <http://www.gnu.org/licenses/>.
23 
24  ***************************************************************************
25  This library is based on a prototype written by Arvind Raja and was
26  licensed under the LGPL with permission of the author. See Arvind Raja,
27  "Object-oriented implementations of Clifford algebras in C++: a prototype",
28  in Ablamowicz, Lounesto and Parra (eds.)
29  "Clifford algebras with numeric and symbolic computations", Birkhauser, 1996.
30  ***************************************************************************
31  See also Arvind Raja's original header comments in glucat.h
32  ***************************************************************************/
33 
34 #include "glucat/global.h"
35 #include "glucat/errors.h"
37 
38 #if defined(_GLUCAT_USE_BOOST_POOL_ALLOC)
39 // Use the Boost pool allocator
40 #include <boost/pool/poolfwd.hpp>
41 #endif
42 
43 #include <string>
44 #include <utility>
45 #include <map>
46 #include <vector>
47 
48 // Use the appropriate type of map
49 
50 #if defined(_GLUCAT_USE_STD_UNORDERED_MAP)
51 # include <unordered_map>
52 #endif
53 
54 #if defined(_GLUCAT_USE_STD_UNORDERED_MAP)
55 # define _GLUCAT_MAP_IS_HASH
56 #else
57 # define _GLUCAT_MAP_IS_ORDERED
58 #endif
59 
60 namespace glucat
61 {
62  // Forward declarations for friends
63 
64  template< typename Scalar_T, const index_t LO, const index_t HI >
65  class framed_multi; // forward
66 
67  template< typename Scalar_T, const index_t LO, const index_t HI >
68  class matrix_multi; // forward
69 
71  template< typename Scalar_T, const index_t LO, const index_t HI >
74 
76  template< typename Scalar_T, const index_t LO, const index_t HI >
79 
81  template< typename Scalar_T, const index_t LO, const index_t HI >
84 
86  template< typename Scalar_T, const index_t LO, const index_t HI >
89 
91  template< typename Scalar_T, const index_t LO, const index_t HI >
92  Scalar_T
94 
96  template< typename Scalar_T, const index_t LO, const index_t HI >
99 
101  template< typename Scalar_T, const index_t LO, const index_t HI >
104 
106  template< typename Scalar_T, const index_t LO, const index_t HI >
107  std::istream&
108  operator>> (std::istream& s, framed_multi<Scalar_T,LO,HI>& val);
109 
111  template< typename Scalar_T, const index_t LO, const index_t HI >
112  std::ostream&
113  operator<< (std::ostream& os, const framed_multi<Scalar_T,LO,HI>& val);
114 
116  template< typename Scalar_T, const index_t LO, const index_t HI >
117  std::ostream&
118  operator<< (std::ostream& os, const std::pair< const index_set<LO,HI>, Scalar_T >& term);
119 
121  template< typename Scalar_T, const index_t LO, const index_t HI >
123  exp(const framed_multi<Scalar_T,LO,HI>& val);
124 
125  template< const index_t LO, const index_t HI>
127  {
128  public:
130  inline size_t operator()(index_set_t val) const { return val.hash_fn(); }
131  };
132 
134  template< typename Scalar_T = double, const index_t LO = DEFAULT_LO, const index_t HI = DEFAULT_HI >
135  class framed_multi :
136  public clifford_algebra< Scalar_T, index_set<LO,HI>, framed_multi<Scalar_T,LO,HI> >,
137 #if defined(_GLUCAT_USE_STD_UNORDERED_MAP)
138  private std::unordered_map< index_set<LO,HI>, Scalar_T, index_set_hash<LO,HI> >
139 #else
140  private std::map< index_set<LO,HI>, Scalar_T,
141  std::less< const index_set<LO,HI> >
142 #if defined(_GLUCAT_USE_BOOST_POOL_ALLOC)
143  , boost::fast_pool_allocator< std::pair<const index_set<LO,HI>, Scalar_T> >
144 #endif
145  >
146 #endif
147  {
148  public:
151  typedef Scalar_T scalar_t;
153  typedef std::pair<const index_set_t, Scalar_T> term_t;
154  typedef std::vector<Scalar_T> vector_t;
157  template< typename Other_Scalar_T, const index_t Other_LO, const index_t Other_HI >
158  friend class matrix_multi;
159  template< typename Other_Scalar_T, const index_t Other_LO, const index_t Other_HI >
160  friend class framed_multi;
161 
162  private:
163  class var_term; // forward
164  typedef class var_term var_term_t;
166  typedef std::map< index_set_t, Scalar_T,
167  std::less<const index_set_t>
168 #if defined(_GLUCAT_USE_BOOST_POOL_ALLOC)
169  , boost::fast_pool_allocator<term_t>
170 #endif
171  >
173 #if defined(_GLUCAT_USE_STD_UNORDERED_MAP)
174  typedef std::unordered_map< index_set_t, Scalar_T, index_set_hash<LO,HI> >
176 #else
177  typedef sorted_map_t map_t;
178 #endif
179 
181  {
182  public:
183  hash_size_t(size_t hash_size)
184  : n(hash_size)
185  { };
186  size_t operator()() const
187  { return n; }
188  private:
189  size_t n;
190  };
191 
192  typedef std::pair< const multivector_t, const multivector_t >
194  typedef typename map_t::size_type size_type;
195  typedef typename map_t::iterator iterator;
196  typedef typename map_t::const_iterator const_iterator;
197 
198  public:
200  static const std::string classname();
204  framed_multi();
205 
206  private:
208  framed_multi(const hash_size_t& hash_size);
209  public:
211  template< typename Other_Scalar_T >
214  template< typename Other_Scalar_T >
216  const index_set_t frm, const bool prechecked = false);
218  framed_multi(const framed_multi_t& val,
219  const index_set_t frm, const bool prechecked = false);
221  framed_multi(const index_set_t ist, const Scalar_T& crd = Scalar_T(1));
223  framed_multi(const index_set_t ist, const Scalar_T& crd,
224  const index_set_t frm, const bool prechecked = false);
226  framed_multi(const Scalar_T& scr, const index_set_t frm = index_set_t());
228  framed_multi(const int scr, const index_set_t frm = index_set_t());
230  framed_multi(const vector_t& vec,
231  const index_set_t frm, const bool prechecked = false);
233  framed_multi(const std::string& str);
235  framed_multi(const std::string& str,
236  const index_set_t frm, const bool prechecked = false);
238  framed_multi(const char* str)
239  { *this = framed_multi(std::string(str)); };
241  framed_multi(const char* str,
242  const index_set_t frm, const bool prechecked = false)
243  { *this = framed_multi(std::string(str), frm, prechecked); };
245  template< typename Other_Scalar_T >
248  template< typename Other_Scalar_T >
251  const framed_multi_t fast_framed_multi() const;
252 
254 
256  unsigned long nbr_terms() const;
257 
259  static const framed_multi_t random(const index_set_t frm, Scalar_T fill = Scalar_T(1));
260 
261  // Friend declarations
262 
263  friend const framed_multi_t
264  operator* <>(const framed_multi_t& lhs, const framed_multi_t& rhs);
265  friend const framed_multi_t
266  operator^ <>(const framed_multi_t& lhs, const framed_multi_t& rhs);
267  friend const framed_multi_t
268  operator& <>(const framed_multi_t& lhs, const framed_multi_t& rhs);
269  friend const framed_multi_t
270  operator% <>(const framed_multi_t& lhs, const framed_multi_t& rhs);
271  friend Scalar_T
272  star <>(const framed_multi_t& lhs, const framed_multi_t& rhs);
273  friend const framed_multi_t
274  operator/ <>(const framed_multi_t& lhs, const framed_multi_t& rhs);
275  friend const framed_multi_t
276  operator| <>(const framed_multi_t& lhs, const framed_multi_t& rhs);
277 
278  friend std::istream&
279  operator>> <>(std::istream& s, multivector_t& val);
280  friend std::ostream&
281  operator<< <>(std::ostream& os, const multivector_t& val);
282  friend std::ostream&
283  operator<< <>(std::ostream& os, const term_t& term);
284 
285  friend const framed_multi_t
286  exp <>(const framed_multi_t& val);
287 
289  multivector_t& operator+= (const term_t& term);
290 
291  private:
293  multivector_t fold(const index_set_t frm) const;
295  multivector_t unfold(const index_set_t frm) const;
303  const framed_pair_t divide(const index_set_t ist) const;
305  const matrix_t fast(const index_t level, const bool odd) const;
306 
308  class var_term :
309  public std::pair<index_set<LO,HI>, Scalar_T>
310  {
311  public:
312  typedef std::pair<index_set<LO,HI>, Scalar_T> var_pair_t;
313 
315  static const std::string classname()
316  { return "var_term"; };
318  ~var_term() {};
321  : var_pair_t(index_set_t(), Scalar_T(1))
322  { };
324  var_term(const index_set_t ist, const Scalar_T& crd = Scalar_T(1))
325  : var_pair_t(ist, crd)
326  { };
329  {
330  this->second *= rhs.second * this->first.sign_of_mult(rhs.first);
331  this->first ^= rhs.first;
332  return *this;
333  }
334  };
335  };
336 
337  // Non-members
338 
340  template< typename Scalar_T, const index_t LO, const index_t HI >
341  inline
342  static
343  Scalar_T
344  crd_of_mult(const std::pair<const index_set<LO,HI>, Scalar_T>& lhs,
345  const std::pair<const index_set<LO,HI>, Scalar_T>& rhs);
346 
348  template< typename Scalar_T, const index_t LO, const index_t HI >
349  const std::pair<const index_set<LO,HI>, Scalar_T>
350  operator*
351  (const std::pair<const index_set<LO,HI>, Scalar_T>& lhs,
352  const std::pair<const index_set<LO,HI>, Scalar_T>& rhs);
353 
355  template< typename Scalar_T, const index_t LO, const index_t HI >
357  sqrt(const framed_multi<Scalar_T,LO,HI>& val, const framed_multi<Scalar_T,LO,HI>& i, bool prechecked);
358 
360  template< typename Scalar_T, const index_t LO, const index_t HI >
362  exp(const framed_multi<Scalar_T,LO,HI>& val);
363 
365  template< typename Scalar_T, const index_t LO, const index_t HI >
367  log(const framed_multi<Scalar_T,LO,HI>& val, const framed_multi<Scalar_T,LO,HI>& i, bool prechecked);
368 }
369 
370 namespace std
371 {
373  template <typename Scalar_T, const glucat::index_t LO, const glucat::index_t HI>
374  struct numeric_limits< glucat::framed_multi<Scalar_T,LO,HI> > :
375  public numeric_limits<Scalar_T>
376  { };
377 }
378 #endif // _GLUCAT_FRAMED_MULTI_H
glucat::framed_multi::framed_multi_t
multivector_t framed_multi_t
Definition: framed_multi.h:150
glucat::operator%
const Multivector< Scalar_T, LO, HI > operator%(const Multivector< Scalar_T, LO, HI > &lhs, const RHS< Scalar_T, LO, HI > &rhs)
Left contraction.
Definition: clifford_algebra_imp.h:272
global.h
glucat::framed_multi::var_term_t
class var_term var_term_t
Definition: framed_multi.h:164
glucat::framed_multi::var_term::var_pair_t
std::pair< index_set< LO, HI >, Scalar_T > var_pair_t
Definition: framed_multi.h:312
glucat::framed_multi::size_type
map_t::size_type size_type
Definition: framed_multi.h:194
glucat::framed_multi::var_term::~var_term
~var_term()
Destructor.
Definition: framed_multi.h:318
glucat::framed_multi::index_set_t
index_set< LO, HI > index_set_t
Definition: framed_multi.h:152
clifford_algebra.h
glucat::framed_multi::hash_size_t::n
size_t n
Definition: framed_multi.h:189
glucat::framed_multi::iterator
map_t::iterator iterator
Definition: framed_multi.h:195
glucat::framed_multi::centre_qp1_pm1
multivector_t & centre_qp1_pm1(index_t &p, index_t &q)
Subalgebra isomorphism: R_{p,q} to R_{q+1,p-1}.
Definition: framed_multi_imp.h:1775
glucat::framed_multi::multivector_t
framed_multi multivector_t
Definition: framed_multi.h:149
glucat::framed_multi::hash_size_t
Definition: framed_multi.h:181
glucat::framed_multi::const_iterator
map_t::const_iterator const_iterator
Definition: framed_multi.h:196
glucat::operator|
const Multivector< Scalar_T, LO, HI > operator|(const Multivector< Scalar_T, LO, HI > &lhs, const RHS< Scalar_T, LO, HI > &rhs)
Transformation via twisted adjoint action.
Definition: clifford_algebra_imp.h:339
PyClical.i
i
Definition: PyClical.pyx:1541
glucat::framed_multi::var_term::operator*=
var_term_t & operator*=(const term_t &rhs)
Product of variable term and term.
Definition: framed_multi.h:328
glucat::framed_multi::matrix_t
matrix_multi_t::matrix_t matrix_t
Definition: framed_multi.h:165
PyClical.ist
ist
Definition: PyClical.pyx:1878
glucat::framed_multi::var_term::classname
static const std::string classname()
Class name used in messages.
Definition: framed_multi.h:315
glucat::framed_multi::~framed_multi
~framed_multi()
Destructor.
Definition: framed_multi.h:202
errors.h
glucat::framed_multi::classname
static const std::string classname()
Class name used in messages.
Definition: framed_multi_imp.h:83
glucat::index_t
int index_t
Size of index_t should be enough to represent LO, HI.
Definition: global.h:106
glucat::framed_multi::framed_pair_t
std::pair< const multivector_t, const multivector_t > framed_pair_t
Definition: framed_multi.h:193
glucat::framed_multi::hash_size_t::hash_size_t
hash_size_t(size_t hash_size)
Definition: framed_multi.h:183
glucat::framed_multi::vector_t
std::vector< Scalar_T > vector_t
Definition: framed_multi.h:154
glucat::index_set
Index set class based on std::bitset<> in Gnu standard C++ library.
Definition: index_set.h:74
glucat::matrix_multi::matrix_t
ublas::compressed_matrix< Scalar_T, orientation_t > matrix_t
Definition: matrix_multi.h:186
glucat::operator>>
std::istream & operator>>(std::istream &s, framed_multi< Scalar_T, LO, HI > &val)
Read multivector from input.
Definition: framed_multi_imp.h:1466
glucat::framed_multi::map_t
std::unordered_map< index_set_t, Scalar_T, index_set_hash< LO, HI > > map_t
Definition: framed_multi.h:175
glucat::operator<<
std::ostream & operator<<(std::ostream &os, const framed_multi< Scalar_T, LO, HI > &val)
Write multivector to output.
Definition: framed_multi_imp.h:1396
glucat::star
Scalar_T star(const Multivector< Scalar_T, LO, HI > &lhs, const RHS< Scalar_T, LO, HI > &rhs)
Hestenes scalar product.
Definition: clifford_algebra_imp.h:287
glucat::framed_multi::var_term
Variable term.
Definition: framed_multi.h:310
glucat::framed_multi::var_term::var_term
var_term()
Default constructor.
Definition: framed_multi.h:320
glucat::framed_multi::centre_pp4_qm4
multivector_t & centre_pp4_qm4(index_t &p, index_t &q)
Subalgebra isomorphism: R_{p,q} to R_{p+4,q-4}.
Definition: framed_multi_imp.h:1730
glucat::framed_multi::framed_multi
framed_multi(const char *str, const index_set_t frm, const bool prechecked=false)
Construct a multivector, within a given frame, from a char*: eg: "3+2{1,2}-6.1e-2{2,...
Definition: framed_multi.h:241
glucat::index_set_hash::index_set_t
index_set< LO, HI > index_set_t
Definition: framed_multi.h:129
glucat::crd_of_mult
static Scalar_T crd_of_mult(const std::pair< const index_set< LO, HI >, Scalar_T > &lhs, const std::pair< const index_set< LO, HI >, Scalar_T > &rhs)
Coordinate of product of terms.
glucat::operator/
const Multivector< Scalar_T, LO, HI > operator/(const Multivector< Scalar_T, LO, HI > &lhs, const Scalar_T &scr)
Quotient of multivector and scalar.
Definition: clifford_algebra_imp.h:298
_GLUCAT_CLIFFORD_ALGEBRA_OPERATIONS
#define _GLUCAT_CLIFFORD_ALGEBRA_OPERATIONS
Definition: clifford_algebra.h:163
PyClical.fill
fill
Definition: PyClical.pyx:1814
glucat::framed_multi::term_t
std::pair< const index_set_t, Scalar_T > term_t
Definition: framed_multi.h:153
glucat::framed_multi::unfold
multivector_t unfold(const index_set_t frm) const
Subalgebra isomorphism: unfold each term within the given frame.
Definition: framed_multi_imp.h:1664
glucat::sqrt
const Multivector< Scalar_T, LO, HI > sqrt(const Multivector< Scalar_T, LO, HI > &val, const Multivector< Scalar_T, LO, HI > &i, const bool prechecked=false)
Square root of multivector with specified complexifier.
Definition: clifford_algebra_imp.h:618
glucat::index_set_hash::operator()
size_t operator()(index_set_t val) const
Definition: framed_multi.h:130
glucat::framed_multi::fold
multivector_t fold(const index_set_t frm) const
Subalgebra isomorphism: fold each term within the given frame.
Definition: framed_multi_imp.h:1644
glucat::framed_multi::framed_multi
framed_multi(const char *str)
Construct a multivector from a char*: eg: "3+2{1,2}-6.1e-2{2,3}".
Definition: framed_multi.h:238
glucat::matrix_multi
A matrix_multi<Scalar_T,LO,HI> is a matrix approximation to a multivector.
Definition: framed_multi.h:68
glucat::error
Specific exception class.
Definition: errors.h:87
glucat::framed_multi
A framed_multi<Scalar_T,LO,HI> is a framed approximation to a multivector.
Definition: framed_multi.h:65
glucat::framed_multi::framed_multi
friend class framed_multi
Definition: framed_multi.h:160
glucat::framed_multi::scalar_t
Scalar_T scalar_t
Definition: framed_multi.h:151
glucat::log
const Multivector< Scalar_T, LO, HI > log(const Multivector< Scalar_T, LO, HI > &val, const Multivector< Scalar_T, LO, HI > &i, const bool prechecked=false)
Natural logarithm of multivector with specified complexifier.
Definition: clifford_algebra_imp.h:733
glucat::operator*
const Multivector< Scalar_T, LO, HI > operator*(const Multivector< Scalar_T, LO, HI > &lhs, const Scalar_T &scr)
Product of multivector and scalar.
Definition: clifford_algebra_imp.h:201
glucat::odd
const Multivector< Scalar_T, LO, HI > odd(const Multivector< Scalar_T, LO, HI > &val)
Odd part.
Definition: clifford_algebra_imp.h:464
glucat::operator&
const Multivector< Scalar_T, LO, HI > operator&(const Multivector< Scalar_T, LO, HI > &lhs, const RHS< Scalar_T, LO, HI > &rhs)
Inner product.
Definition: clifford_algebra_imp.h:257
glucat::index_set_hash
Definition: framed_multi.h:127
glucat::framed_multi::var_term::var_term
var_term(const index_set_t ist, const Scalar_T &crd=Scalar_T(1))
Construct a variable term from an index set and a scalar coordinate.
Definition: framed_multi.h:324
std
Definition: framed_multi.h:371
glucat
Definition: clifford_algebra.h:39
glucat::framed_multi::error_t
error< multivector_t > error_t
Definition: framed_multi.h:155
glucat::framed_multi::matrix_multi_t
matrix_multi< Scalar_T, LO, HI > matrix_multi_t
Definition: framed_multi.h:156
glucat::framed_multi::hash_size_t::operator()
size_t operator()() const
Definition: framed_multi.h:186
glucat::framed_multi::fast
const matrix_t fast(const index_t level, const bool odd) const
Generalized FFT from framed_multi_t to matrix_t.
Definition: framed_multi_imp.h:1830
glucat::framed_multi::sorted_map_t
std::map< index_set_t, Scalar_T, std::less< const index_set_t > > sorted_map_t
Definition: framed_multi.h:172
glucat::framed_multi::fast_framed_multi
const framed_multi_t fast_framed_multi() const
Use inverse generalized FFT to construct a framed_multi_t.
Definition: framed_multi_imp.h:1928
glucat::framed_multi::fast_matrix_multi
const matrix_multi< Other_Scalar_T, LO, HI > fast_matrix_multi(const index_set_t frm) const
Use generalized FFT to construct a matrix_multi_t.
Definition: framed_multi_imp.h:1896
glucat::index_set::hash_fn
size_t hash_fn() const
Hash function.
Definition: index_set_imp.h:977
glucat::framed_multi::random
static const framed_multi_t random(const index_set_t frm, Scalar_T fill=Scalar_T(1))
Random multivector within a frame.
Definition: framed_multi_imp.h:1303
glucat::framed_multi::nbr_terms
_GLUCAT_CLIFFORD_ALGEBRA_OPERATIONS unsigned long nbr_terms() const
Number of terms.
Definition: framed_multi_imp.h:1575
glucat::framed_multi::operator+=
multivector_t & operator+=(const term_t &term)
Add a term, if non-zero.
Definition: framed_multi_imp.h:359
glucat::exp
const framed_multi< Scalar_T, LO, HI > exp(const framed_multi< Scalar_T, LO, HI > &val)
Exponential of multivector.
Definition: framed_multi_imp.h:1977
glucat::operator^
const Multivector< Scalar_T, LO, HI > operator^(const Multivector< Scalar_T, LO, HI > &lhs, const RHS< Scalar_T, LO, HI > &rhs)
Outer product.
Definition: clifford_algebra_imp.h:242
glucat::framed_multi::centre_pm4_qp4
multivector_t & centre_pm4_qp4(index_t &p, index_t &q)
Subalgebra isomorphism: R_{p,q} to R_{p-4,q+4}.
Definition: framed_multi_imp.h:1685
glucat::framed_multi::divide
const framed_pair_t divide(const index_set_t ist) const
Divide multivector into part divisible by index_set and remainder.
Definition: framed_multi_imp.h:1811