* Implementation of GiNaC's clifford algebra (Dirac gamma) objects. */
/*
- * GiNaC Copyright (C) 1999-2007 Johannes Gutenberg University Mainz, Germany
+ * GiNaC Copyright (C) 1999-2008 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
if (is_dirac_slash(seq[0])) {
seq[0].print(c, precedence());
c.s << "\\";
- } else
- this->print_dispatch<inherited>(c, level);
+ } else { // We do not print representation label if it is 0
+ if (representation_label == 0) {
+ this->print_dispatch<inherited>(c, level);
+ } else { // otherwise we put it before indices in square brackets; the code is borrowed from indexed.cpp
+ if (precedence() <= level) {
+ c.s << '(';
+ }
+ seq[0].print(c, precedence());
+ c.s << '[' << int(representation_label) << ']';
+ printindices(c, level);
+ if (precedence() <= level) {
+ c.s << ')';
+ }
+ }
+ }
}
void clifford::do_print_latex(const print_latex & c, unsigned level) const
return clifford(ONE, rl);
}
+static unsigned get_dim_uint(const ex& e)
+{
+ if (!is_a<idx>(e))
+ throw std::invalid_argument("get_dim_uint: argument is not an index");
+ ex dim = ex_to<idx>(e).get_dim();
+ if (!dim.info(info_flags::posint))
+ throw std::invalid_argument("get_dim_uint: dimension of index should be a positive integer");
+ unsigned d = ex_to<numeric>(dim).to_int();
+ return d;
+}
+
ex clifford_unit(const ex & mu, const ex & metr, unsigned char rl)
{
- static ex unit = (new cliffordunit)->setflag(status_flags::dynallocated);
+ //static ex unit = (new cliffordunit)->setflag(status_flags::dynallocated);
+ ex unit = (new cliffordunit)->setflag(status_flags::dynallocated);
if (!is_a<idx>(mu))
throw(std::invalid_argument("clifford_unit(): index of Clifford unit must be of type idx or varidx"));
unsigned n = M.rows();
bool symmetric = true;
- static idx xi((new symbol)->setflag(status_flags::dynallocated), n),
+ //static idx xi((new symbol)->setflag(status_flags::dynallocated), n),
+ // chi((new symbol)->setflag(status_flags::dynallocated), n);
+ idx xi((new symbol)->setflag(status_flags::dynallocated), n),
chi((new symbol)->setflag(status_flags::dynallocated), n);
- if ((n == M.cols()) && (n == ex_to<idx>(mu).get_dim())) {
+ if ((n == M.cols()) && (n == get_dim_uint(mu))) {
for (unsigned i = 0; i < n; i++) {
for (unsigned j = i+1; j < n; j++) {
- if (M(i, j) != M(j, i)) {
+ if (!M(i, j).is_equal(M(j, i))) {
symmetric = false;
}
}
throw(std::invalid_argument("clifford_unit(): metric for Clifford unit must be a square matrix with the same dimensions as index"));
}
} else if (indices.size() == 0) { // a tensor or other expression without indices
- static varidx xi((new symbol)->setflag(status_flags::dynallocated), ex_to<idx>(mu).get_dim()),
+ //static varidx xi((new symbol)->setflag(status_flags::dynallocated), ex_to<idx>(mu).get_dim()),
+ // chi((new symbol)->setflag(status_flags::dynallocated), ex_to<idx>(mu).get_dim());
+ varidx xi((new symbol)->setflag(status_flags::dynallocated), ex_to<idx>(mu).get_dim()),
chi((new symbol)->setflag(status_flags::dynallocated), ex_to<idx>(mu).get_dim());
return clifford(unit, mu, indexed(metr, xi, chi), rl);
} else
ex mu = e.op(1);
ex mu_toggle
= is_a<varidx>(mu) ? ex_to<varidx>(mu).toggle_variance() : mu;
- unsigned dim = (ex_to<numeric>(ex_to<idx>(mu).get_dim())).to_int();
+ unsigned dim = get_dim_uint(mu);
if (is_a<matrix>(v)) {
if (ex_to<matrix>(v).cols() > ex_to<matrix>(v).rows()) {
if (min == 1) {
if (dim == max)
return indexed(v, mu_toggle) * e;
- else
+ else if (max - dim == 1) {
+ if (ex_to<matrix>(v).cols() > ex_to<matrix>(v).rows())
+ return v.op(0) * dirac_ONE(ex_to<clifford>(e).get_representation_label()) + indexed(sub_matrix(ex_to<matrix>(v), 0, 1, 1, dim), mu_toggle) * e;
+ else
+ return v.op(0) * dirac_ONE(ex_to<clifford>(e).get_representation_label()) + indexed(sub_matrix(ex_to<matrix>(v), 1, dim, 0, 1), mu_toggle) * e;
+ } else
throw(std::invalid_argument("lst_to_clifford(): dimensions of vector and clifford unit mismatch"));
} else
throw(std::invalid_argument("lst_to_clifford(): first argument should be a vector (nx1 or 1xn matrix)"));
} else if (v.info(info_flags::list)) {
if (dim == ex_to<lst>(v).nops())
return indexed(matrix(dim, 1, ex_to<lst>(v)), mu_toggle) * e;
+ else if (ex_to<lst>(v).nops() - dim == 1)
+ return v.op(0) * dirac_ONE(ex_to<clifford>(e).get_representation_label()) + indexed(sub_matrix(matrix(dim+1, 1, ex_to<lst>(v)), 1, dim, 0, 1), mu_toggle) * e;
else
throw(std::invalid_argument("lst_to_clifford(): list length and dimension of clifford unit mismatch"));
} else
or (not is_a<numeric>(pow(c.subs(mu == i, subs_options::no_pattern), 2))))
algebraic = false;
lst V;
+ ex v0 = remove_dirac_ONE(canonicalize_clifford(e+clifford_prime(e)).normal())/2;
+ if (not v0.is_zero())
+ V.append(v0);
+ ex e1 = canonicalize_clifford(e - v0 * dirac_ONE(ex_to<clifford>(c).get_representation_label()));
if (algebraic) {
for (unsigned int i = 0; i < D; i++)
V.append(remove_dirac_ONE(
- simplify_indexed(canonicalize_clifford(e * c.subs(mu == i, subs_options::no_pattern) + c.subs(mu == i, subs_options::no_pattern) * e))
+ simplify_indexed(canonicalize_clifford(e1 * c.subs(mu == i, subs_options::no_pattern) + c.subs(mu == i, subs_options::no_pattern) * e1))
/ (2*pow(c.subs(mu == i, subs_options::no_pattern), 2))));
} else {
- ex e1 = canonicalize_clifford(e);
try {
for (unsigned int i = 0; i < D; i++)
V.append(get_clifford_comp(e1, c.subs(c.op(1) == i, subs_options::no_pattern)));
} catch (std::exception &p) {
/* Try to expand dummy summations to simplify the expression*/
- e1 = canonicalize_clifford(expand_dummy_sum(e1, true));
+ e1 = canonicalize_clifford(expand_dummy_sum(e, true));
+ V.remove_all();
+ v0 = remove_dirac_ONE(canonicalize_clifford(e1+clifford_prime(e1)).normal())/2;
+ if (not v0.is_zero()) {
+ V.append(v0);
+ e1 = canonicalize_clifford(e1 - v0 * dirac_ONE(ex_to<clifford>(c).get_representation_label()));
+ }
for (unsigned int i = 0; i < D; i++)
V.append(get_clifford_comp(e1, c.subs(c.op(1) == i, subs_options::no_pattern)));
}
ex clifford_moebius_map(const ex & M, const ex & v, const ex & G, unsigned char rl)
{
- if (is_a<matrix>(M))
- return clifford_moebius_map(ex_to<matrix>(M)(0,0), ex_to<matrix>(M)(0,1),
- ex_to<matrix>(M)(1,0), ex_to<matrix>(M)(1,1), v, G, rl);
+ if (is_a<matrix>(M) && (ex_to<matrix>(M).rows() == 2) && (ex_to<matrix>(M).cols() == 2))
+ return clifford_moebius_map(M.op(0), M.op(1), M.op(2), M.op(3), v, G, rl);
else
- throw(std::invalid_argument("clifford_moebius_map(): parameter M should be a matrix"));
+ throw(std::invalid_argument("clifford_moebius_map(): parameter M should be a 2x2 matrix"));
}
} // namespace GiNaC