MLIR 22.0.0git
GeneratingFunction.h
Go to the documentation of this file.
1//===- GeneratingFunction.h - Generating Functions over Q^d -----*- C++ -*-===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8//
9// Definition of the GeneratingFunction class for Barvinok's algorithm,
10// which represents a function over Q^n, parameterized by d parameters.
11//
12//===----------------------------------------------------------------------===//
13
14#ifndef MLIR_ANALYSIS_PRESBURGER_GENERATINGFUNCTION_H
15#define MLIR_ANALYSIS_PRESBURGER_GENERATINGFUNCTION_H
16
19
20namespace mlir {
21namespace presburger {
22namespace detail {
23
24// A parametric point is a vector, each of whose elements
25// is an affine function of n parameters. Each column
26// in the matrix represents the affine function and
27// has n+1 elements.
29
30// A point is simply a vector.
32
33// A class to describe the type of generating function
34// used to enumerate the integer points in a polytope.
35// Consists of a set of terms, where the ith term has
36// * a sign, ±1, stored in `signs[i]`
37// * a numerator, of the form x^{n},
38// where n, stored in `numerators[i]`,
39// is a parametric point.
40// * a denominator, of the form (1 - x^{d1})...(1 - x^{dn}),
41// where each dj, stored in `denominators[i][j]`,
42// is a vector.
43//
44// Represents functions f_p : Q^n -> Q of the form
45//
46// f_p(x) = \sum_i s_i * (x^n_i(p)) / (\prod_j (1 - x^d_{ij})
47//
48// where s_i is ±1,
49// n_i \in Q^d -> Q^n is an n-vector of affine functions on d parameters, and
50// g_{ij} \in Q^n are vectors.
52public:
53 GeneratingFunction(unsigned numParam, SmallVector<int> signs,
54 std::vector<ParamPoint> nums,
55 std::vector<std::vector<Point>> dens)
56 : numParam(numParam), signs(signs), numerators(nums), denominators(dens) {
57#ifndef NDEBUG
58 for (const ParamPoint &term : numerators)
59 assert(term.getNumRows() == numParam + 1 &&
60 "dimensionality of numerator exponents does not match number of "
61 "parameters!");
62#endif // NDEBUG
63 }
64
65 unsigned getNumParams() const { return numParam; }
66
67 SmallVector<int> getSigns() const { return signs; }
68
69 std::vector<ParamPoint> getNumerators() const { return numerators; }
70
71 std::vector<std::vector<Point>> getDenominators() const {
72 return denominators;
73 }
74
76 assert(numParam == gf.getNumParams() &&
77 "two generating functions with different numbers of parameters "
78 "cannot be added!");
79 SmallVector<int> sumSigns = signs;
80 sumSigns.append(gf.signs);
81
82 std::vector<ParamPoint> sumNumerators = numerators;
83 llvm::append_range(sumNumerators, gf.numerators);
84
85 std::vector<std::vector<Point>> sumDenominators = denominators;
86 llvm::append_range(sumDenominators, gf.denominators);
87 return GeneratingFunction(numParam, sumSigns, sumNumerators,
88 sumDenominators);
89 }
90
91 llvm::raw_ostream &print(llvm::raw_ostream &os) const {
92 for (unsigned i = 0, e = signs.size(); i < e; i++) {
93 if (i == 0) {
94 if (signs[i] == -1)
95 os << "- ";
96 } else {
97 if (signs[i] == 1)
98 os << " + ";
99 else
100 os << " - ";
101 }
102
103 os << "x^[";
104 unsigned r = numerators[i].getNumRows();
105 for (unsigned j = 0; j < r - 1; j++) {
106 os << "[";
107 for (unsigned k = 0, c = numerators[i].getNumColumns(); k < c - 1; k++)
108 os << numerators[i].at(j, k) << ",";
109 os << numerators[i].getRow(j).back() << "],";
110 }
111 os << "[";
112 for (unsigned k = 0, c = numerators[i].getNumColumns(); k < c - 1; k++)
113 os << numerators[i].at(r - 1, k) << ",";
114 os << numerators[i].getRow(r - 1).back() << "]]/";
115
116 for (const Point &den : denominators[i]) {
117 os << "(x^[";
118 for (unsigned j = 0, e = den.size(); j < e - 1; j++)
119 os << den[j] << ",";
120 os << den.back() << "])";
121 }
122 }
123 return os;
124 }
125
126private:
127 unsigned numParam;
128 SmallVector<int> signs;
129 std::vector<ParamPoint> numerators;
130 std::vector<std::vector<Point>> denominators;
131};
132
133} // namespace detail
134} // namespace presburger
135} // namespace mlir
136
137#endif // MLIR_ANALYSIS_PRESBURGER_GENERATINGFUNCTION_H
std::vector< ParamPoint > getNumerators() const
std::vector< std::vector< Point > > getDenominators() const
GeneratingFunction operator+(const GeneratingFunction &gf) const
llvm::raw_ostream & print(llvm::raw_ostream &os) const
GeneratingFunction(unsigned numParam, SmallVector< int > signs, std::vector< ParamPoint > nums, std::vector< std::vector< Point > > dens)
SmallVector< Fraction > Point
Include the generated interface declarations.
Eliminates variable at the specified position using Fourier-Motzkin variable elimination.