manpagez: man pages & more
info ginac
Home | html | info | man
[ < ] [ > ]   [ << ] [ Up ] [ >> ]         [Top] [Contents] [Index] [ ? ]

4.14.3 Symmetries

Indexed objects can have certain symmetry properties with respect to their indices. Symmetries are specified as a tree of objects of class symmetry that is constructed with the helper functions

 
symmetry sy_none(...);
symmetry sy_symm(...);
symmetry sy_anti(...);
symmetry sy_cycl(...);

sy_none() stands for no symmetry, sy_symm() and sy_anti() specify fully symmetric or antisymmetric, respectively, and sy_cycl() represents a cyclic symmetry. Each of these functions accepts up to four arguments which can be either symmetry objects themselves or unsigned integer numbers that represent an index position (counting from 0). A symmetry specification that consists of only a single sy_symm(), sy_anti() or sy_cycl() with no arguments specifies the respective symmetry for all indices.

Here are some examples of symmetry definitions:

 
    ...
    // No symmetry:
    e = indexed(A, i, j);
    e = indexed(A, sy_none(), i, j);     // equivalent
    e = indexed(A, sy_none(0, 1), i, j); // equivalent

    // Symmetric in all three indices:
    e = indexed(A, sy_symm(), i, j, k);
    e = indexed(A, sy_symm(0, 1, 2), i, j, k); // equivalent
    e = indexed(A, sy_symm(2, 0, 1), i, j, k); // same symmetry, but yields a
                                               // different canonical order

    // Symmetric in the first two indices only:
    e = indexed(A, sy_symm(0, 1), i, j, k);
    e = indexed(A, sy_none(sy_symm(0, 1), 2), i, j, k); // equivalent

    // Antisymmetric in the first and last index only (index ranges need not
    // be contiguous):
    e = indexed(A, sy_anti(0, 2), i, j, k);
    e = indexed(A, sy_none(sy_anti(0, 2), 1), i, j, k); // equivalent

    // An example of a mixed symmetry: antisymmetric in the first two and
    // last two indices, symmetric when swapping the first and last index
    // pairs (like the Riemann curvature tensor):
    e = indexed(A, sy_symm(sy_anti(0, 1), sy_anti(2, 3)), i, j, k, l);

    // Cyclic symmetry in all three indices:
    e = indexed(A, sy_cycl(), i, j, k);
    e = indexed(A, sy_cycl(0, 1, 2), i, j, k); // equivalent

    // The following examples are invalid constructions that will throw
    // an exception at run time.

    // An index may not appear multiple times:
    e = indexed(A, sy_symm(0, 0, 1), i, j, k); // ERROR
    e = indexed(A, sy_none(sy_symm(0, 1), sy_anti(0, 2)), i, j, k); // ERROR

    // Every child of sy_symm(), sy_anti() and sy_cycl() must refer to the
    // same number of indices:
    e = indexed(A, sy_symm(sy_anti(0, 1), 2), i, j, k); // ERROR

    // And of course, you cannot specify indices which are not there:
    e = indexed(A, sy_symm(0, 1, 2, 3), i, j, k); // ERROR
    ...

If you need to specify more than four indices, you have to use the .add() method of the symmetry class. For example, to specify full symmetry in the first six indices you would write sy_symm(0, 1, 2, 3).add(4).add(5).

If an indexed object has a symmetry, GiNaC will automatically bring the indices into a canonical order which allows for some immediate simplifications:

 
    ...
    cout << indexed(A, sy_symm(), i, j)
          + indexed(A, sy_symm(), j, i) << endl;
     // -> 2*A.j.i
    cout << indexed(B, sy_anti(), i, j)
          + indexed(B, sy_anti(), j, i) << endl;
     // -> 0
    cout << indexed(B, sy_anti(), i, j, k)
          - indexed(B, sy_anti(), j, k, i) << endl;
     // -> 0
    ...

[ < ] [ > ]   [ << ] [ Up ] [ >> ]         [Top] [Contents] [Index] [ ? ]
© manpagez.com 2000-2024
Individual documents may contain additional copyright information.