Dear All, Apologies for flooding this list, but 1. I found one more bug in clifford_prime(): it did not map itself on the usual (commutative) products "mul". 2. I also changed the behaviour of remove_dirac_ONE() slightly: it is now aware of representation_label for Clifford numbers. API and default behaviour remain the same (but not a binary compatibility). So here is the cumulative patch to my previous post on Tue Mar 29 13:34:13. Best wishes, Vladimir -- Vladimir V. Kisil email: kisilv@maths.leeds.ac.uk -- www: http://maths.leeds.ac.uk/~kisilv/ Index: doc/tutorial/ginac.texi =================================================================== RCS file: /home/cvs/GiNaC/doc/tutorial/ginac.texi,v retrieving revision 1.162 diff -r1.162 ginac.texi 3178,3181c3178,3190 < generators @samp{e~k} satisfying the identities < @samp{e~i e~j + e~j e~i = B(i, j)} for some matrix (@code{metric}) < @math{B(i, j)}, which may be non-symmetric. Such generators are created < by the function ---
generators @tex $e_k$ @end tex satisfying the identities @tex $e_i e_j + e_j e_i = M(i, j) $ @end tex @ifnottex e~i e~j + e~j e~i = M(i, j) @end ifnottex for some matrix (@code{metric}) @math{M(i, j)}, which may be non-symmetric and containing symbolic entries. Such generators are created by the function 3188c3197 < generators, @code{metr} defines the metric @math{B(i, j)} and can be
generators, @code{metr} defines the metric @math{M(i, j)} and can be 3196c3205 < If the matrix @math{B(i, j)} is in fact symmetric you may prefer to create
If the matrix @math{M(i, j)} is in fact symmetric you may prefer to create 3200c3209 < ex e = clifford_unit(mu, indexed(B, sy_symm(), i, j));
ex e = clifford_unit(mu, indexed(M, sy_symm(), i, j));
3211,3214c3220,3222 < varidx nu(symbol("nu"), 3); < matrix M(3, 3) = 1, 0, 0, < 0,-1, 0, < 0, 0, 0; ---
varidx nu(symbol("nu"), 4); realsymbol s("s"); ex M = diag_matrix(lst(1, -1, 0, s));
3218a3227
ex e3 = e.subs(nu == 3);
3223,3224c3232,3238 < will produce three generators of a Clifford algebra with properties < @code{pow(e0, 2) = 1}, @code{pow(e1, 2) = -1} and @code{pow(e2, 2) = 0}. ---
will produce four anti-commuting generators of a Clifford algebra with properties @tex $e_0^2=1 $, $e_1^2=-1$, $e_2^2=0$ and $e_3^2=s$. @end tex @ifnottex @code{pow(e0, 2) = 1}, @code{pow(e1, 2) = -1}, @code{pow(e2, 2) = 0} and @code{pow(e3, 2) = s}. @end ifnottex 3231a3246 ex lst_to_clifford(const ex & v, const ex & e); 3234,3237c3249,3268 < which converts a list or vector @samp{v = (v~0, v~1, ..., v~n)} into < the Clifford number @samp{v~0 e.0 + v~1 e.1 + ... + v~n e.n} with @samp{e.k} < being created by @code{clifford_unit(mu, metr, rl)}. The previous code < may be rewritten with the help of @code{lst_to_clifford()} as follows
which converts a list or vector @tex $v = (v^0, v^1, ..., v^n)$ @end tex @ifnottex @samp{v = (v~0, v~1, ..., v~n)} @end ifnottex into the Clifford number @tex $v^0 e_0 + v^1 e_1 + ... + v^n e_n$ @end tex @ifnottex @samp{v~0 e.0 + v~1 e.1 + ... + v~n e.n} @end ifnottex with @samp{e.k} directly supplied in the second form of the procedure. In the first form the Clifford unit @samp{e.k} is generated by the call of @code{clifford_unit(mu, metr, rl)}. The previous code may be rewritten with the help of @code{lst_to_clifford()} as follows 3242,3248c3273,3279 < varidx nu(symbol("nu"), 3); < matrix M(3, 3) = 1, 0, 0, < 0,-1, 0, < 0, 0, 0; < ex e0 = lst_to_clifford(lst(1, 0, 0), nu, M); < ex e1 = lst_to_clifford(lst(0, 1, 0), nu, M); < ex e2 = lst_to_clifford(lst(0, 0, 1), nu, M);
varidx nu(symbol("nu"), 4); realsymbol s("s"); ex M = diag_matrix(lst(1, -1, 0, s)); ex e0 = lst_to_clifford(lst(1, 0, 0, 0), nu, M); ex e1 = lst_to_clifford(lst(0, 1, 0, 0), nu, M); ex e2 = lst_to_clifford(lst(0, 0, 1, 0), nu, M); ex e3 = lst_to_clifford(lst(0, 0, 0, 1), nu, M);
3261,3262c3292,3305 < @samp{v = (v~0, v~1, ..., v~n)} such that @samp{e = v~0 c.0 + v~1 c.1 + ... < + v~n c.n} with respect to the given Clifford units @code{c} and none of ---
@tex $v = (v^0, v^1, ..., v^n)$ @end tex @ifnottex @samp{v = (v~0, v~1, ..., v~n)} @end ifnottex such that @tex $e = v^0 c_0 + v^1 c_1 + ... + v^n c_n$ @end tex @ifnottex @samp{e = v~0 c.0 + v~1 c.1 + ... + v~n c.n} @end ifnottex with respect to the given Clifford units @code{c} and none of 3266c3309,3315 < @samp{(e c.k + c.k e)/pow(c.k, 2)}. If @samp{pow(c.k, 2) = 0} for some @samp{k}
@tex $(e c_k + c_k e)/c_k^2$. If $c_k^2$ @end tex @ifnottex @samp{(e c.k + c.k e)/pow(c.k, 2)}. If @samp{pow(c.k, 2)} @end ifnottex is zero or is not a @code{numeric} for some @samp{k} 3292a3342,3344 @ifnottex e* @end ifnottex 3296a3349,3351 @ifnottex @code{\bar@{e@}} @end ifnottex 3309c3364 < $||e||^2 = e\overline{e}$
$||e||^2 = e\overline{e}$. 3311,3312c3366,3369 < . The inverse of a Clifford expression is returned < by the function
@ifnottex @code{||e||^2 = e \bar@{e@}} @end ifnottex The inverse of a Clifford expression is returned by the function 3320c3377 < $e^{-1} = e/||e||^2$
$e^{-1} = \overline{e}/||e||^2$. 3322c3379,3382 < . If
@ifnottex @math{e^@{-1@} = \bar@{e@}/||e||^2} @end ifnottex If 3325a3386,3388 @ifnottex @math{||e||=0} @end ifnottex 3350,3354c3413,3418 < It takes a list or vector @code{v} and makes the Moebius < (conformal or linear-fractional) transformation @samp{v -> < (av+b)/(cv+d)} defined by the matrix @samp{M = [[a, b], [c, d]]}. The < parameter @code{G} defines the metric of the surrounding < (pseudo-)Euclidean space. The returned value of this function is a list
It takes a list or vector @code{v} and makes the Moebius (conformal or linear-fractional) transformation @samp{v -> (av+b)/(cv+d)} defined by the matrix @samp{M = [[a, b], [c, d]]}. The parameter @code{G} defines the metric of the surrounding (pseudo-)Euclidean space. This can be a matrix or a Clifford unit, in the later case the parameter @code{rl} is ignored even if supplied. The returned value of this function is a list 3356a3421,3453 LaTeX output for Clifford units looks like @code{\clifford[1]@{e@}^@{@{\nu@}@}}, where @code{1} is the @code{representation_label} and @code{\nu} is the index of the corresponding unit. This provides a flexible typesetting with a suitable defintion of the @code{\clifford} command. For example, the definition @example \newcommand@{\clifford@}[1][]@{@} @end example typesets all Clifford units identically, while the alternative definition @example \newcommand@{\clifford@}[2][]@{\ifcase #1 #2\or \tilde@{#2@} \or \breve@{#2@} \fi@} @end example prints units with @code{representation_label=0} as @tex $e$, @end tex @ifnottex @code{e}, @end ifnottex with @code{representation_label=1} as @tex $\tilde{e}$ @end tex @ifnottex @code{\tilde@{e@}} @end ifnottex and with @code{representation_label=2} as @tex $\breve{e}$. @end tex @ifnottex @code{\breve@{e@}}. @end ifnottex Index: ginac/clifford.h =================================================================== RCS file: /home/cvs/GiNaC/ginac/clifford.h,v retrieving revision 1.55 diff -r1.55 clifford.h 278,279c278,284 < /** Replaces all dirac_ONE's in e with 1 (effectively removing them). */ < ex remove_dirac_ONE(const ex & e);
/** Replaces dirac_ONE's (with a representation_label no less than rl) in e with 1. * For the default value rl = 0 remove all of them. Aborts if e contains any * clifford_unit with representation_label to be removed. * * @param e Expression to be processed * @param rl Value of representation label */ ex remove_dirac_ONE(const ex & e, unsigned char rl = 0); 292a298 * @param e Clifford unit object 294a301 ex lst_to_clifford(const ex & v, const ex & e); 304c311,312 < * @param algebraic Use algebraic or symbolic algorithm for extractions */
* @param algebraic Use algebraic or symbolic algorithm for extractions * @return List of components of a Clifford vector*/ 318,319c326,328 < * @param G Metric of the surrounding space < * @param rl Representation label */
* @param G Metric of the surrounding space, may be a Clifford unit then the next parameter is ignored * @param rl Representation label * @return List of components of the transformed vector*/ 327,328c336,338 < * @param G Metric of the surrounding space < * @param rl Representation label */
* @param G Metric of the surrounding space, may be a Clifford unit then the next parameter is ignored * @param rl Representation label * @return List of components of the transformed vector*/ Index: ginac/clifford.cpp =================================================================== RCS file: /home/cvs/GiNaC/ginac/clifford.cpp,v retrieving revision 1.84 diff -r1.84 clifford.cpp 216c216,217 < } else
} else { c.s << "\\clifford[" << int(representation_label) << "]"; 217a219 } 227c229 < DEFAULT_PRINT_LATEX(diracone, "ONE", "\\mathbb{1}")
DEFAULT_PRINT_LATEX(diracone, "ONE", "\\mathbf{1}") 940c942 < ex canonicalize_clifford(const ex & e)
ex canonicalize_clifford(const ex & e_) 944,946c946,948 < if (is_a<matrix>(e) // || is_a<pseries>(e) || is_a<integral>(e) < || is_a<lst>(e)) { < return e.map(fcn);
if (is_a<matrix>(e_) // || is_a<pseries>(e) || is_a<integral>(e) || is_a<lst>(e_)) { return e_.map(fcn); 947a950 ex e=simplify_indexed(e_); 1007,1008c1010,1011 < } else if (is_a<add>(e) || is_a<ncmul>(e) // || is_a<pseries>(e) || is_a<integral>(e) < || is_a<matrix>(e) || is_a<lst>(e)) {
} else if (is_a<add>(e) || is_a<ncmul>(e) || is_a<mul>(e) //|| is_a<pseries>(e) || is_a<integral>(e) || is_a<matrix>(e) || is_a<lst>(e)) { 1016c1019 < ex remove_dirac_ONE(const ex & e)
ex remove_dirac_ONE(const ex & e, unsigned char rl) 1018,1020c1021,1026 < pointer_to_map_function fcn(remove_dirac_ONE); < if (is_a<clifford>(e) && is_a<diracone>(e.op(0))) { < return 1;
pointer_to_map_function_1arg<unsigned char> fcn(remove_dirac_ONE, rl); if (is_a<clifford>(e) && ex_to<clifford>(e).get_representation_label() >= rl) { if (is_a<diracone>(e.op(0))) return 1; else throw(std::invalid_argument("Expression is a non-scalar Clifford number!")); 1022c1028 < || is_a<matrix>(e) || is_a<lst>(e)) {
|| is_a<matrix>(e) || is_a<lst>(e)) {
1046d1051 < unsigned min, max; 1049,1050c1054,1056 < unsigned dim = (ex_to<numeric>(ex_to<idx>(mu).get_dim())).to_int(); < ex c = clifford_unit(mu, metr, rl); ---
ex e = clifford_unit(mu, metr, rl); return lst_to_clifford(v, e); } 1052,1063c1058,1075 < if (is_a<matrix>(v)) { < if (ex_to<matrix>(v).cols() > ex_to<matrix>(v).rows()) { < min = ex_to<matrix>(v).rows(); < max = ex_to<matrix>(v).cols(); < } else { < min = ex_to<matrix>(v).cols(); < max = ex_to<matrix>(v).rows(); < } < if (min == 1) { < if (dim == max) < if (is_a<varidx>(mu)) // need to swap variance < return indexed(v, ex_to<varidx>(mu).toggle_variance()) * c;
ex lst_to_clifford(const ex & v, const ex & e) { unsigned min, max;
if (is_a<clifford>(e)) { varidx mu = ex_to<varidx>(e.op(1)); unsigned dim = (ex_to<numeric>(mu.get_dim())).to_int();
if (is_a<matrix>(v)) { if (ex_to<matrix>(v).cols() > ex_to<matrix>(v).rows()) { min = ex_to<matrix>(v).rows(); max = ex_to<matrix>(v).cols(); } else { min = ex_to<matrix>(v).cols(); max = ex_to<matrix>(v).rows(); } if (min == 1) { if (dim == max) return indexed(v, ex_to<varidx>(mu).toggle_variance()) * e; 1065c1077,1082 < return indexed(v, mu) * c;
throw(std::invalid_argument("Dimensions of vector and clifford unit mismatch")); } else throw(std::invalid_argument("First argument should be a vector vector")); } else if (is_a<lst>(v)) { if (dim == ex_to<lst>(v).nops()) return indexed(matrix(dim, 1, ex_to<lst>(v)), ex_to<varidx>(mu).toggle_variance()) * e;
1067c1084 < throw(std::invalid_argument("Dimensions of vector and clifford unit mismatch")); ---
throw(std::invalid_argument("List length and dimension of clifford unit mismatch"));
1069,1074c1086 < throw(std::invalid_argument("First argument should be a vector vector")); < } else if (is_a<lst>(v)) { < if (dim == ex_to<lst>(v).nops()) < return indexed(matrix(dim, 1, ex_to<lst>(v)), ex_to<varidx>(mu).toggle_variance()) * c; < else < throw(std::invalid_argument("List length and dimension of clifford unit mismatch")); ---
throw(std::invalid_argument("Cannot construct from anything but list or vector"));
1076c1088 < throw(std::invalid_argument("Cannot construct from anything but list or vector")); ---
throw(std::invalid_argument("The second argument should be a Clifford unit"));
1146c1158,1159 < if (pow(c.subs(mu == i), 2) == 0) ---
if (pow(c.subs(mu == i), 2).is_zero() or (not is_a<numeric>(pow(c.subs(mu == i), 2))))
1165,1171c1178 < ex x, D; < if (is_a<indexed>(G)) < D = ex_to<varidx>(G.op(1)).get_dim(); < else if (is_a<matrix>(G)) < D = ex_to<matrix>(G).rows(); < else < throw(std::invalid_argument("metric should be an indexed object or matrix")); ---
ex x, D, cu; 1173,1174d1179 < varidx mu((new symbol)->setflag(status_flags::dynallocated), D); < 1176a1182,1194
if (is_a<clifford>(G)) { cu = G; } else { if (is_a<indexed>(G)) D = ex_to<varidx>(G.op(1)).get_dim(); else if (is_a<matrix>(G)) D = ex_to<matrix>(G).rows(); else throw(std::invalid_argument("metric should be an indexed object, matrix, or a Clifford unit"));
varidx mu((new symbol)->setflag(status_flags::dynallocated), D); cu = clifford_unit(mu, G, rl); } 1178c1196 < x = lst_to_clifford(v, mu, G, rl);
x = lst_to_clifford(v, cu); 1180d1197 < ex cu = clifford_unit(mu, G); Index: check/exam_clifford.cpp =================================================================== RCS file: /home/cvs/GiNaC/check/exam_clifford.cpp,v retrieving revision 1.23 diff -r1.23 exam_clifford.cpp 344c344,345 < e = lst_to_clifford(lst(t, x, y, z), mu, G) * lst_to_clifford(lst(1, 2, 3, 4), nu, G);
ex c = clifford_unit(nu, G, 1); e = lst_to_clifford(lst(t, x, y, z), mu, G, 1) * lst_to_clifford(lst(1, 2, 3, 4), c); 346c347 < result += check_equal((e*e1).simplify_indexed().normal(), dirac_ONE());
result += check_equal((e*e1).simplify_indexed().normal(), dirac_ONE(1));
participants (1)
-
Vladimir Kisil