FLINT3.7.0-dev
Module · 128 functions

gr_mpoly.h

#include <flint/gr_mpoly.h>

This module implements sparse multivariate polynomials f \in R[X_1, \ldots, X_n] over a ring R given by a generic context. A polynomial is stored as an array of coefficients in R and an array of packed exponent vectors, sorted by a monomial ordering, in the same format as fmpz_mpoly and the other multivariate modules (mpoly.h). Unlike gr_poly, the context of this module is the context of the polynomial ring itself: a gr_mpoly_ctx_t is a gr_ctx_t whose elements are gr_mpoly_t, so the polynomials can be used with the generic functions (gr_add, gr_mul, gr_div, gr_set_str, ...), in matrices (gr_mat), as coefficients of univariate polynomials and in any other generic algorithm.

Products are computed with Johnson's heap algorithm and exact quotients and divisions with remainder with the heap algorithm of Monagan and Pearce [MonPea2007; MonPea2009], in parallel for large inputs over thread-safe coefficient rings (Sparse and dense multiplication, Division, exact division and square roots); see Multivariate polynomials: representations and algorithms for the specialised multivariate modules (fmpz_mpoly, nmod_mpoly, fq_nmod_mpoly, ...), which are much faster over their rings and also provide GCDs and factorisation.

Guides#

Types and conventions#

A multivariate polynomial: the fields are coeffs (an array of coefficients in R), exps (the packed exponent vectors, bits bits per exponent field), length (the number of terms), bits, and the allocated sizes coeffs_alloc and exps_alloc. The terms are sorted in decreasing order of their monomials with respect to the ordering of the context, and no two terms have the same monomial. A gr_mpoly_t is an array of one gr_mpoly_struct.

A polynomial is normalised by removing terms whose coefficient is provably zero. Over rings with undecidable zero tests (balls, exact real numbers) a coefficient that may be zero is kept, as in 3xy^2 + [\pm 0.01] xy, so that the length and the degrees are upper bounds; functions that need the exact term structure, such as division, return GR_UNABLE for such inputs. Functions returning int return status codes as described in gr.h, and functions without a leading underscore allow aliasing of inputs and outputs.

The context of a polynomial ring R[X_1, \ldots, X_n]. It is a gr_ctx_t, so the generic gr functions can be used with it: gr_add on gr_mpoly_t elements of this context is gr_mpoly_add. The context data (of type _gr_mpoly_ctx_struct) consists of the coefficient context cctx, which is not owned by the polynomial context and must stay alive as long as it is used; an mpoly_ctx_t mctx with the number of variables and the monomial ordering, which is owned; and an optional array vars of names of the generators, set with gr_mpoly_ctx_set_gen_names (by default NULL, meaning default names). The names are used for printing, for parsing with gr_set_str and for conversions between rings.

The coefficient context, the mpoly_ctx_struct of the exponent format and ordering, the array of generator names, and the number of variables of a gr_mpoly context.

Contexts#

void gr_mpoly_ctx_init(gr_mpoly_ctx_t ctx, gr_ctx_t base_ring, slong nvars, const ordering_t ord)

Initialises ctx as the ring of polynomials in nvars variables over base_ring, with the monomial ordering ord (ORD_LEX, ORD_DEGLEX or ORD_DEGREVLEX).

void gr_mpoly_ctx_init_rand(gr_mpoly_ctx_t ctx, flint_rand_t state, gr_ctx_t base_ring, slong max_nvars)

Initialises ctx with a random number of variables between 0 and max_nvars and a random ordering, for testing.

Clears the context (but not the coefficient ring).

int gr_mpoly_ctx_set_gen_names(gr_mpoly_ctx_t ctx, const char ** s)

Sets the names of the n generators to copies of the strings s[0], …, s[n-1].

Context methods: a description of the ring, and structural predicates inherited from the coefficient ring. The polynomial ring is a field only if it has no variables and the coefficient ring is a field.

Memory management#

Initialise A as the zero polynomial; init2 and init3 allocate space for alloc terms, with the default number of bits per exponent or with bits bits.

