X-Git-Url: https://www.ginac.de/ginac.git//ginac.git?p=ginac.git;a=blobdiff_plain;f=ginac%2Fcontainer.pl;h=39c75385197ddbe0a93b684c039a90212a943e88;hp=bed117f6acc37476190f6ee6517eacdf82757067;hb=f3c347622199012c7ffabc1ce26bb544e32df52b;hpb=d7eee2dd8de4149ff805fd69641316418450275b diff --git a/ginac/container.pl b/ginac/container.pl index bed117f6..39c75385 100755 --- a/ginac/container.pl +++ b/ginac/container.pl @@ -23,6 +23,7 @@ if ($type eq 'exprseq') { $STLHEADER="vector"; $reserve=1; $prepend=0; + $sort=0; $let_op=0; $open_bracket='('; $close_bracket=')'; @@ -34,6 +35,7 @@ if ($type eq 'exprseq') { $STLHEADER="list"; $reserve=0; $prepend=1; + $sort=1; $let_op=1; $open_bracket='{'; $close_bracket='}'; @@ -64,6 +66,7 @@ ${CONTAINER} & ${CONTAINER}::prepend(const ex & b) seq.push_front(b); return *this; } + ${CONTAINER} & ${CONTAINER}::remove_first(void) { ensure_if_modifiable(); @@ -76,6 +79,32 @@ END_OF_PREPEND_IMPLEMENTATION $PREPEND_IMPLEMENTATION=""; } +if ($sort) { + $SORT_INTERFACE=<(). - * This is unsafe: you need to check the type first. */ -inline const ${CONTAINER} &ex_to_${CONTAINER}(const ex &e) -{ - return static_cast(*e.bp); -} - /** Specialization of is_exactly_a<${CONTAINER}>(obj) for ${CONTAINER} objects. */ template<> inline bool is_exactly_a<${CONTAINER}>(const basic & obj) { return obj.tinfo()==TINFO_${CONTAINER}; } -inline ${CONTAINER} &ex_to_nonconst_${CONTAINER}(const ex &e) -{ - return static_cast<${CONTAINER} &>(*e.bp); -} - } // namespace GiNaC #endif // ndef __GINAC_${CONTAINER_UC}_H__ @@ -281,7 +299,7 @@ $implementation=<(s)); } else { @@ -356,7 +369,6 @@ ${CONTAINER}::${CONTAINER}(${STLT} const & s, bool discardable) : basic(TINFO_$ ${CONTAINER}::${CONTAINER}(${STLT} * vp) : basic(TINFO_${CONTAINER}) { - debugmsg("${CONTAINER} ctor from ${STLT} *",LOGLEVEL_CONSTRUCT); GINAC_ASSERT(vp!=0); seq.swap(*vp); delete vp; @@ -371,7 +383,6 @@ ${constructors_implementation} /** Construct object from archive_node. */ ${CONTAINER}::${CONTAINER}(const archive_node &n, const lst &sym_lst) : inherited(n, sym_lst) { - debugmsg("${CONTAINER} ctor from archive_node", LOGLEVEL_CONSTRUCT); for (unsigned int i=0; true; i++) { ex e; if (n.find_ex("seq", e, sym_lst, i)) @@ -391,23 +402,21 @@ ex ${CONTAINER}::unarchive(const archive_node &n, const lst &sym_lst) void ${CONTAINER}::archive(archive_node &n) const { inherited::archive(n); - ${STLT}::const_iterator i = seq.begin(), iend = seq.end(); - while (i != iend) { + ${STLT}::const_iterator i = seq.begin(), end = seq.end(); + while (i != end) { n.add_ex("seq", *i); - i++; + ++i; } } ////////// -// functions overriding virtual functions from bases classes +// functions overriding virtual functions from base classes ////////// // public void ${CONTAINER}::print(const print_context & c, unsigned level) const { - debugmsg("${CONTAINER} print", LOGLEVEL_PRINT); - if (is_a(c)) { c.s << std::string(level, ' ') << class_name() @@ -415,10 +424,17 @@ void ${CONTAINER}::print(const print_context & c, unsigned level) const << ", nops=" << nops() << std::endl; unsigned delta_indent = static_cast(c).delta_indent; - for (${STLT}::const_iterator cit=seq.begin(); cit!=seq.end(); ++cit) - cit->print(c, level + delta_indent); + ${STLT}::const_iterator i = seq.begin(), end = seq.end(); + while (i != end) { + i->print(c, level + delta_indent); + ++i; + } c.s << std::string(level + delta_indent,' ') << "=====" << std::endl; - + } else if (is_a(c)) { + printseq(c, '[', ',', ']', precedence(), precedence()+1); + } else if (is_a(c)) { + c.s << class_name (); + printseq(c, '(', ',', ')', precedence(), precedence()+1); } else { // always print brackets around seq, ignore upper_precedence printseq(c, '${open_bracket}', ',', '${close_bracket}', precedence(), precedence()+1); @@ -436,10 +452,14 @@ ${LET_OP_IMPLEMENTATION} ex ${CONTAINER}::map(map_function & f) const { + // This implementation is here because basic::map() uses let_op() + // which is not defined for all containers ${STLT} s; RESERVE(s,seq.size()); - for (${STLT}::const_iterator it=seq.begin(); it!=seq.end(); ++it) { - s.push_back(f(*it)); + ${STLT}::const_iterator i = seq.begin(), end = seq.end(); + while (i != end) { + s.push_back(f(*i)); + ++i; } return this${CONTAINER}(s); @@ -457,7 +477,7 @@ ex ${CONTAINER}::subs(const lst & ls, const lst & lr, bool no_pattern) const { ${STLT} *vp = subschildren(ls, lr, no_pattern); if (vp) - return this${CONTAINER}(vp).bp->basic::subs(ls, lr, no_pattern); + return ex_to(this${CONTAINER}(vp)).basic::subs(ls, lr, no_pattern); else return basic::subs(ls, lr, no_pattern); } @@ -529,6 +549,8 @@ ${CONTAINER} & ${CONTAINER}::remove_last(void) ${PREPEND_IMPLEMENTATION} +${SORT_IMPLEMENTATION} + // protected void ${CONTAINER}::printseq(const print_context & c, char openbracket, char delim, @@ -538,13 +560,13 @@ void ${CONTAINER}::printseq(const print_context & c, char openbracket, char deli if (this_precedence <= upper_precedence) c.s << openbracket; - if (seq.size() != 0) { + if (!seq.empty()) { ${STLT}::const_iterator it = seq.begin(), itend = seq.end(); --itend; while (it != itend) { it->print(c, this_precedence); c.s << delim; - it++; + ++it; } it->print(c, this_precedence); } @@ -577,11 +599,11 @@ bool ${CONTAINER}::is_canonical() const { if (seq.size()<=1) { return 1; } - ${STLT}::const_iterator it=seq.begin(); + ${STLT}::const_iterator it = seq.begin(), itend = seq.end(); ${STLT}::const_iterator it_last=it; - for (++it; it!=seq.end(); it_last=it, ++it) { - if ((*it_last).compare(*it)>0) { - if ((*it_last).compare(*it)>0) { + for (++it; it!=itend; it_last=it, ++it) { + if (it_last->compare(*it)>0) { + if (it_last->compare(*it)>0) { std::cout << *it_last << ">" << *it << "\\n"; return 0; } @@ -603,8 +625,10 @@ ${STLT} ${CONTAINER}::evalchildren(int level) const throw(std::runtime_error("max recursion level reached")); } --level; - for (${STLT}::const_iterator it=seq.begin(); it!=seq.end(); ++it) { - s.push_back((*it).eval(level)); + ${STLT}::const_iterator it = seq.begin(), itend = seq.end(); + while (it != itend) { + s.push_back(it->eval(level)); + ++it; } return s; } @@ -615,28 +639,29 @@ ${STLT} * ${CONTAINER}::subschildren(const lst & ls, const lst & lr, bool no_pat // returns a pointer to a newly created epvector otherwise // (which has to be deleted somewhere else) - ${STLT}::const_iterator last=seq.end(); - ${STLT}::const_iterator cit=seq.begin(); - while (cit!=last) { - const ex & subsed_ex=(*cit).subs(ls,lr,no_pattern); - if (!are_ex_trivially_equal(*cit,subsed_ex)) { + ${STLT}::const_iterator cit = seq.begin(), end = seq.end(); + while (cit != end) { + const ex & subsed_ex = cit->subs(ls, lr, no_pattern); + if (!are_ex_trivially_equal(*cit, subsed_ex)) { // something changed, copy seq, subs and return it ${STLT} *s=new ${STLT}; - RESERVE(*s,seq.size()); + RESERVE(*s, seq.size()); // copy parts of seq which are known not to have changed - ${STLT}::const_iterator cit2=seq.begin(); - while (cit2!=cit) { + ${STLT}::const_iterator cit2 = seq.begin(); + while (cit2 != cit) { s->push_back(*cit2); ++cit2; } + // copy first changed element s->push_back(subsed_ex); ++cit2; + // copy rest - while (cit2!=last) { - s->push_back((*cit2).subs(ls,lr,no_pattern)); + while (cit2 != end) { + s->push_back(cit2->subs(ls, lr, no_pattern)); ++cit2; } return s;