Hi, I tried this very confuse code, and I am happy if somebody could help-me. I tried to make covariant derivative derivated from a indexed. Use it like: D(indexed(A,mu),nu) But the fatal errors in this code (among millions..): i) simplify_indexed() crashs or doesnt work !! II) get_free_indexes not work, so D^\alpha(A_beta)A^\beta A_\alpha -D^\beta(A_alpha)A^\beta A_\alpha is not zero In the last post , Christian Bauer suggests "override is eval_indexed() (for automatic evaluation) and contract_with()/add_indexed()/scalar_mul_indexed() (for manual evaluation, AKA simplify_indexed())" and showed the way: look color.cpp source. Any suggestions are welcome Marco #include <iostream> #include <ginac/ginac.h> #define N 4 #define N1 8 using namespace std; using namespace GiNaC; const unsigned TINFO_covdiff = 0x42420001U; class covdiff : public indexed { GINAC_DECLARE_REGISTERED_CLASS(covdiff, indexed) public: covdiff(const ex & b,const ex & i1); covdiff(const ex & b, const ex & i1, const ex & i2); covdiff(const ex & b, const ex & i1, const ex & i2,const ex & i3); covdiff(const ex & b, const ex & i1, const ex & i2,const ex & i3, const ex & i4); covdiff(const ex & b, const lst & iv); size_t nops() const; ex op(size_t i) const; ex & let_op(size_t i); ex subs(const exmap & m, unsigned options) const; protected: void do_print(const print_context & c, unsigned level) const; ex symtree, arg,index; lst seq; }; GINAC_IMPLEMENT_REGISTERED_CLASS_OPT(covdiff, indexed, print_func<print_context>(&covdiff::do_print)) covdiff::covdiff(const ex & b, const ex & i1) : inherited(b, i1),arg(b),index(i1), symtree(not_symmetric()) { tinfo_key = TINFO_covdiff; } covdiff::covdiff(const ex & b, const ex & i1, const ex & i2) : inherited(b, i1, i2),arg(b), symtree(not_symmetric()) { seq =i1,i2; tinfo_key = TINFO_covdiff; } covdiff::covdiff(const ex & b, const ex & i1, const ex & i2, const ex & i3) : inherited(b, i1, i2, i3),arg(b), symtree(not_symmetric()) { seq=i1,i2,i3; tinfo_key = TINFO_covdiff; } covdiff::covdiff(const ex & b, const ex & i1, const ex & i2, const ex & i3, const ex & i4) : inherited(b, i1, i2, i3, i4),arg(b), symtree(not_symmetric()) {seq = i1,i2,i3,i4; tinfo_key = TINFO_covdiff; } covdiff::covdiff(const ex & b, const lst & iv) : inherited(b),arg(b), symtree(not_symmetric()) { seq=iv; tinfo_key = TINFO_covdiff; } //archiving covdiff::covdiff(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 unsigned symm = 0; n.find_unsigned("symmetry", symm); switch (symm) { case 1: symtree = sy_symm(); break; case 2: symtree = sy_anti(); break; default: symtree = not_symmetric(); break; } const_cast<symmetry &>(ex_to<symmetry>(symtree)).validate(seq.nops() - 1); } } void covdiff::archive(archive_node &n) const { inherited::archive(n); n.add_ex("symmetry", symtree); } ex covdiff::unarchive(const archive_node &n, lst &sym_lst) { return (new covdiff(n, sym_lst))->setflag(status_flags::dynallocated); } //comparation method void covdiff::do_print(const print_context & c, unsigned level) const { if (is_a<print_tree>(c)) covdiff::print(c,level); if (seq.nops() > 1) { for( lst::const_iterator it=seq.begin();it != seq.end();++it) c.s<<"D"<<*it; c.s<<"("<<arg<<")"; } else c.s << "D"<<index <<" ("<<arg<<")"; } int covdiff::compare_same_type(const basic & other) const { GINAC_ASSERT(is_a<covdiff>(other)); return inherited::compare_same_type(other); } ex covdiff::op(size_t i) const{ if(i==0) return arg; if(seq.nops() > 0 && i != 0) return seq[i-1]; if(seq.nops()==0 && i==1) return index; else throw std::range_error("covdiff::let_op(): no such operand"); } size_t covdiff::nops() const { if(seq.nops()>0) return seq.nops()+1; else return 2; } ex & covdiff:: let_op(size_t i) { ensure_if_modifiable(); if(i==0) return arg; if(seq.nops() > 0 && i != 0) return seq[i-1]; if(seq.nops()==0 && i==1) return index; else throw std::range_error("covdiff::let_op(): no such operand"); } ex covdiff::subs(const exmap & m, unsigned options) const { size_t num = nops(); if (num) { // Substitute in subexpressions for (size_t i=0; i<num; i++) { const ex & orig_op = op(i); const ex & subsed_op = orig_op.subs(m, options); if (!are_ex_trivially_equal(orig_op, subsed_op)) { // Something changed, clone the object basic *copy = duplicate(); copy->setflag(status_flags::dynallocated); copy->clearflag(status_flags::hash_calculated | status_flags::expanded); // Substitute the changed operand copy->let_op(i++) = subsed_op; // Substitute the other operands for (; i<num; i++) copy->let_op(i) = op(i).subs(m, options); // Perform substitutions on the new object as a whole return copy->subs_one_level(m, options); } } } // Nothing changed or no subexpressions return subs_one_level(m, options); } ex Derivative_helper(ex e, ex var) { lst iv; if(is_a<covdiff>(e)){ for(size_t i=1; i<e.nops();i++) iv.append(e.op(i)); iv.append(var); return covdiff(e.op(0),iv); }else if(is_a<indexed>(e)){ if(is_a<su3f>(e.op(0)) && e.nops()==4) return 0; else return covdiff(e,var); } else return 0; } struct make_diff : public map_function{ ex var; make_diff(ex var_): var(var_){} ex operator()(const ex & e) { if(is_a<add>(e)) return e.map(*this); else if(is_a<mul>(e)) { ex result =0; for(size_t i=0;i<e.nops();++i) { result +=e.subs(e.op(i)==Derivative_helper(e.op(i),var)); }; return result; }else return Derivative_helper(e,var); } }; ex D(ex e, ex index){ ex result; make_diff D(index); return D(e); } ------------------------------------------------- This mail sent through IMP: http://horde.org/imp/
On Sun, Apr 03, 2005 at 11:47:47PM -0300, mdias@ift.unesp.br wrote:
I tried this very confuse code, and I am happy if somebody could help-me. I tried to make covariant derivative derivated from a indexed. Use it like: D(indexed(A,mu),nu) But the fatal errors in this code (among millions..): i) simplify_indexed() crashs or doesnt work !! II) get_free_indexes not work, so D^\alpha(A_beta)A^\beta A_\alpha -D^\beta(A_alpha)A^\beta A_\alpha is not zero In the last post , Christian Bauer suggests "override is eval_indexed() (for automatic evaluation) and contract_with()/add_indexed()/scalar_mul_indexed() (for manual evaluation, AKA simplify_indexed())" and showed the way: look color.cpp source.
[snip]
protected: void do_print(const print_context & c, unsigned level) const; ex symtree, arg,index; lst seq;
You have re-defined `seq' member. Class indexed already has one (of type std::vector<GiNaC::ex> type). This looks like asking for trouble, unless you *exaclty* know what are you doing. [Huge snip] You haven't implemented codiff::eval_indexed(), codiff::add_indexed(), etc. So simplify_indexed() can't do something useful with your class.
ex covdiff::subs(const exmap & m, unsigned options) const
Do you really need to re-implement subs? -- ---------------------------------------------------------------------- One disk to rule them all, One disk to find them. One disk to bring them all And in the darkness grind them. In the Land of Redmond where the shadows lie. ----------------------------------------------------------------------
Thank you very much for releasing you code. Unfortunately I didn't have time to play with it and also I am taking my general relativity exam in a week, so I won't have time to use it during my preparation. Pity. See you, Ondrej On Sun, Apr 03, 2005 at 11:47:47PM -0300, mdias@ift.unesp.br wrote:
Hi,
I tried this very confuse code, and I am happy if somebody could help-me. I tried to make covariant derivative derivated from a indexed. Use it like: D(indexed(A,mu),nu) But the fatal errors in this code (among millions..): i) simplify_indexed() crashs or doesnt work !! II) get_free_indexes not work, so D^\alpha(A_beta)A^\beta A_\alpha -D^\beta(A_alpha)A^\beta A_\alpha is not zero In the last post , Christian Bauer suggests "override is eval_indexed() (for automatic evaluation) and contract_with()/add_indexed()/scalar_mul_indexed() (for manual evaluation, AKA simplify_indexed())" and showed the way: look color.cpp source.
Any suggestions are welcome
Marco
#include <iostream> #include <ginac/ginac.h>
#define N 4 #define N1 8 using namespace std; using namespace GiNaC;
const unsigned TINFO_covdiff = 0x42420001U;
class covdiff : public indexed { GINAC_DECLARE_REGISTERED_CLASS(covdiff, indexed) public: covdiff(const ex & b,const ex & i1); covdiff(const ex & b, const ex & i1, const ex & i2); covdiff(const ex & b, const ex & i1, const ex & i2,const ex & i3); covdiff(const ex & b, const ex & i1, const ex & i2,const ex & i3, const ex & i4); covdiff(const ex & b, const lst & iv); size_t nops() const; ex op(size_t i) const; ex & let_op(size_t i); ex subs(const exmap & m, unsigned options) const; protected: void do_print(const print_context & c, unsigned level) const; ex symtree, arg,index; lst seq; };
GINAC_IMPLEMENT_REGISTERED_CLASS_OPT(covdiff, indexed, print_func<print_context>(&covdiff::do_print))
covdiff::covdiff(const ex & b, const ex & i1) : inherited(b, i1),arg(b),index(i1), symtree(not_symmetric()) { tinfo_key = TINFO_covdiff; }
covdiff::covdiff(const ex & b, const ex & i1, const ex & i2) : inherited(b, i1, i2),arg(b), symtree(not_symmetric()) { seq =i1,i2; tinfo_key = TINFO_covdiff; }
covdiff::covdiff(const ex & b, const ex & i1, const ex & i2, const ex & i3) : inherited(b, i1, i2, i3),arg(b), symtree(not_symmetric()) { seq=i1,i2,i3; tinfo_key = TINFO_covdiff; }
covdiff::covdiff(const ex & b, const ex & i1, const ex & i2, const ex & i3, const ex & i4) : inherited(b, i1, i2, i3, i4),arg(b), symtree(not_symmetric()) {seq = i1,i2,i3,i4; tinfo_key = TINFO_covdiff; } covdiff::covdiff(const ex & b, const lst & iv) : inherited(b),arg(b), symtree(not_symmetric()) { seq=iv; tinfo_key = TINFO_covdiff;
}
//archiving covdiff::covdiff(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 unsigned symm = 0; n.find_unsigned("symmetry", symm); switch (symm) { case 1: symtree = sy_symm(); break; case 2: symtree = sy_anti(); break; default: symtree = not_symmetric(); break; } const_cast<symmetry &>(ex_to<symmetry>(symtree)).validate(seq.nops() - 1); } }
void covdiff::archive(archive_node &n) const { inherited::archive(n); n.add_ex("symmetry", symtree); }
ex covdiff::unarchive(const archive_node &n, lst &sym_lst) { return (new covdiff(n, sym_lst))->setflag(status_flags::dynallocated); }
//comparation method
void covdiff::do_print(const print_context & c, unsigned level) const { if (is_a<print_tree>(c)) covdiff::print(c,level); if (seq.nops() > 1) { for( lst::const_iterator it=seq.begin();it != seq.end();++it) c.s<<"D"<<*it; c.s<<"("<<arg<<")"; } else c.s << "D"<<index <<" ("<<arg<<")"; }
int covdiff::compare_same_type(const basic & other) const { GINAC_ASSERT(is_a<covdiff>(other)); return inherited::compare_same_type(other); }
ex covdiff::op(size_t i) const{ if(i==0) return arg; if(seq.nops() > 0 && i != 0) return seq[i-1]; if(seq.nops()==0 && i==1) return index; else throw std::range_error("covdiff::let_op(): no such operand");
}
size_t covdiff::nops() const { if(seq.nops()>0) return seq.nops()+1; else return 2; } ex & covdiff:: let_op(size_t i) { ensure_if_modifiable(); if(i==0) return arg; if(seq.nops() > 0 && i != 0) return seq[i-1]; if(seq.nops()==0 && i==1) return index; else throw std::range_error("covdiff::let_op(): no such operand"); }
ex covdiff::subs(const exmap & m, unsigned options) const { size_t num = nops(); if (num) {
// Substitute in subexpressions for (size_t i=0; i<num; i++) { const ex & orig_op = op(i); const ex & subsed_op = orig_op.subs(m, options); if (!are_ex_trivially_equal(orig_op, subsed_op)) {
// Something changed, clone the object basic *copy = duplicate(); copy->setflag(status_flags::dynallocated); copy->clearflag(status_flags::hash_calculated | status_flags::expanded);
// Substitute the changed operand copy->let_op(i++) = subsed_op;
// Substitute the other operands for (; i<num; i++) copy->let_op(i) = op(i).subs(m, options);
// Perform substitutions on the new object as a whole return copy->subs_one_level(m, options); } } }
// Nothing changed or no subexpressions return subs_one_level(m, options); }
ex Derivative_helper(ex e, ex var) { lst iv; if(is_a<covdiff>(e)){ for(size_t i=1; i<e.nops();i++) iv.append(e.op(i)); iv.append(var); return covdiff(e.op(0),iv); }else if(is_a<indexed>(e)){ if(is_a<su3f>(e.op(0)) && e.nops()==4) return 0; else return covdiff(e,var); } else return 0; }
struct make_diff : public map_function{ ex var; make_diff(ex var_): var(var_){} ex operator()(const ex & e) { if(is_a<add>(e)) return e.map(*this); else if(is_a<mul>(e)) { ex result =0; for(size_t i=0;i<e.nops();++i) { result +=e.subs(e.op(i)==Derivative_helper(e.op(i),var)); }; return result; }else return Derivative_helper(e,var); } }; ex D(ex e, ex index){ ex result; make_diff D(index); return D(e); }
------------------------------------------------- This mail sent through IMP: http://horde.org/imp/
_______________________________________________ GiNaC-list mailing list GiNaC-list@ginac.de http://thep.physik.uni-mainz.de/mailman/listinfo/ginac-list
participants (3)
-
mdias@ift.unesp.br
-
Ondrej Certik
-
varg@theor.jinr.ru