Ensure space for len terms, or exponent fields of at least bits bits (repacking the existing exponents), or both. The reset_bits version sets the number of bits to bits without preserving the exponents, for use before writing a new polynomial.

void _gr_mpoly_fit_length(gr_ptr * coeffs, slong * coeffs_alloc, ulong ** exps, slong * exps_alloc, slong N, slong length, gr_ctx_t cctx)

Grows the arrays *coeffs and *exps (with N words per exponent vector) to hold at least length terms, updating the allocation counters. Here cctx is the coefficient ring.

Set the number of terms of A (which must be allocated), without normalising, and return the number of terms.

Removes the terms whose coefficient is provably zero. All functions return normalised polynomials; this is for code that writes terms directly.

Swap two polynomials in constant time, and make res a shallow copy of poly sharing its arrays (which must then not be cleared twice).

Vectors of polynomials#

A resizable vector of polynomials over one context, with the fields entries, alloc and length. It has the layout of a gr_vec_t whose elements are polynomials, and can be cast to and from it.

Initialise vec as len zero polynomials, and clear it.

gr_mpoly_struct * gr_mpoly_vec_entry_ptr(gr_mpoly_vec_t vec, slong i, gr_mpoly_ctx_t ctx)
const gr_mpoly_struct * gr_mpoly_vec_entry_srcptr(const gr_mpoly_vec_t vec, slong i, gr_mpoly_ctx_t ctx)

Return a pointer to the entry with index 0 \le i < length, and the length.

Allocate space for len entries, change the length (appending zero polynomials), copy a vector, and append a copy of f.

Assignment, generators and comparisons#

Set A to a copy of B, to zero or to one.

Converts the element A of the ring A_ctx into the polynomial ring.

More

Set A to the generator with index var (from 0), res to the vector of the generators X_1, \ldots, X_n, or vec to the generators of the coefficient ring (recursively, as constants) followed by X_1, \ldots, X_n.

Return whether A is zero, one, the generator with index var, or equal to B, comparing terms and deciding coefficients in the coefficient ring.

Random polynomials#

Set A to a random polynomial with up to length terms, with exponents of up to exp_bits bits or less than exp_bound, and random coefficients (gr_randtest). The default version, used for gr_randtest, chooses small random parameters.

Input and output#

Write the polynomial as an expression in the generator names of the context, with the terms in decreasing order; gr_mpoly_write is the same as gr_mpoly_write_pretty. Polynomials can be parsed with gr_set_str.

Coefficients and terms#

Set c to the coefficient of the monomial with exponent vector exp (zero if there is no such term).

Set the coefficient of the monomial with exponent vector exp (given as fmpz or ulong entries) to c, inserting or removing the term as needed. Each call costs time linear in the number of terms; to build a polynomial term by term, use the push functions below.

Append a term with exponent vector exp at the end of A, increasing the number of bits per exponent if necessary; the underscore versions append only the monomial and leave the new coefficient for the caller to set. The result is in general not sorted and may contain repeated monomials or zero coefficients: call gr_mpoly_sort_terms and gr_mpoly_combine_like_terms afterwards.

Sort the terms of A by the monomial ordering, and add the coefficients of terms with equal monomials, removing provably zero terms; the second assumes sorted terms.

Check that A is in canonical form: terms strictly sorted, exponents fitting in the bit size, and no provably zero coefficients. gr_mpoly_assert_canonical aborts with an error message otherwise.

Arithmetic#

Set A to -B, B + C or B - C, by merging the sorted term lists.

Set A to B c for a scalar c (removing terms that become zero).

Set A to the product BC. The heap version uses Johnson's algorithm, which merges the |B| sorted rows b_i C with a heap of size |B|, with O(|B| |C| \log |B|) monomial comparisons and memory proportional to the output; the heap_threaded version divides the output among threads. The monomial version requires C to have one term.

More
int gr_mpoly_sqr(gr_mpoly_t poly1, const gr_mpoly_t poly2, gr_mpoly_ctx_t ctx)

