* Implementation of GiNaC's non-commutative products of expressions. */
/*
- * GiNaC Copyright (C) 1999-2001 Johannes Gutenberg University Mainz, Germany
+ * GiNaC Copyright (C) 1999-2003 Johannes Gutenberg University Mainz, Germany
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
GINAC_IMPLEMENT_REGISTERED_CLASS(ncmul, exprseq)
//////////
-// default ctor, dtor, copy ctor, assignment operator and helpers
+// default constructor
//////////
ncmul::ncmul()
tinfo_key = TINFO_ncmul;
}
-DEFAULT_COPY(ncmul)
-DEFAULT_DESTROY(ncmul)
-
//////////
// other constructors
//////////
intvector positions_of_adds(expanded_seq.size());
intvector number_of_add_operands(expanded_seq.size());
- int number_of_adds = 0;
- int number_of_expanded_terms = 1;
+ size_t number_of_adds = 0;
+ size_t number_of_expanded_terms = 1;
- unsigned current_position = 0;
+ size_t current_position = 0;
exvector::const_iterator last = expanded_seq.end();
for (exvector::const_iterator cit=expanded_seq.begin(); cit!=last; ++cit) {
if (is_exactly_a<add>(*cit)) {
positions_of_adds[number_of_adds] = current_position;
- unsigned num_ops = cit->nops();
+ size_t num_ops = cit->nops();
number_of_add_operands[number_of_adds] = num_ops;
number_of_expanded_terms *= num_ops;
number_of_adds++;
while (true) {
exvector term = expanded_seq;
- for (int i=0; i<number_of_adds; i++)
+ for (size_t i=0; i<number_of_adds; i++)
term[positions_of_adds[i]] = expanded_seq[positions_of_adds[i]].op(k[i]);
distrseq.push_back((new ncmul(term, true))->
setflag(status_flags::dynallocated | (options == 0 ? status_flags::expanded : 0)));
return _ex0;
}
-unsigned ncmul::count_factors(const ex & e) const
+size_t ncmul::count_factors(const ex & e) const
{
- if ((is_ex_exactly_of_type(e,mul)&&(e.return_type()!=return_types::commutative))||
- (is_ex_exactly_of_type(e,ncmul))) {
- unsigned factors=0;
- for (unsigned i=0; i<e.nops(); i++)
+ if ((is_exactly_a<mul>(e)&&(e.return_type()!=return_types::commutative))||
+ (is_exactly_a<ncmul>(e))) {
+ size_t factors=0;
+ for (size_t i=0; i<e.nops(); i++)
factors += count_factors(e.op(i));
return factors;
void ncmul::append_factors(exvector & v, const ex & e) const
{
- if ((is_ex_exactly_of_type(e,mul)&&(e.return_type()!=return_types::commutative))||
- (is_ex_exactly_of_type(e,ncmul))) {
- for (unsigned i=0; i<e.nops(); i++)
- append_factors(v,e.op(i));
+ if ((is_exactly_a<mul>(e)&&(e.return_type()!=return_types::commutative))||
+ (is_exactly_a<ncmul>(e))) {
+ for (size_t i=0; i<e.nops(); i++)
+ append_factors(v, e.op(i));
} else
v.push_back(e);
}
* - ncmul() -> 1
* - ncmul(...,c1,...,c2,...) -> *(c1,c2,ncmul(...)) (pull out commutative elements)
* - ncmul(x1,y1,x2,y2) -> *(ncmul(x1,x2),ncmul(y1,y2)) (collect elements of same type)
- * - ncmul(x1,x2,x3,...) -> x::simplify_ncmul(x1,x2,x3,...)
+ * - ncmul(x1,x2,x3,...) -> x::eval_ncmul(x1,x2,x3,...)
*
* @param level cut-off in recursive evaluation */
ex ncmul::eval(int level) const
// ncmul(...,*(x1,x2),...,ncmul(x3,x4),...) ->
// ncmul(...,x1,x2,...,x3,x4,...) (associativity)
- unsigned factors = 0;
+ size_t factors = 0;
exvector::const_iterator cit = evaledseq.begin(), citend = evaledseq.end();
while (cit != citend)
factors += count_factors(*cit++);
// determine return types
unsignedvector rettypes;
rettypes.reserve(assocseq.size());
- unsigned i = 0;
- unsigned count_commutative=0;
- unsigned count_noncommutative=0;
- unsigned count_noncommutative_composite=0;
+ size_t i = 0;
+ size_t count_commutative=0;
+ size_t count_noncommutative=0;
+ size_t count_noncommutative_composite=0;
cit = assocseq.begin(); citend = assocseq.end();
while (cit != citend) {
switch (rettypes[i] = cit->return_type()) {
commutativeseq.reserve(count_commutative+1);
exvector noncommutativeseq;
noncommutativeseq.reserve(assocseq.size()-count_commutative);
- unsigned num = assocseq.size();
- for (unsigned i=0; i<num; ++i) {
+ size_t num = assocseq.size();
+ for (size_t i=0; i<num; ++i) {
if (rettypes[i]==return_types::commutative)
commutativeseq.push_back(assocseq[i]);
else
// elements in assocseq
GINAC_ASSERT(count_commutative==0);
- unsigned assoc_num = assocseq.size();
+ size_t assoc_num = assocseq.size();
exvectorvector evv;
unsignedvector rttinfos;
evv.reserve(assoc_num);
cit = assocseq.begin(), citend = assocseq.end();
while (cit != citend) {
unsigned ti = cit->return_type_tinfo();
- unsigned rtt_num = rttinfos.size();
+ size_t rtt_num = rttinfos.size();
// search type in vector of known types
for (i=0; i<rtt_num; ++i) {
if (ti == rttinfos[i]) {
++cit;
}
- unsigned evv_num = evv.size();
+ size_t evv_num = evv.size();
#ifdef DO_GINAC_ASSERT
GINAC_ASSERT(evv_num == rttinfos.size());
GINAC_ASSERT(evv_num > 0);
- unsigned s=0;
+ size_t s=0;
for (i=0; i<evv_num; ++i)
s += evv[i].size();
GINAC_ASSERT(s == assoc_num);
// if all elements are of same type, simplify the string
if (evv_num == 1)
- return evv[0][0].simplify_ncmul(evv[0]);
+ return evv[0][0].eval_ncmul(evv[0]);
exvector splitseq;
splitseq.reserve(evv_num);
status_flags::evaluated);
}
-ex ncmul::evalm(void) const
+ex ncmul::evalm() const
{
// Evaluate children first
exvector *s = new exvector;
// If there are only matrices, simply multiply them
it = s->begin(); itend = s->end();
- if (is_ex_of_type(*it, matrix)) {
+ if (is_a<matrix>(*it)) {
matrix prod(ex_to<matrix>(*it));
it++;
while (it != itend) {
- if (!is_ex_of_type(*it, matrix))
+ if (!is_a<matrix>(*it))
goto no_matrix;
prod = prod.mul(ex_to<matrix>(*it));
it++;
return (new ncmul(s))->setflag(status_flags::dynallocated);
}
-ex ncmul::thisexprseq(const exvector & v) const
+ex ncmul::thiscontainer(const exvector & v) const
{
return (new ncmul(v))->setflag(status_flags::dynallocated);
}
-ex ncmul::thisexprseq(exvector * vp) const
+ex ncmul::thiscontainer(exvector * vp) const
{
return (new ncmul(vp))->setflag(status_flags::dynallocated);
}
* @see ex::diff */
ex ncmul::derivative(const symbol & s) const
{
- unsigned num = seq.size();
+ size_t num = seq.size();
exvector addseq;
addseq.reserve(num);
// D(a*b*c) = D(a)*b*c + a*D(b)*c + a*b*D(c)
exvector ncmulseq = seq;
- for (unsigned i=0; i<num; ++i) {
+ for (size_t i=0; i<num; ++i) {
ex e = seq[i].diff(s);
e.swap(ncmulseq[i]);
addseq.push_back((new ncmul(ncmulseq))->setflag(status_flags::dynallocated));
return inherited::compare_same_type(other);
}
-unsigned ncmul::return_type(void) const
+unsigned ncmul::return_type() const
{
if (seq.empty())
return return_types::commutative;
return all_commutative ? return_types::commutative : return_types::noncommutative;
}
-unsigned ncmul::return_type_tinfo(void) const
+unsigned ncmul::return_type_tinfo() const
{
if (seq.empty())
return tinfo_key;
return s;
}
-const exvector & ncmul::get_factors(void) const
+const exvector & ncmul::get_factors() const
{
return seq;
}
// friend functions
//////////
-ex nonsimplified_ncmul(const exvector & v)
+ex reeval_ncmul(const exvector & v)
{
return (new ncmul(v))->setflag(status_flags::dynallocated);
}
-ex simplified_ncmul(const exvector & v)
+ex hold_ncmul(const exvector & v)
{
if (v.empty())
return _ex1;