passagemath-brial 10.8.1a3__cp314-cp314-manylinux_2_24_aarch64.manylinux_2_28_aarch64.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- passagemath_brial/__init__.py +3 -0
- passagemath_brial-10.8.1a3.dist-info/METADATA +96 -0
- passagemath_brial-10.8.1a3.dist-info/RECORD +39 -0
- passagemath_brial-10.8.1a3.dist-info/WHEEL +6 -0
- passagemath_brial-10.8.1a3.dist-info/top_level.txt +3 -0
- passagemath_brial.libs/libbrial-a2b87c7c.so.3.0.7 +0 -0
- passagemath_brial.libs/libbrial_groebner-607bf574.so.3.0.7 +0 -0
- passagemath_brial.libs/libgmp-93ebf16a.so.10.5.0 +0 -0
- passagemath_brial.libs/libm4ri-4311ab86.so.2.0.1 +0 -0
- passagemath_brial.libs/libpng16-5d944a30.so.16.54.0 +0 -0
- sage/all__sagemath_brial.py +9 -0
- sage/libs/all__sagemath_brial.py +1 -0
- sage/libs/polybori/__init__.pxd +2 -0
- sage/libs/polybori/decl.pxd +401 -0
- sage/libs/polybori/pb_wrap.h +133 -0
- sage/rings/all__sagemath_brial.py +1 -0
- sage/rings/polynomial/all__sagemath_brial.py +1 -0
- sage/rings/polynomial/pbori/PyPolyBoRi.py +124 -0
- sage/rings/polynomial/pbori/__init__.py +46 -0
- sage/rings/polynomial/pbori/blocks.py +499 -0
- sage/rings/polynomial/pbori/cnf.py +241 -0
- sage/rings/polynomial/pbori/easy_polynomials.py +59 -0
- sage/rings/polynomial/pbori/fglm.py +93 -0
- sage/rings/polynomial/pbori/frontend.py +70 -0
- sage/rings/polynomial/pbori/gbcore.py +644 -0
- sage/rings/polynomial/pbori/gbrefs.py +129 -0
- sage/rings/polynomial/pbori/heuristics.py +35 -0
- sage/rings/polynomial/pbori/interpolate.py +122 -0
- sage/rings/polynomial/pbori/interred.py +34 -0
- sage/rings/polynomial/pbori/ll.py +302 -0
- sage/rings/polynomial/pbori/nf.py +671 -0
- sage/rings/polynomial/pbori/parallel.py +308 -0
- sage/rings/polynomial/pbori/pbori.cpython-314-aarch64-linux-gnu.so +0 -0
- sage/rings/polynomial/pbori/pbori.pxd +127 -0
- sage/rings/polynomial/pbori/pbori.pyx +8103 -0
- sage/rings/polynomial/pbori/randompoly.py +111 -0
- sage/rings/polynomial/pbori/rank.py +27 -0
- sage/rings/polynomial/pbori/specialsets.py +119 -0
- sage/rings/polynomial/pbori/statistics.py +35 -0
|
@@ -0,0 +1,241 @@
|
|
|
1
|
+
# sage_setup: distribution = sagemath-brial
|
|
2
|
+
# sage.doctest: needs sage.rings.polynomial.pbori
|
|
3
|
+
from random import Random
|
|
4
|
+
|
|
5
|
+
from sage.rings.polynomial.pbori.pbori import if_then_else as ite
|
|
6
|
+
from sage.rings.polynomial.pbori.PyPolyBoRi import Polynomial
|
|
7
|
+
from sage.rings.polynomial.pbori.statistics import used_vars_set
|
|
8
|
+
|
|
9
|
+
|
|
10
|
+
class CNFEncoder:
|
|
11
|
+
def __init__(self, r, random_seed=16):
|
|
12
|
+
self.random_generator = Random(random_seed)
|
|
13
|
+
self.one_set = r.one().set()
|
|
14
|
+
self.empty_set = r.zero().set()
|
|
15
|
+
self.r = r
|
|
16
|
+
|
|
17
|
+
def zero_blocks(self, f):
|
|
18
|
+
r"""
|
|
19
|
+
Divide the zero set of f into blocks.
|
|
20
|
+
|
|
21
|
+
TESTS::
|
|
22
|
+
|
|
23
|
+
sage: from sage.rings.polynomial.pbori import *
|
|
24
|
+
sage: r = declare_ring(["x", "y", "z"], dict())
|
|
25
|
+
sage: from sage.rings.polynomial.pbori.cnf import CNFEncoder
|
|
26
|
+
sage: e = CNFEncoder(r)
|
|
27
|
+
sage: e.zero_blocks(r.variable(0)*r.variable(1)*r.variable(2))
|
|
28
|
+
[{z: 0}, {y: 0}, {x: 0}]
|
|
29
|
+
"""
|
|
30
|
+
f = Polynomial(f)
|
|
31
|
+
variables = f.vars_as_monomial()
|
|
32
|
+
|
|
33
|
+
space = variables.divisors()
|
|
34
|
+
variables = list(variables.variables())
|
|
35
|
+
zeros = f.zeros_in(space)
|
|
36
|
+
rest = zeros
|
|
37
|
+
res = []
|
|
38
|
+
|
|
39
|
+
# inefficient compared to polynomials lex_lead
|
|
40
|
+
def choose(s):
|
|
41
|
+
indices = []
|
|
42
|
+
assert not s.empty()
|
|
43
|
+
nav = s.navigation()
|
|
44
|
+
while not nav.constant():
|
|
45
|
+
e = nav.else_branch()
|
|
46
|
+
t = nav.then_branch()
|
|
47
|
+
if e.constant() and not e.terminal_one():
|
|
48
|
+
indices.append(nav.value())
|
|
49
|
+
nav = t
|
|
50
|
+
elif self.random_generator.randint(0, 1):
|
|
51
|
+
indices.append(nav.value())
|
|
52
|
+
nav = t
|
|
53
|
+
|
|
54
|
+
else:
|
|
55
|
+
nav = e
|
|
56
|
+
assert nav.terminal_one()
|
|
57
|
+
res = self.one_set
|
|
58
|
+
for i in reversed(indices):
|
|
59
|
+
res = ite(i, res, self.empty_set)
|
|
60
|
+
return next(iter(res))
|
|
61
|
+
while not rest.empty():
|
|
62
|
+
l = choose(rest)
|
|
63
|
+
l_variables = set(l.variables())
|
|
64
|
+
|
|
65
|
+
def get_val(var):
|
|
66
|
+
if var in l_variables:
|
|
67
|
+
return 1
|
|
68
|
+
return 0
|
|
69
|
+
block_dict = {v: get_val(v) for v in variables}
|
|
70
|
+
|
|
71
|
+
l = l.set()
|
|
72
|
+
self.random_generator.shuffle(variables)
|
|
73
|
+
for v in variables:
|
|
74
|
+
candidate = l.change(v.index())
|
|
75
|
+
if candidate.diff(zeros).empty():
|
|
76
|
+
l = l.union(candidate)
|
|
77
|
+
del block_dict[v]
|
|
78
|
+
rest = rest.diff(l)
|
|
79
|
+
res.append(block_dict)
|
|
80
|
+
return res
|
|
81
|
+
|
|
82
|
+
def clauses(self, f):
|
|
83
|
+
r"""
|
|
84
|
+
|
|
85
|
+
TESTS::
|
|
86
|
+
|
|
87
|
+
sage: from sage.rings.polynomial.pbori import *
|
|
88
|
+
sage: r = declare_ring(["x", "y", "z"], dict())
|
|
89
|
+
sage: from sage.rings.polynomial.pbori.cnf import CNFEncoder
|
|
90
|
+
sage: e = CNFEncoder(r)
|
|
91
|
+
sage: sorted(e.clauses(r.variable(0)*r.variable(1)*r.variable(2)), key=lambda d: sorted(d.items()))
|
|
92
|
+
[{z: 0, y: 0, x: 0}]
|
|
93
|
+
sage: sorted(e.clauses(r.variable(Integer(1))+r.variable(Integer(0))), key=lambda d: sorted(d.items()))
|
|
94
|
+
[{y: 0, x: 1}, {y: 1, x: 0}]
|
|
95
|
+
"""
|
|
96
|
+
# we form an expression for a var configuration *not* lying in the
|
|
97
|
+
# block it is evaluated to 0 by f, iff it is not lying in any zero
|
|
98
|
+
# block of f+1
|
|
99
|
+
return [{variable: 1 - value for variable, value in b.items()}
|
|
100
|
+
for b in self.zero_blocks(f + 1)]
|
|
101
|
+
|
|
102
|
+
def polynomial_clauses(self, f):
|
|
103
|
+
r"""
|
|
104
|
+
|
|
105
|
+
TESTS::
|
|
106
|
+
|
|
107
|
+
sage: from sage.rings.polynomial.pbori import *
|
|
108
|
+
sage: r = declare_ring(["x", "y", "z"], dict())
|
|
109
|
+
sage: from sage.rings.polynomial.pbori.cnf import CNFEncoder
|
|
110
|
+
sage: e = CNFEncoder(r)
|
|
111
|
+
sage: e.polynomial_clauses(r.variable(0)*r.variable(1)*r.variable(2))
|
|
112
|
+
[x*y*z]
|
|
113
|
+
sage: v = r.variable
|
|
114
|
+
sage: p = v(1)*v(2)+v(2)*v(0)+1
|
|
115
|
+
sage: groebner_basis([p], heuristic = False)==groebner_basis(e.polynomial_clauses(p), heuristic = False)
|
|
116
|
+
True
|
|
117
|
+
"""
|
|
118
|
+
|
|
119
|
+
def product(l):
|
|
120
|
+
res = l[0]
|
|
121
|
+
for p in l[1:]:
|
|
122
|
+
res = res * p
|
|
123
|
+
# please care about the order of these multiplications for
|
|
124
|
+
# performance
|
|
125
|
+
return res
|
|
126
|
+
return [product([variable + value for (variable, value)
|
|
127
|
+
in b.items()]) for b in self.clauses(f)]
|
|
128
|
+
|
|
129
|
+
def to_dimacs_index(self, v):
|
|
130
|
+
return v.index() + 1
|
|
131
|
+
|
|
132
|
+
def dimacs_encode_clause(self, c):
|
|
133
|
+
def get_sign(value):
|
|
134
|
+
if value == 1:
|
|
135
|
+
return 1
|
|
136
|
+
return -1
|
|
137
|
+
|
|
138
|
+
items = sorted(c.items(), reverse=True)
|
|
139
|
+
return " ".join([str(v) for v in [
|
|
140
|
+
get_sign(value) * self.to_dimacs_index(variable)
|
|
141
|
+
for (variable, value) in items] + [0]])
|
|
142
|
+
|
|
143
|
+
def dimacs_encode_polynomial(self, p):
|
|
144
|
+
r"""
|
|
145
|
+
|
|
146
|
+
TESTS::
|
|
147
|
+
|
|
148
|
+
sage: from sage.rings.polynomial.pbori import *
|
|
149
|
+
sage: d = {}
|
|
150
|
+
sage: r = declare_ring(["x", "y", "z"], d)
|
|
151
|
+
sage: from sage.rings.polynomial.pbori.cnf import CNFEncoder
|
|
152
|
+
sage: e = CNFEncoder(r)
|
|
153
|
+
sage: sorted(e.dimacs_encode_polynomial(d["x"]+d["y"]+d["z"]))
|
|
154
|
+
['-1 -2 -3 0', '-1 2 3 0', '1 -2 3 0', '1 2 -3 0']
|
|
155
|
+
"""
|
|
156
|
+
return [self.dimacs_encode_clause(c) for c in self.clauses(p)]
|
|
157
|
+
|
|
158
|
+
def dimacs_cnf(self, polynomial_system):
|
|
159
|
+
r"""
|
|
160
|
+
|
|
161
|
+
TESTS::
|
|
162
|
+
|
|
163
|
+
sage: from sage.rings.polynomial.pbori import *
|
|
164
|
+
sage: r = declare_ring(["x", "y", "z"], dict())
|
|
165
|
+
sage: from sage.rings.polynomial.pbori.cnf import CNFEncoder
|
|
166
|
+
sage: e = CNFEncoder(r)
|
|
167
|
+
sage: e.dimacs_cnf([r.variable(0)*r.variable(1)*r.variable(2)])
|
|
168
|
+
'c cnf generated by PolyBoRi\np cnf 3 1\n-1 -2 -3 0'
|
|
169
|
+
sage: e.dimacs_cnf([r.variable(1)+r.variable(0)])
|
|
170
|
+
'c cnf generated by PolyBoRi\np cnf 3 2\n-1 2 0\n1 -2 0'
|
|
171
|
+
sage: e.dimacs_cnf([r.variable(0)*r.variable(1)*r.variable(2), r.variable(1)+r.variable(0)])
|
|
172
|
+
'c cnf generated by PolyBoRi\np cnf 3 3\n-1 -2 -3 0\n1 -2 0\n-1 2 0'
|
|
173
|
+
"""
|
|
174
|
+
clauses_list = [c for p in polynomial_system for c in self.
|
|
175
|
+
dimacs_encode_polynomial(p)]
|
|
176
|
+
res = ["c cnf generated by PolyBoRi"]
|
|
177
|
+
r = polynomial_system[0].ring()
|
|
178
|
+
n_variables = r.n_variables()
|
|
179
|
+
res.append(f"p cnf {n_variables} {len(clauses_list)}")
|
|
180
|
+
res.extend(clauses_list)
|
|
181
|
+
return "\n".join(res)
|
|
182
|
+
|
|
183
|
+
|
|
184
|
+
class CryptoMiniSatEncoder(CNFEncoder):
|
|
185
|
+
group_counter = 0
|
|
186
|
+
|
|
187
|
+
def dimacs_encode_polynomial(self, p):
|
|
188
|
+
r"""
|
|
189
|
+
|
|
190
|
+
TESTS::
|
|
191
|
+
|
|
192
|
+
sage: from sage.rings.polynomial.pbori import *
|
|
193
|
+
sage: d=dict()
|
|
194
|
+
sage: r = declare_ring(["x", "y", "z"], d)
|
|
195
|
+
sage: from sage.rings.polynomial.pbori.cnf import CryptoMiniSatEncoder
|
|
196
|
+
sage: e = CryptoMiniSatEncoder(r)
|
|
197
|
+
sage: p = d["x"]+d["y"]+d["z"]
|
|
198
|
+
sage: p.deg()
|
|
199
|
+
1
|
|
200
|
+
sage: len(p)
|
|
201
|
+
3
|
|
202
|
+
sage: e.dimacs_encode_polynomial(p)
|
|
203
|
+
['x1 2 3 0\nc g 1 x + y + z']
|
|
204
|
+
sage: e.dimacs_encode_polynomial(p+1)
|
|
205
|
+
['x1 2 -3 0\nc g 2 x + y + z + 1']
|
|
206
|
+
"""
|
|
207
|
+
if p.deg() != 1 or len(p) <= 1:
|
|
208
|
+
res = super().dimacs_encode_polynomial(p)
|
|
209
|
+
else:
|
|
210
|
+
invert_last = bool(p.has_constant_part())
|
|
211
|
+
variables = list(p.vars_as_monomial().variables())
|
|
212
|
+
indices = [self.to_dimacs_index(v) for v in variables]
|
|
213
|
+
if invert_last:
|
|
214
|
+
indices[-1] = -indices[-1]
|
|
215
|
+
indices.append(0)
|
|
216
|
+
res = ["x" + " ".join(str(v) for v in indices)]
|
|
217
|
+
self.group_counter = self.group_counter + 1
|
|
218
|
+
group_comment = f"\nc g {self.group_counter} {str(p)[:30]}"
|
|
219
|
+
return [c + group_comment for c in res]
|
|
220
|
+
|
|
221
|
+
def dimacs_cnf(self, polynomial_system):
|
|
222
|
+
r"""
|
|
223
|
+
|
|
224
|
+
TESTS::
|
|
225
|
+
|
|
226
|
+
sage: from sage.rings.polynomial.pbori import *
|
|
227
|
+
sage: r = declare_ring(["x", "y", "z"], dict())
|
|
228
|
+
sage: from sage.rings.polynomial.pbori.cnf import CryptoMiniSatEncoder
|
|
229
|
+
sage: e = CryptoMiniSatEncoder(r)
|
|
230
|
+
sage: e.dimacs_cnf([r.variable(0)*r.variable(1)*r.variable(2)])
|
|
231
|
+
'c cnf generated by PolyBoRi\np cnf 3 1\n-1 -2 -3 0\nc g 1 x*y*z\nc v 1 x\nc v 2 y\nc v 3 z'
|
|
232
|
+
sage: e.dimacs_cnf([r.variable(1)+r.variable(0)])
|
|
233
|
+
'c cnf generated by PolyBoRi\np cnf 3 1\nx1 2 0\nc g 2 x + y\nc v 1 x\nc v 2 y'
|
|
234
|
+
sage: e.dimacs_cnf([r.variable(0)*r.variable(1)*r.variable(2), r.variable(1)+r.variable(0)])
|
|
235
|
+
'c cnf generated by PolyBoRi\np cnf 3 2\n-1 -2 -3 0\nc g 3 x*y*z\nx1 2 0\nc g 4 x + y\nc v 1 x\nc v 2 y\nc v 3 z'
|
|
236
|
+
"""
|
|
237
|
+
uv = list(used_vars_set(polynomial_system).variables())
|
|
238
|
+
res = super().dimacs_cnf(polynomial_system)
|
|
239
|
+
res += "\n" + "\n".join(f"c v {self.to_dimacs_index(v)} {v}"
|
|
240
|
+
for v in uv)
|
|
241
|
+
return res
|
|
@@ -0,0 +1,59 @@
|
|
|
1
|
+
# sage_setup: distribution = sagemath-brial
|
|
2
|
+
# sage.doctest: needs sage.rings.polynomial.pbori
|
|
3
|
+
from sage.rings.polynomial.pbori.interpolate import (
|
|
4
|
+
nf_lex_points,
|
|
5
|
+
variety_lex_leading_terms,
|
|
6
|
+
)
|
|
7
|
+
from sage.rings.polynomial.pbori.pbori import easy_linear_factors
|
|
8
|
+
|
|
9
|
+
|
|
10
|
+
def easy_linear_polynomials(p):
|
|
11
|
+
r"""
|
|
12
|
+
Get linear polynomials implied by given polynomial.
|
|
13
|
+
|
|
14
|
+
EXAMPLES::
|
|
15
|
+
|
|
16
|
+
sage: from sage.rings.polynomial.pbori.frontend import x
|
|
17
|
+
sage: from sage.rings.polynomial.pbori.easy_polynomials import easy_linear_polynomials
|
|
18
|
+
sage: easy_linear_polynomials(x(1)*x(2) + 1)
|
|
19
|
+
[x(1) + 1, x(2) + 1]
|
|
20
|
+
sage: easy_linear_polynomials(x(1)*x(2) + 0)
|
|
21
|
+
[]
|
|
22
|
+
sage: easy_linear_polynomials(x(0)*x(1) + x(0)*x(2) + 1)
|
|
23
|
+
[x(0) + 1, x(1) + x(2) + 1]
|
|
24
|
+
"""
|
|
25
|
+
res = []
|
|
26
|
+
if p.deg() >= 2:
|
|
27
|
+
if p.vars_as_monomial().deg() > 8:
|
|
28
|
+
res.extend(q + 1 for q in easy_linear_factors(p + 1))
|
|
29
|
+
else:
|
|
30
|
+
res = easy_linear_polynomials_via_interpolation(p)
|
|
31
|
+
return res
|
|
32
|
+
|
|
33
|
+
|
|
34
|
+
def easy_linear_polynomials_via_interpolation(p):
|
|
35
|
+
r"""
|
|
36
|
+
Get linear polynomials implied by given polynomial using interpolation of the variety.
|
|
37
|
+
|
|
38
|
+
TESTS::
|
|
39
|
+
|
|
40
|
+
sage: from sage.rings.polynomial.pbori.frontend import x
|
|
41
|
+
sage: from sage.rings.polynomial.pbori.easy_polynomials import easy_linear_polynomials_via_interpolation
|
|
42
|
+
sage: easy_linear_polynomials_via_interpolation(x(1)*x(2) + 1)
|
|
43
|
+
[x(1) + 1, x(2) + 1]
|
|
44
|
+
sage: easy_linear_polynomials_via_interpolation(x(1)*x(2) + 0)
|
|
45
|
+
[]
|
|
46
|
+
sage: easy_linear_polynomials_via_interpolation(x(0)*x(1) + x(0)*x(2) + 1)
|
|
47
|
+
[x(0) + 1, x(1) + x(2) + 1]
|
|
48
|
+
"""
|
|
49
|
+
res = []
|
|
50
|
+
p_vars = p.vars_as_monomial()
|
|
51
|
+
space = p_vars.divisors()
|
|
52
|
+
zeros = p.zeros_in(space)
|
|
53
|
+
lex_leads = variety_lex_leading_terms(zeros, p_vars)
|
|
54
|
+
for m in lex_leads:
|
|
55
|
+
if m.deg() == 1:
|
|
56
|
+
red = m + nf_lex_points(m, zeros)
|
|
57
|
+
if red.lead_deg() == 1: # normal ordering
|
|
58
|
+
res.append(red)
|
|
59
|
+
return res
|
|
@@ -0,0 +1,93 @@
|
|
|
1
|
+
# sage_setup: distribution = sagemath-brial
|
|
2
|
+
# sage.doctest: needs sage.rings.polynomial.pbori
|
|
3
|
+
from sage.rings.polynomial.pbori.pbori import BooleSet, FGLMStrategy
|
|
4
|
+
from sage.rings.polynomial.pbori.PyPolyBoRi import BoolePolynomialVector, Polynomial
|
|
5
|
+
|
|
6
|
+
|
|
7
|
+
def _fglm(I, from_ring, to_ring):
|
|
8
|
+
r"""
|
|
9
|
+
Unchecked variant of fglm
|
|
10
|
+
"""
|
|
11
|
+
vec = BoolePolynomialVector(I)
|
|
12
|
+
return FGLMStrategy(from_ring, to_ring, vec).main()
|
|
13
|
+
|
|
14
|
+
|
|
15
|
+
def fglm(I, from_ring, to_ring):
|
|
16
|
+
r"""
|
|
17
|
+
Convert *reduced* Groebner Basis in ``from_ring`` to a GroebnerBasis
|
|
18
|
+
in ``to_ring``.
|
|
19
|
+
|
|
20
|
+
It acts independent of the global ring, which is restored at the end of the
|
|
21
|
+
computation.
|
|
22
|
+
|
|
23
|
+
TESTS::
|
|
24
|
+
|
|
25
|
+
sage: from sage.rings.polynomial.pbori import *
|
|
26
|
+
sage: from sage.rings.polynomial.pbori.PyPolyBoRi import OrderCode
|
|
27
|
+
sage: from sage.rings.polynomial.pbori.fglm import fglm
|
|
28
|
+
sage: dp_asc = OrderCode.dp_asc
|
|
29
|
+
sage: r = declare_ring(['x','y','z'],dict())
|
|
30
|
+
sage: old_ring = r
|
|
31
|
+
sage: new_ring = old_ring.clone(ordering=dp_asc)
|
|
32
|
+
sage: x,y,z = (old_ring.variable(i) for i in range(3))
|
|
33
|
+
sage: ideal = [x+z, y+z] # lp Groebner basis
|
|
34
|
+
sage: list(fglm(ideal, old_ring, new_ring))
|
|
35
|
+
[y + x, z + x]
|
|
36
|
+
"""
|
|
37
|
+
for poly in I:
|
|
38
|
+
if poly.ring().id() != from_ring.id():
|
|
39
|
+
raise ValueError("Ideal I must be from the first ring argument")
|
|
40
|
+
return _fglm(I, from_ring, to_ring)
|
|
41
|
+
|
|
42
|
+
|
|
43
|
+
def vars_real_divisors(monomial, monomial_set):
|
|
44
|
+
r"""
|
|
45
|
+
Return all elements of ``monomial_set``, which result multiplied by a variable in monomial.
|
|
46
|
+
|
|
47
|
+
EXAMPLES::
|
|
48
|
+
|
|
49
|
+
sage: from sage.rings.polynomial.pbori.pbori import *
|
|
50
|
+
sage: from sage.rings.polynomial.pbori.PyPolyBoRi import OrderCode
|
|
51
|
+
sage: dp_asc = OrderCode.dp_asc
|
|
52
|
+
sage: from sage.rings.polynomial.pbori.PyPolyBoRi import Ring
|
|
53
|
+
sage: r = Ring(1000)
|
|
54
|
+
sage: x = r.variable
|
|
55
|
+
sage: b = BooleSet([x(1)*x(2),x(2)])
|
|
56
|
+
sage: from sage.rings.polynomial.pbori.fglm import vars_real_divisors
|
|
57
|
+
sage: vars_real_divisors(x(1)*x(2)*x(3),b)
|
|
58
|
+
{{x(1),x(2)}}
|
|
59
|
+
"""
|
|
60
|
+
return BooleSet(Polynomial(monomial_set.divisors_of(monomial)).
|
|
61
|
+
graded_part(monomial.deg() - 1))
|
|
62
|
+
|
|
63
|
+
|
|
64
|
+
def m_k_plus_one(completed_elements, variables):
|
|
65
|
+
r"""
|
|
66
|
+
Calculate `m_{k+1}` from the FGLM algorithm.
|
|
67
|
+
|
|
68
|
+
Calculate `m_{k+1}` from the FGLM algorithm as described in Wichmann [Wich1997]_.
|
|
69
|
+
|
|
70
|
+
.. NOTE::
|
|
71
|
+
|
|
72
|
+
It would be nice to be able to efficiently extract the smallest term of a polynomial.
|
|
73
|
+
|
|
74
|
+
EXAMPLES::
|
|
75
|
+
|
|
76
|
+
sage: from sage.rings.polynomial.pbori.pbori import *
|
|
77
|
+
sage: from sage.rings.polynomial.pbori.PyPolyBoRi import OrderCode
|
|
78
|
+
sage: from sage.rings.polynomial.pbori.fglm import m_k_plus_one
|
|
79
|
+
sage: dp_asc = OrderCode.dp_asc
|
|
80
|
+
sage: from sage.rings.polynomial.pbori.PyPolyBoRi import Ring
|
|
81
|
+
sage: r = Ring(1000)
|
|
82
|
+
sage: x = r.variable
|
|
83
|
+
sage: from sage.rings.polynomial.pbori.PyPolyBoRi import Monomial
|
|
84
|
+
sage: s = BooleSet([x(1)*x(2),x(1),x(2),Monomial(r),x(3)])
|
|
85
|
+
sage: variables = BooleSet([x(1),x(2),x(3)])
|
|
86
|
+
sage: m_k_plus_one(s,variables)
|
|
87
|
+
x(2)*x(3)
|
|
88
|
+
sage: r2 = r.clone(ordering=dp_asc)
|
|
89
|
+
sage: m_k_plus_one(r2(s).set(),r2(variables).set())
|
|
90
|
+
x(1)*x(3)
|
|
91
|
+
"""
|
|
92
|
+
return sorted(completed_elements.cartesian_product(variables).diff(
|
|
93
|
+
completed_elements))[0]
|
|
@@ -0,0 +1,70 @@
|
|
|
1
|
+
# sage_setup: distribution = sagemath-brial
|
|
2
|
+
# sage.doctest: needs sage.rings.polynomial.pbori
|
|
3
|
+
# Import basic functionality
|
|
4
|
+
r"""
|
|
5
|
+
This module defines an initial ring, and patches the declare_ring to use
|
|
6
|
+
a given context.
|
|
7
|
+
|
|
8
|
+
EXAMPLES::
|
|
9
|
+
|
|
10
|
+
sage: from sage.rings.polynomial.pbori.frontend import x
|
|
11
|
+
sage: x(0)
|
|
12
|
+
x(0)
|
|
13
|
+
sage: x(0)*x(0)
|
|
14
|
+
x(0)
|
|
15
|
+
sage: x(0) + x(0)
|
|
16
|
+
0
|
|
17
|
+
sage: x(9999)
|
|
18
|
+
x(9999)
|
|
19
|
+
sage: x(9999)*x(9999)
|
|
20
|
+
x(9999)
|
|
21
|
+
sage: x(9999) + x(9999)
|
|
22
|
+
0
|
|
23
|
+
|
|
24
|
+
sage: from sage.rings.polynomial.pbori.frontend import x, polybori_start
|
|
25
|
+
sage: context = dict(globals())
|
|
26
|
+
sage: polybori_start(context)
|
|
27
|
+
ipbori...
|
|
28
|
+
sage: r = context['declare_ring']('abc')
|
|
29
|
+
sage: context['a']
|
|
30
|
+
a
|
|
31
|
+
sage: r.variable(0)
|
|
32
|
+
a
|
|
33
|
+
"""
|
|
34
|
+
|
|
35
|
+
|
|
36
|
+
from sage.rings.polynomial.pbori.blocks import declare_ring as orig_declare_ring
|
|
37
|
+
from sage.rings.polynomial.pbori.pbori import VariableFactory
|
|
38
|
+
from sage.rings.polynomial.pbori.PyPolyBoRi import Ring
|
|
39
|
+
|
|
40
|
+
|
|
41
|
+
def block_scheme_names(blocks):
|
|
42
|
+
r"""
|
|
43
|
+
Helper for Singular interface.
|
|
44
|
+
"""
|
|
45
|
+
context = {}
|
|
46
|
+
from .blocks import declare_block_scheme
|
|
47
|
+
declare_block_scheme(blocks, context)
|
|
48
|
+
|
|
49
|
+
return list(context.keys())
|
|
50
|
+
|
|
51
|
+
|
|
52
|
+
ipbname = 'ipbori'
|
|
53
|
+
|
|
54
|
+
|
|
55
|
+
def polybori_start(global_context):
|
|
56
|
+
def declare_ring(blocks, context=None):
|
|
57
|
+
if context is None:
|
|
58
|
+
context = global_context
|
|
59
|
+
|
|
60
|
+
return orig_declare_ring(blocks, context)
|
|
61
|
+
declare_ring.__doc__ = orig_declare_ring.__doc__
|
|
62
|
+
global_context["declare_ring"] = declare_ring
|
|
63
|
+
|
|
64
|
+
print(ipbname + """ -- The interactive command line tool of PolyBoRi/BRiAL %s
|
|
65
|
+
""" % global_context.get("polybori_version", ''))
|
|
66
|
+
|
|
67
|
+
|
|
68
|
+
# Here come the defaults
|
|
69
|
+
r = Ring(10000)
|
|
70
|
+
x = VariableFactory(r)
|