Set poly1 to the square of poly2. The commutative versions require a commutative (or approximately commutative) coefficient ring and compute only the products b_i b_j with i \le j, doubling the off-diagonal ones; the default uses them (threaded above 100 terms) and the monomial version for a single term.

Division#

Checked exact division. If B divides A, set Q = A / B and return GR_SUCCESS; if not, set Q to zero and return GR_DOMAIN; if divisibility cannot be decided, return GR_UNABLE. Division by zero gives GR_DOMAIN (except in the zero ring).

More

Set Q = A / B, assuming without checking that B divides A, which saves the divisibility checks. The default is threaded under the same conditions as gr_mpoly_divides.

Multivariate division with remainder: A = QB + R where no monomial of R is divisible by the leading monomial of B. The div versions return only Q. Over a field this always works; over other rings it works whenever each division by the leading coefficient of B that occurs is exact, and returns GR_DOMAIN (with Q and R set to zero) otherwise. The defaults use the threaded algorithm for |A| > 500, |B| > 2 and a thread-safe ring when threads are available.

Weak division with remainder over rings that are not fields: when a coefficient division by the leading coefficient of B is not exact, the coefficients are divided with remainder (gr_euclidean_divrem in the coefficient ring, the analogue of fmpz_fdiv_qr over \mathbb{Z}) and the remainder is kept, instead of failing. The result satisfies A = QB + R, but monomials of R may still be divisible by the leading monomial of B.

Division by a vector of divisors B_1, \ldots, B_k: A = \sum_i Q_i B_i + R, where no monomial of R is divisible by any leading monomial \operatorname{lm}(B_i) (the multivariate division algorithm, [CLO2015, §2.3]); the result depends on the order of the divisors unless they form a Gröbner basis. The weak versions accumulate inexact coefficient remainders as for gr_mpoly_divrem_weak. The output vector Q is resized to k entries.

Pseudo-division: compute a scalar scale (an element of the coefficient ring, a product of powers of leading coefficients of the divisors) with \mathit{scale} \cdot A = QB + R, respectively \mathit{scale} \cdot A = \sum_i Q_i B_i + R, and no monomial of R divisible by a leading monomial of the divisors. This divides over the fraction field of an integral domain without leaving the ring.

Sets res to the inverse of poly if it is a constant with an invertible coefficient. Returns GR_DOMAIN if poly is zero (outside the zero ring) or, over an integral domain, nonconstant; returns GR_UNABLE if invertibility cannot be decided (over rings with nilpotents a nonconstant polynomial can be a unit).

Sets res to the canonical associate of poly: poly multiplied by the unit c that makes its leading coefficient canonical in the coefficient ring (gr_canonical_associate: monic over a field, positive over \mathbb{Z}). If u is not NULL it is set to c, so that \mathit{res} = u \cdot \mathit{poly}.

Derivatives and integrals#

Sets A to the partial derivative of B with respect to the variable with index var.

Sets A to the integral of B with respect to the variable with index var, with zero constant of integration; this divides coefficients by the new exponents (gr_div_ui), which must be possible in the coefficient ring.

References#

  • [MonPea2007] M. Monagan and R. Pearce. Polynomial division using dynamic arrays, heaps, and packed exponent vectors. Computer Algebra in Scientific Computing (CASC 2007), Lecture Notes in Computer Science 4770, Springer, 2007, 295–315. https://doi.org/10.1007/978-3-540-75187-8_23
  • [MonPea2009] M. Monagan and R. Pearce. Parallel sparse polynomial multiplication using heaps. Proceedings of ISSAC 2009, ACM, 263–270. https://doi.org/10.1145/1576702.1576739
  • [CLO2015] D. Cox, J. Little and D. O'Shea. Ideals, Varieties, and Algorithms, fourth edition. Undergraduate Texts in Mathematics, Springer, 2015. https://doi.org/10.1007/978-3-319-16721-3
Cite this page

The FLINT team, “gr_mpoly.h (module overview),” FLINT: Fast Library for Number Theory, documentation, version 3.7.0-dev, 2026. https://flintlib.org/doc/gr_mpoly/index.html (generated 2026-10-20).