CALIB provides the Za
domain, representing the ring
Z(a), the extension of the integers with given algebraic integer
a (specified via a monic irreducible polynomial in Z[x]
of degree at least two).
The “values” of this domain are represented by the following object:
struct calib_Za_obj { const struct calib_Za_dom * dom; /* Z(a) domain containing this value */ mpz_ptr coeff; /* Coefficients. This is an array of */ /* k integers. */ };
These value objects are subject to init()
and clear()
operations.
All such objects must be initialized prior to use by any other CALIB
operation.
Memory leaks result if they are not cleared when done.
The CALIB Za
domain is constructed by specifying a monic,
irreducible “generator” polynomial of degree k in
Z[x].
One may access CALIB’s Za
domain as follows:
#include "calib/Za.h" ... struct calib_Zx_obj * apoly; struct calib_Za_dom * Za; apoly = /* monic, irreducible polynomial defining 'a'. */ Za = calib_make_Za_dom (apoly); ... calib_free_Za_dom (Za);
Let k be the degree of the monic polynomial defining the algebraic integer a. The “values” of this Za domain are polynomials in Z[a] having degree at most k-1.
The struct calib_Za_dom
object contains the following members
(pointers to functions) that provide operations of the domain:
void (*init) (const struct calib_Za_dom * rp, struct calib_Z_obj * x);
Initialize Za value object x
to be a member of the Za
domain rp
, where:
rp | is the Za ring/domain performing this operation; and |
x | is the Za value object to be initialized. |
void (*clear) (struct calib_Z_obj * x);
Clear out the given Za value object x
(freeing all memory it
might hold), where:
x | is the Za value object to be cleared. |
void (*set) (struct calib_Za_obj * rop, const struct calib_Za_obj * op);
Set rop
to op
in Za, where:
rop | is the destination Z(a) value; and |
op | is the source Z(a) value. |
void (*set_si) (struct calib_Za_obj * rop, calib_si_t op);
Set rop
to op
in Za, where:
rop | is the destination Z(a) value; and |
op | is the source integer value. |
void (*set_z) (struct calib_Za_obj * rop, mpz_srcptr op);
Set rop
to op
in Za, where:
rop | is the destination Z(a) value; and |
op | is the source GMP integer value. |
void (*set_q) (struct calib_Za_obj * rop, mpq_srcptr op);
Set rop
to op
in Za, where:
rp | is the Za ring/domain performing this operation; |
rop | is the destination Z(a) value; and |
op | is the source GMP integer value. |
The denominator of op
must be 1.
void (*set_var_power) (struct calib_Za_obj * rop, int power);
Set rop
to a ** power
in Za, where:
rop | is the destination Z(a) value; and |
power | is the power to set (must be non-negative). |
void (*add) (struct calib_Za_obj * rop, const struct calib_Za_obj * op1, const struct calib_Za_obj * op2);
Set rop
to op1 + op2
in Za, where:
rop | is the destination Z(a) value; |
a | is the first operand; and |
b | is the second operand. |
void (*sub) (struct calib_Za_obj * rop, const struct calib_Za_obj * op1, const struct calib_Za_obj * op2);
Set rop
to op1 - op2
in Za, where:
rop | is the destination Z(a) value; |
op1 | is the first operand; and |
op2 | is the second operand. |
void (*neg) (struct calib_Za_obj * rop, const struct calib_Za_obj * op);
Set rop
to - op
in Za, where:
rop | is the destination Z(a) value; and |
op | is the operand to be negated. |
void (*mul) (struct calib_Za_obj * rop, const struct calib_Za_obj * op1, const struct calib_Za_obj * op2);
Set rop
to op1 * op2
in Za, where:
rop | is the destination Z(a) value; |
op1 | is the first operand; and |
op2 | is the second operand. |
void (*mul_z) (struct calib_Za_obj * rop, const struct calib_Za_obj * op1, mpz_srcptr op2);
Set rop
to op1 * op2
in Za, where:
rop | is the destination Z(a) value; |
op1 | is the first operand; and |
op2 | is the second operand. |
void (*mul_a) (struct calib_Za_obj * rop, const struct calib_Za_obj * op);
Set rop
to op * a
(multiply by algebraic integer
a), where:
rop | is the destination Z(a) value; and |
op | is the source operand being multiplied. |
void (*ipow) (struct calib_Za_obj * rop, const struct calib_Za_obj * op, int power);
Set rop
to op ** power
in Za, where:
rop | is the destination Z(a) value; |
op | is the operand to exponentiate; and |
power | is the power to take (must be >= 0). |
void (*pinv) (struct calib_Za_obj * rop, mpz_ptr d, const struct calib_Za_obj * op);
Pseudo-inverse in Z(a). Compute rop in Z(a) and d in Z such that rop * op = d, where:
rop | is the destination Z(a) value; |
d | is a single GMP integer receiving the value d; and |
op | is the source operand to pseudo-invert. |
void (*div_z_exact) (struct calib_Za_obj * rop, const struct calib_Za_obj * op1, mpz_srcptr op2);
Set rop
to op1 / op2
in Za, where:
rop | is the destination Z(a) value; |
op1 | is the first operand; and |
op2 | is the second operand. |
The division must be exact.
void (*prim_part) (mpz_ptr content, struct calib_Za_obj * ppart, const struct calib_Za_obj * op);
Compute content and primitive part of op
in Z(a), storing them
in content
and ppart
, respectively, where:
content | receives the content of op ; |
ppart | is the Z(a) value object receiving the primitive part of
op ; and |
op | is the operand for which to compute the content and primitive part. |
void (*cvZa) (struct calib_Za_obj * rop, const struct calib_Za_obj * op);
Set rop
to op
. Note that rop
and op
are
permitted to belong to different Za domains, and this routine performs
the necessary conversion, where:
rop | is the destination Z(a) value; and |
op | is the source Z(a) value to convert. |
int (*degree) (const struct calib_Za_obj * op);
Return the degree (in a) of the given Z(a) value
op
, where:
op | is the operand for which to get the degree. |
Note that the degree of a zero value is -1.
calib_bool (*zerop) (const struct calib_Za_obj * op);
Return 1 if-and-only-if op
is identically zero and 0 otherwise,
where:
op | is the operand to test for zero. |
calib_bool (*onep) (const struct calib_Za_obj * op);
Return 1 if-and-only-if op
is identically one and 0 otherwise,
where:
op | is the operand to test for one. |
void (*set_genrep) (struct calib_Za_obj * rop, const struct calib_genrep * op, const char * var);
Given a genrep op
and the name var
of the algebraic
integer a, convert this genrep into a value in this Z(a)
domain, storing the result in rop
, where:
rop | is the Z(a) value object receiving value; |
op | is the genrep being converted; and |
var | is the name of the algebraic integer a appearing within
genrep op . |
struct calib_genrep * (*to_genrep) (const struct calib_Za_obj * op, const char * var);
Return a dynamically-allocated genrep representing the given value
op
of the given Z(a) domain, using the given variable
name var
to represent the algebraic integer a, where:
op | is value from Z(a) being converted to genrep form; and |
var | is the name of the algebraic integer a as it should appear
within the genrep returned. |