#include "archive.h"
#include "registrar.h"
#include "ex.h"
+#include "lst.h"
#include "config.h"
#include "tostring.h"
found:
// Recursively unarchive all nodes, starting at the root node
- return nodes[i->root].unarchive(sym_lst);
+ lst sym_lst_copy = sym_lst;
+ return nodes[i->root].unarchive(sym_lst_copy);
}
ex archive::unarchive_ex(const lst &sym_lst, unsigned index) const
throw (std::range_error("index of archived expression out of range"));
// Recursively unarchive all nodes, starting at the root node
- return nodes[exprs[index].root].unarchive(sym_lst);
+ lst sym_lst_copy = sym_lst;
+ return nodes[exprs[index].root].unarchive(sym_lst_copy);
}
ex archive::unarchive_ex(const lst &sym_lst, std::string &name, unsigned index) const
name = unatomize(exprs[index].name);
// Recursively unarchive all nodes, starting at the root node
- return nodes[exprs[index].root].unarchive(sym_lst);
+ lst sym_lst_copy = sym_lst;
+ return nodes[exprs[index].root].unarchive(sym_lst_copy);
}
unsigned archive::num_expressions(void) const
return false;
}
-bool archive_node::find_ex(const std::string &name, ex &ret, const lst &sym_lst, unsigned index) const
+bool archive_node::find_ex(const std::string &name, ex &ret, lst &sym_lst, unsigned index) const
{
archive_atom name_atom = a.atomize(name);
std::vector<property>::const_iterator i = props.begin(), iend = props.end();
/** Convert archive node to GiNaC expression. */
-ex archive_node::unarchive(const lst &sym_lst) const
+ex archive_node::unarchive(lst &sym_lst) const
{
// Already unarchived? Then return cached unarchived expression.
if (has_expression)
/** Retrieve property of type "ex" from node.
* @return "true" if property was found, "false" otherwise */
- bool find_ex(const std::string &name, ex &ret, const lst &sym_lst, unsigned index = 0) const;
+ bool find_ex(const std::string &name, ex &ret, lst &sym_lst, unsigned index = 0) const;
/** Retrieve property of type "ex" from node, returning the node of
* the sub-expression. */
/** Return vector of properties stored in node. */
void get_properties(propinfovector &v) const;
- ex unarchive(const lst &sym_lst) const;
+ ex unarchive(lst &sym_lst) const;
bool has_same_ex_as(const archive_node &other) const;
void forget(void);
//////////
/** Construct object from archive_node. */
-basic::basic(const archive_node &n, const lst &sym_lst) : flags(0), refcount(0)
+basic::basic(const archive_node &n, lst &sym_lst) : flags(0), refcount(0)
{
// Reconstruct tinfo_key from class name
std::string class_name;
* debugger because it might not know what cout is. This method can be
* invoked with no argument and it will simply print to stdout.
*
- * @see basic::print */
+ * @see basic::print
+ * @see basic::dbgprinttree */
void basic::dbgprint(void) const
{
this->print(std::cerr);
/** Little wrapper around printtree to be called within a debugger.
*
- * @see basic::dbgprint
- * @see basic::printtree */
+ * @see basic::dbgprint */
void basic::dbgprinttree(void) const
{
this->print(print_tree(std::cerr));
// archiving
//////////
-clifford::clifford(const archive_node &n, const lst &sym_lst) : inherited(n, sym_lst)
+clifford::clifford(const archive_node &n, lst &sym_lst) : inherited(n, sym_lst)
{
unsigned rl;
n.find_unsigned("label", rl);
// archiving
//////////
-color::color(const archive_node &n, const lst &sym_lst) : inherited(n, sym_lst)
+color::color(const archive_node &n, lst &sym_lst) : inherited(n, sym_lst)
{
unsigned rl;
n.find_unsigned("label", rl);
// archiving
//////////
-constant::constant(const archive_node &n, const lst &sym_lst) : inherited(n, sym_lst) {}
+constant::constant(const archive_node &n, lst &sym_lst) : inherited(n, sym_lst) {}
-ex constant::unarchive(const archive_node &n, const lst &sym_lst)
+ex constant::unarchive(const archive_node &n, lst &sym_lst)
{
// Find constant by name (!! this is bad: 'twould be better if there
// was a list of all global constants that we could search)
//////////
/** Construct object from archive_node. */
-${CONTAINER}::${CONTAINER}(const archive_node &n, const lst &sym_lst) : inherited(n, sym_lst)
+${CONTAINER}::${CONTAINER}(const archive_node &n, lst &sym_lst) : inherited(n, sym_lst)
{
for (unsigned int i=0; true; i++) {
ex e;
}
/** Unarchive the object. */
-ex ${CONTAINER}::unarchive(const archive_node &n, const lst &sym_lst)
+ex ${CONTAINER}::unarchive(const archive_node &n, lst &sym_lst)
{
return (new ${CONTAINER}(n, sym_lst))->setflag(status_flags::dynallocated);
}
bp->print(c, level);
}
-/** Print expression to stream in a tree-like format suitable for debugging. */
-void ex::printtree(std::ostream & os) const
-{
- GINAC_ASSERT(bp!=0);
- bp->print(print_tree(os));
-}
-
/** Little wrapper arount print to be called within a debugger. */
void ex::dbgprint(void) const
{
}
void print(const print_context & c, unsigned level = 0) const;
- void printtree(std::ostream & os) const;
void dbgprint(void) const;
void dbgprinttree(void) const;
bool info(unsigned inf) const { return bp->info(inf); }
// archiving
//////////
-expairseq::expairseq(const archive_node &n, const lst &sym_lst) : inherited(n, sym_lst)
+expairseq::expairseq(const archive_node &n, lst &sym_lst) : inherited(n, sym_lst)
#if EXPAIRSEQ_USE_HASHTAB
, hashtabsize(0)
#endif
// archiving
//////////
-fderivative::fderivative(const archive_node &n, const lst &sym_lst) : inherited(n, sym_lst)
+fderivative::fderivative(const archive_node &n, lst &sym_lst) : inherited(n, sym_lst)
{
unsigned i = 0;
while (true) {
};
};
-/** Flags to control the behavior of print(). */
-class print_options {
-public:
- enum {
- print_index_dimensions = 0x0001 ///< print the dimensions of indices
- };
-};
-
} // namespace GiNaC
#endif // ndef __GINAC_FLAGS_H__
//////////
/** Construct object from archive_node. */
-function::function(const archive_node &n, const lst &sym_lst) : inherited(n, sym_lst)
+function::function(const archive_node &n, lst &sym_lst) : inherited(n, sym_lst)
{
// Find serial number by function name
std::string s;
}
/** Unarchive the object. */
-ex function::unarchive(const archive_node &n, const lst &sym_lst)
+ex function::unarchive(const archive_node &n, lst &sym_lst)
{
return (new function(n, sym_lst))->setflag(status_flags::dynallocated);
}
// archiving
//////////
-idx::idx(const archive_node &n, const lst &sym_lst) : inherited(n, sym_lst)
+idx::idx(const archive_node &n, lst &sym_lst) : inherited(n, sym_lst)
{
n.find_ex("value", value, sym_lst);
n.find_ex("dim", dim, sym_lst);
}
-varidx::varidx(const archive_node &n, const lst &sym_lst) : inherited(n, sym_lst)
+varidx::varidx(const archive_node &n, lst &sym_lst) : inherited(n, sym_lst)
{
n.find_bool("covariant", covariant);
}
-spinidx::spinidx(const archive_node &n, const lst &sym_lst) : inherited(n, sym_lst)
+spinidx::spinidx(const archive_node &n, lst &sym_lst) : inherited(n, sym_lst)
{
n.find_bool("dotted", dotted);
}
// archiving
//////////
-indexed::indexed(const archive_node &n, const lst &sym_lst) : inherited(n, sym_lst)
+indexed::indexed(const archive_node &n, lst &sym_lst) : inherited(n, sym_lst)
{
if (!n.find_ex("symmetry", symtree, sym_lst)) {
// GiNaC versions <= 0.9.0 had an unsigned "symmetry" property
// archiving
//////////
-matrix::matrix(const archive_node &n, const lst &sym_lst) : inherited(n, sym_lst)
+matrix::matrix(const archive_node &n, lst &sym_lst) : inherited(n, sym_lst)
{
if (!(n.find_unsigned("row", row)) || !(n.find_unsigned("col", col)))
throw (std::runtime_error("unknown matrix dimensions in archive"));
// archiving
//////////
-numeric::numeric(const archive_node &n, const lst &sym_lst) : inherited(n, sym_lst)
+numeric::numeric(const archive_node &n, lst &sym_lst) : inherited(n, sym_lst)
{
cln::cl_N ctorval = 0;
return i;
}
+// Stream format gets copied or destroyed
static void my_ios_callback(std::ios_base::event ev, std::ios_base & s, int i)
{
print_context *p = static_cast<print_context *>(s.pword(i));
if (ev == std::ios_base::erase_event) {
delete p;
s.pword(i) = 0;
- } else if (ev == std::ios_base::copyfmt_event && p != 0) {
+ } else if (ev == std::ios_base::copyfmt_event && p != 0)
s.pword(i) = p->duplicate();
- }
}
enum {
callback_registered = 1
};
-static print_context *get_print_context(std::ios_base & s)
+// Get print_context associated with stream, may return 0 if no context has
+// been associated yet
+static inline print_context *get_print_context(std::ios_base & s)
{
return static_cast<print_context *>(s.pword(my_ios_index()));
}
+// Set print_context associated with stream, retain options
static void set_print_context(std::ios_base & s, const print_context & c)
{
int i = my_ios_index();
s.register_callback(my_ios_callback, i);
s.iword(i) = flags | callback_registered;
}
- delete static_cast<print_context *>(s.pword(i));
- s.pword(i) = c.duplicate();
+ print_context *p = static_cast<print_context *>(s.pword(i));
+ unsigned options = p ? p->options : c.options;
+ delete p;
+ p = c.duplicate();
+ p->options = options;
+ s.pword(i) = p;
+}
+
+// Get options for print_context associated with stream
+static inline unsigned get_print_options(std::ios_base & s)
+{
+ print_context *p = get_print_context(s);
+ return p ? p->options : 0;
+}
+
+// Set options for print_context associated with stream
+static void set_print_options(std::ostream & s, unsigned options)
+{
+ print_context *p = get_print_context(s);
+ if (p == 0)
+ set_print_context(s, print_context(s, options));
+ else
+ p->options = options;
}
std::ostream & operator<<(std::ostream & os, const ex & e)
{
- if (get_print_context(os) == 0)
+ print_context *p = get_print_context(os);
+ if (p == 0)
e.print(print_context(os));
else
- e.print(*get_print_context(os));
+ e.print(*p);
return os;
}
std::ostream & dflt(std::ostream & os)
{
set_print_context(os, print_context(os));
+ set_print_options(os, 0);
return os;
}
return os;
}
+std::ostream & csrc(std::ostream & os)
+{
+ set_print_context(os, print_csrc_double(os));
+ return os;
+}
+
std::ostream & csrc_float(std::ostream & os)
{
set_print_context(os, print_csrc_float(os));
return os;
}
-std::ostream & csrc(std::ostream & os)
+std::ostream & index_dimensions(std::ostream & os)
{
- set_print_context(os, print_csrc_double(os));
+ set_print_options(os, get_print_options(os) | print_options::print_index_dimensions);
+ return os;
+}
+
+std::ostream & no_index_dimensions(std::ostream & os)
+{
+ set_print_options(os, get_print_options(os) & ~print_options::print_index_dimensions);
return os;
}
std::ostream & python(std::ostream & os);
std::ostream & python_repr(std::ostream & os);
std::ostream & tree(std::ostream & os);
+std::ostream & csrc(std::ostream & os); // same as csrc_double
std::ostream & csrc_float(std::ostream & os);
std::ostream & csrc_double(std::ostream & os);
std::ostream & csrc_cl_N(std::ostream & os);
-std::ostream & csrc(std::ostream & os); // same as csrc_double
+
+std::ostream & index_dimensions(std::ostream & os);
+std::ostream & no_index_dimensions(std::ostream & os);
} // namespace GiNaC
// archiving
//////////
-power::power(const archive_node &n, const lst &sym_lst) : inherited(n, sym_lst)
+power::power(const archive_node &n, lst &sym_lst) : inherited(n, sym_lst)
{
n.find_ex("basis", basis, sym_lst);
n.find_ex("exponent", exponent, sym_lst);
namespace GiNaC {
+
+/*
+ * The following classes remain publicly visible for compatibility
+ * reasons only. New code should use the iostream manipulators defined
+ * in operators.h instead.
+ */
+
+
+/** Flags to control the behavior of a print_context. */
+class print_options {
+public:
+ enum {
+ print_index_dimensions = 0x0001 ///< print the dimensions of indices
+ };
+};
+
+
/** Context for default (ginsh-parsable) output. */
class print_context
{
* Archiving
*/
-pseries::pseries(const archive_node &n, const lst &sym_lst) : inherited(n, sym_lst)
+pseries::pseries(const archive_node &n, lst &sym_lst) : inherited(n, sym_lst)
{
for (unsigned int i=0; true; ++i) {
ex rest;
/** Unarchiving function (static member function of every GiNaC class). */
-typedef ex (*unarch_func)(const archive_node &n, const lst &sym_lst);
+typedef ex (*unarch_func)(const archive_node &n, lst &sym_lst);
/** Head of list of all registered_class_info structures. */
typedef supername inherited; \
static registered_class_info reg_info; \
virtual const char *class_name(void) const; \
- classname(const archive_node &n, const lst &sym_lst); \
+ classname(const archive_node &n, lst &sym_lst); \
virtual void archive(archive_node &n) const; \
- static ex unarchive(const archive_node &n, const lst &sym_lst);
+ static ex unarchive(const archive_node &n, lst &sym_lst);
/** Macro for inclusion in the declaration of each registered class.
* It declares some functions that are common to all classes derived
// archiving
//////////
-relational::relational(const archive_node &n, const lst &sym_lst) : inherited(n, sym_lst)
+relational::relational(const archive_node &n, lst &sym_lst) : inherited(n, sym_lst)
{
unsigned int opi;
if (!(n.find_unsigned("op", opi)))
//////////
/** Construct object from archive_node. */
-symbol::symbol(const archive_node &n, const lst &sym_lst) : inherited(n, sym_lst)
+symbol::symbol(const archive_node &n, lst &sym_lst) : inherited(n, sym_lst)
{
serial = next_serial++;
if (!(n.find_string("name", name)))
}
/** Unarchive the object. */
-ex symbol::unarchive(const archive_node &n, const lst &sym_lst)
+ex symbol::unarchive(const archive_node &n, lst &sym_lst)
{
ex s = (new symbol(n, sym_lst))->setflag(status_flags::dynallocated);
-
+
// If symbol is in sym_lst, return the existing symbol
for (size_t i=0; i<sym_lst.nops(); i++) {
if (is_a<symbol>(sym_lst.op(i)) && (ex_to<symbol>(sym_lst.op(i)).name == ex_to<symbol>(s).name))
return sym_lst.op(i);
}
+
+ // Otherwise add new symbol to list and return it
+ sym_lst.append(s);
return s;
}
//////////
/** Construct object from archive_node. */
-symmetry::symmetry(const archive_node &n, const lst &sym_lst) : inherited(n, sym_lst)
+symmetry::symmetry(const archive_node &n, lst &sym_lst) : inherited(n, sym_lst)
{
unsigned t;
if (!(n.find_unsigned("type", t)))
DEFAULT_UNARCHIVE(minkmetric)
DEFAULT_UNARCHIVE(tensepsilon)
-minkmetric::minkmetric(const archive_node &n, const lst &sym_lst) : inherited(n, sym_lst)
+minkmetric::minkmetric(const archive_node &n, lst &sym_lst) : inherited(n, sym_lst)
{
n.find_bool("pos_sig", pos_sig);
}
n.add_bool("pos_sig", pos_sig);
}
-tensepsilon::tensepsilon(const archive_node &n, const lst &sym_lst) : inherited(n, sym_lst)
+tensepsilon::tensepsilon(const archive_node &n, lst &sym_lst) : inherited(n, sym_lst)
{
n.find_bool("minkowski", minkowski);
n.find_bool("pos_sig", pos_sig);
DEFAULT_DESTROY(classname)
#define DEFAULT_UNARCHIVE(classname) \
-ex classname::unarchive(const archive_node &n, const lst &sym_lst) \
+ex classname::unarchive(const archive_node &n, lst &sym_lst) \
{ \
return (new classname(n, sym_lst))->setflag(status_flags::dynallocated); \
}
#define DEFAULT_ARCHIVING(classname) \
-classname::classname(const archive_node &n, const lst &sym_lst) : inherited(n, sym_lst) {} \
+classname::classname(const archive_node &n, lst &sym_lst) : inherited(n, sym_lst) {} \
DEFAULT_UNARCHIVE(classname) \
void classname::archive(archive_node &n) const \
{ \
// archiving
//////////
-wildcard::wildcard(const archive_node &n, const lst &sym_lst) : inherited(n, sym_lst)
+wildcard::wildcard(const archive_node &n, lst &sym_lst) : inherited(n, sym_lst)
{
n.find_unsigned("label", label);
}