I am done

This commit is contained in:
2024-10-30 22:14:35 +01:00
parent 720dc28c09
commit 40e2a747cf
36901 changed files with 5011519 additions and 0 deletions

View File

@ -0,0 +1,196 @@
from sympy.core.symbol import symbols
from sympy.functions.elementary.trigonometric import (cos, sin)
from sympy.polys import QQ, ZZ
from sympy.polys.polytools import Poly
from sympy.polys.polyerrors import NotInvertible
from sympy.polys.agca.extensions import FiniteExtension
from sympy.polys.domainmatrix import DomainMatrix
from sympy.testing.pytest import raises
from sympy.abc import x, y, t
def test_FiniteExtension():
# Gaussian integers
A = FiniteExtension(Poly(x**2 + 1, x))
assert A.rank == 2
assert str(A) == 'ZZ[x]/(x**2 + 1)'
i = A.generator
assert i.parent() is A
assert i*i == A(-1)
raises(TypeError, lambda: i*())
assert A.basis == (A.one, i)
assert A(1) == A.one
assert i**2 == A(-1)
assert i**2 != -1 # no coercion
assert (2 + i)*(1 - i) == 3 - i
assert (1 + i)**8 == A(16)
assert A(1).inverse() == A(1)
raises(NotImplementedError, lambda: A(2).inverse())
# Finite field of order 27
F = FiniteExtension(Poly(x**3 - x + 1, x, modulus=3))
assert F.rank == 3
a = F.generator # also generates the cyclic group F - {0}
assert F.basis == (F(1), a, a**2)
assert a**27 == a
assert a**26 == F(1)
assert a**13 == F(-1)
assert a**9 == a + 1
assert a**3 == a - 1
assert a**6 == a**2 + a + 1
assert F(x**2 + x).inverse() == 1 - a
assert F(x + 2)**(-1) == F(x + 2).inverse()
assert a**19 * a**(-19) == F(1)
assert (a - 1) / (2*a**2 - 1) == a**2 + 1
assert (a - 1) // (2*a**2 - 1) == a**2 + 1
assert 2/(a**2 + 1) == a**2 - a + 1
assert (a**2 + 1)/2 == -a**2 - 1
raises(NotInvertible, lambda: F(0).inverse())
# Function field of an elliptic curve
K = FiniteExtension(Poly(t**2 - x**3 - x + 1, t, field=True))
assert K.rank == 2
assert str(K) == 'ZZ(x)[t]/(t**2 - x**3 - x + 1)'
y = K.generator
c = 1/(x**3 - x**2 + x - 1)
assert ((y + x)*(y - x)).inverse() == K(c)
assert (y + x)*(y - x)*c == K(1) # explicit inverse of y + x
def test_FiniteExtension_eq_hash():
# Test eq and hash
p1 = Poly(x**2 - 2, x, domain=ZZ)
p2 = Poly(x**2 - 2, x, domain=QQ)
K1 = FiniteExtension(p1)
K2 = FiniteExtension(p2)
assert K1 == FiniteExtension(Poly(x**2 - 2))
assert K2 != FiniteExtension(Poly(x**2 - 2))
assert len({K1, K2, FiniteExtension(p1)}) == 2
def test_FiniteExtension_mod():
# Test mod
K = FiniteExtension(Poly(x**3 + 1, x, domain=QQ))
xf = K(x)
assert (xf**2 - 1) % 1 == K.zero
assert 1 % (xf**2 - 1) == K.zero
assert (xf**2 - 1) / (xf - 1) == xf + 1
assert (xf**2 - 1) // (xf - 1) == xf + 1
assert (xf**2 - 1) % (xf - 1) == K.zero
raises(ZeroDivisionError, lambda: (xf**2 - 1) % 0)
raises(TypeError, lambda: xf % [])
raises(TypeError, lambda: [] % xf)
# Test mod over ring
K = FiniteExtension(Poly(x**3 + 1, x, domain=ZZ))
xf = K(x)
assert (xf**2 - 1) % 1 == K.zero
raises(NotImplementedError, lambda: (xf**2 - 1) % (xf - 1))
def test_FiniteExtension_from_sympy():
# Test to_sympy/from_sympy
K = FiniteExtension(Poly(x**3 + 1, x, domain=ZZ))
xf = K(x)
assert K.from_sympy(x) == xf
assert K.to_sympy(xf) == x
def test_FiniteExtension_set_domain():
KZ = FiniteExtension(Poly(x**2 + 1, x, domain='ZZ'))
KQ = FiniteExtension(Poly(x**2 + 1, x, domain='QQ'))
assert KZ.set_domain(QQ) == KQ
def test_FiniteExtension_exquo():
# Test exquo
K = FiniteExtension(Poly(x**4 + 1))
xf = K(x)
assert K.exquo(xf**2 - 1, xf - 1) == xf + 1
def test_FiniteExtension_convert():
# Test from_MonogenicFiniteExtension
K1 = FiniteExtension(Poly(x**2 + 1))
K2 = QQ[x]
x1, x2 = K1(x), K2(x)
assert K1.convert(x2) == x1
assert K2.convert(x1) == x2
K = FiniteExtension(Poly(x**2 - 1, domain=QQ))
assert K.convert_from(QQ(1, 2), QQ) == K.one/2
def test_FiniteExtension_division_ring():
# Test division in FiniteExtension over a ring
KQ = FiniteExtension(Poly(x**2 - 1, x, domain=QQ))
KZ = FiniteExtension(Poly(x**2 - 1, x, domain=ZZ))
KQt = FiniteExtension(Poly(x**2 - 1, x, domain=QQ[t]))
KQtf = FiniteExtension(Poly(x**2 - 1, x, domain=QQ.frac_field(t)))
assert KQ.is_Field is True
assert KZ.is_Field is False
assert KQt.is_Field is False
assert KQtf.is_Field is True
for K in KQ, KZ, KQt, KQtf:
xK = K.convert(x)
assert xK / K.one == xK
assert xK // K.one == xK
assert xK % K.one == K.zero
raises(ZeroDivisionError, lambda: xK / K.zero)
raises(ZeroDivisionError, lambda: xK // K.zero)
raises(ZeroDivisionError, lambda: xK % K.zero)
if K.is_Field:
assert xK / xK == K.one
assert xK // xK == K.one
assert xK % xK == K.zero
else:
raises(NotImplementedError, lambda: xK / xK)
raises(NotImplementedError, lambda: xK // xK)
raises(NotImplementedError, lambda: xK % xK)
def test_FiniteExtension_Poly():
K = FiniteExtension(Poly(x**2 - 2))
p = Poly(x, y, domain=K)
assert p.domain == K
assert p.as_expr() == x
assert (p**2).as_expr() == 2
K = FiniteExtension(Poly(x**2 - 2, x, domain=QQ))
K2 = FiniteExtension(Poly(t**2 - 2, t, domain=K))
assert str(K2) == 'QQ[x]/(x**2 - 2)[t]/(t**2 - 2)'
eK = K2.convert(x + t)
assert K2.to_sympy(eK) == x + t
assert K2.to_sympy(eK ** 2) == 4 + 2*x*t
p = Poly(x + t, y, domain=K2)
assert p**2 == Poly(4 + 2*x*t, y, domain=K2)
def test_FiniteExtension_sincos_jacobian():
# Use FiniteExtensino to compute the Jacobian of a matrix involving sin
# and cos of different symbols.
r, p, t = symbols('rho, phi, theta')
elements = [
[sin(p)*cos(t), r*cos(p)*cos(t), -r*sin(p)*sin(t)],
[sin(p)*sin(t), r*cos(p)*sin(t), r*sin(p)*cos(t)],
[ cos(p), -r*sin(p), 0],
]
def make_extension(K):
K = FiniteExtension(Poly(sin(p)**2+cos(p)**2-1, sin(p), domain=K[cos(p)]))
K = FiniteExtension(Poly(sin(t)**2+cos(t)**2-1, sin(t), domain=K[cos(t)]))
return K
Ksc1 = make_extension(ZZ[r])
Ksc2 = make_extension(ZZ)[r]
for K in [Ksc1, Ksc2]:
elements_K = [[K.convert(e) for e in row] for row in elements]
J = DomainMatrix(elements_K, (3, 3), K)
det = J.charpoly()[-1] * (-K.one)**3
assert det == K.convert(r**2*sin(p))

View File

@ -0,0 +1,113 @@
"""Tests for homomorphisms."""
from sympy.core.singleton import S
from sympy.polys.domains.rationalfield import QQ
from sympy.abc import x, y
from sympy.polys.agca import homomorphism
from sympy.testing.pytest import raises
def test_printing():
R = QQ.old_poly_ring(x)
assert str(homomorphism(R.free_module(1), R.free_module(1), [0])) == \
'Matrix([[0]]) : QQ[x]**1 -> QQ[x]**1'
assert str(homomorphism(R.free_module(2), R.free_module(2), [0, 0])) == \
'Matrix([ \n[0, 0], : QQ[x]**2 -> QQ[x]**2\n[0, 0]]) '
assert str(homomorphism(R.free_module(1), R.free_module(1) / [[x]], [0])) == \
'Matrix([[0]]) : QQ[x]**1 -> QQ[x]**1/<[x]>'
assert str(R.free_module(0).identity_hom()) == 'Matrix(0, 0, []) : QQ[x]**0 -> QQ[x]**0'
def test_operations():
F = QQ.old_poly_ring(x).free_module(2)
G = QQ.old_poly_ring(x).free_module(3)
f = F.identity_hom()
g = homomorphism(F, F, [0, [1, x]])
h = homomorphism(F, F, [[1, 0], 0])
i = homomorphism(F, G, [[1, 0, 0], [0, 1, 0]])
assert f == f
assert f != g
assert f != i
assert (f != F.identity_hom()) is False
assert 2*f == f*2 == homomorphism(F, F, [[2, 0], [0, 2]])
assert f/2 == homomorphism(F, F, [[S.Half, 0], [0, S.Half]])
assert f + g == homomorphism(F, F, [[1, 0], [1, x + 1]])
assert f - g == homomorphism(F, F, [[1, 0], [-1, 1 - x]])
assert f*g == g == g*f
assert h*g == homomorphism(F, F, [0, [1, 0]])
assert g*h == homomorphism(F, F, [0, 0])
assert i*f == i
assert f([1, 2]) == [1, 2]
assert g([1, 2]) == [2, 2*x]
assert i.restrict_domain(F.submodule([x, x]))([x, x]) == i([x, x])
h1 = h.quotient_domain(F.submodule([0, 1]))
assert h1([1, 0]) == h([1, 0])
assert h1.restrict_domain(h1.domain.submodule([x, 0]))([x, 0]) == h([x, 0])
raises(TypeError, lambda: f/g)
raises(TypeError, lambda: f + 1)
raises(TypeError, lambda: f + i)
raises(TypeError, lambda: f - 1)
raises(TypeError, lambda: f*i)
def test_creation():
F = QQ.old_poly_ring(x).free_module(3)
G = QQ.old_poly_ring(x).free_module(2)
SM = F.submodule([1, 1, 1])
Q = F / SM
SQ = Q.submodule([1, 0, 0])
matrix = [[1, 0], [0, 1], [-1, -1]]
h = homomorphism(F, G, matrix)
h2 = homomorphism(Q, G, matrix)
assert h.quotient_domain(SM) == h2
raises(ValueError, lambda: h.quotient_domain(F.submodule([1, 0, 0])))
assert h2.restrict_domain(SQ) == homomorphism(SQ, G, matrix)
raises(ValueError, lambda: h.restrict_domain(G))
raises(ValueError, lambda: h.restrict_codomain(G.submodule([1, 0])))
raises(ValueError, lambda: h.quotient_codomain(F))
im = [[1, 0, 0], [0, 1, 0], [0, 0, 1]]
for M in [F, SM, Q, SQ]:
assert M.identity_hom() == homomorphism(M, M, im)
assert SM.inclusion_hom() == homomorphism(SM, F, im)
assert SQ.inclusion_hom() == homomorphism(SQ, Q, im)
assert Q.quotient_hom() == homomorphism(F, Q, im)
assert SQ.quotient_hom() == homomorphism(SQ.base, SQ, im)
class conv:
def convert(x, y=None):
return x
class dummy:
container = conv()
def submodule(*args):
return None
raises(TypeError, lambda: homomorphism(dummy(), G, matrix))
raises(TypeError, lambda: homomorphism(F, dummy(), matrix))
raises(
ValueError, lambda: homomorphism(QQ.old_poly_ring(x, y).free_module(3), G, matrix))
raises(ValueError, lambda: homomorphism(F, G, [0, 0]))
def test_properties():
R = QQ.old_poly_ring(x, y)
F = R.free_module(2)
h = homomorphism(F, F, [[x, 0], [y, 0]])
assert h.kernel() == F.submodule([-y, x])
assert h.image() == F.submodule([x, 0], [y, 0])
assert not h.is_injective()
assert not h.is_surjective()
assert h.restrict_codomain(h.image()).is_surjective()
assert h.restrict_domain(F.submodule([1, 0])).is_injective()
assert h.quotient_domain(
h.kernel()).restrict_codomain(h.image()).is_isomorphism()
R2 = QQ.old_poly_ring(x, y, order=(("lex", x), ("ilex", y))) / [x**2 + 1]
F = R2.free_module(2)
h = homomorphism(F, F, [[x, 0], [y, y + 1]])
assert h.is_isomorphism()

View File

@ -0,0 +1,131 @@
"""Test ideals.py code."""
from sympy.polys import QQ, ilex
from sympy.abc import x, y, z
from sympy.testing.pytest import raises
def test_ideal_operations():
R = QQ.old_poly_ring(x, y)
I = R.ideal(x)
J = R.ideal(y)
S = R.ideal(x*y)
T = R.ideal(x, y)
assert not (I == J)
assert I == I
assert I.union(J) == T
assert I + J == T
assert I + T == T
assert not I.subset(T)
assert T.subset(I)
assert I.product(J) == S
assert I*J == S
assert x*J == S
assert I*y == S
assert R.convert(x)*J == S
assert I*R.convert(y) == S
assert not I.is_zero()
assert not J.is_whole_ring()
assert R.ideal(x**2 + 1, x).is_whole_ring()
assert R.ideal() == R.ideal(0)
assert R.ideal().is_zero()
assert T.contains(x*y)
assert T.subset([x, y])
assert T.in_terms_of_generators(x) == [R(1), R(0)]
assert T**0 == R.ideal(1)
assert T**1 == T
assert T**2 == R.ideal(x**2, y**2, x*y)
assert I**5 == R.ideal(x**5)
def test_exceptions():
I = QQ.old_poly_ring(x).ideal(x)
J = QQ.old_poly_ring(y).ideal(1)
raises(ValueError, lambda: I.union(x))
raises(ValueError, lambda: I + J)
raises(ValueError, lambda: I * J)
raises(ValueError, lambda: I.union(J))
assert (I == J) is False
assert I != J
def test_nontriv_global():
R = QQ.old_poly_ring(x, y, z)
def contains(I, f):
return R.ideal(*I).contains(f)
assert contains([x, y], x)
assert contains([x, y], x + y)
assert not contains([x, y], 1)
assert not contains([x, y], z)
assert contains([x**2 + y, x**2 + x], x - y)
assert not contains([x + y + z, x*y + x*z + y*z, x*y*z], x**2)
assert contains([x + y + z, x*y + x*z + y*z, x*y*z], x**3)
assert contains([x + y + z, x*y + x*z + y*z, x*y*z], x**4)
assert not contains([x + y + z, x*y + x*z + y*z, x*y*z], x*y**2)
assert contains([x + y + z, x*y + x*z + y*z, x*y*z], x**4 + y**3 + 2*z*y*x)
assert contains([x + y + z, x*y + x*z + y*z, x*y*z], x*y*z)
assert contains([x, 1 + x + y, 5 - 7*y], 1)
assert contains(
[x**3 + y**3, y**3 + z**3, z**3 + x**3, x**2*y + x**2*z + y**2*z],
x**3)
assert not contains(
[x**3 + y**3, y**3 + z**3, z**3 + x**3, x**2*y + x**2*z + y**2*z],
x**2 + y**2)
# compare local order
assert not contains([x*(1 + x + y), y*(1 + z)], x)
assert not contains([x*(1 + x + y), y*(1 + z)], x + y)
def test_nontriv_local():
R = QQ.old_poly_ring(x, y, z, order=ilex)
def contains(I, f):
return R.ideal(*I).contains(f)
assert contains([x, y], x)
assert contains([x, y], x + y)
assert not contains([x, y], 1)
assert not contains([x, y], z)
assert contains([x**2 + y, x**2 + x], x - y)
assert not contains([x + y + z, x*y + x*z + y*z, x*y*z], x**2)
assert contains([x*(1 + x + y), y*(1 + z)], x)
assert contains([x*(1 + x + y), y*(1 + z)], x + y)
def test_intersection():
R = QQ.old_poly_ring(x, y, z)
# SCA, example 1.8.11
assert R.ideal(x, y).intersect(R.ideal(y**2, z)) == R.ideal(y**2, y*z, x*z)
assert R.ideal(x, y).intersect(R.ideal()).is_zero()
R = QQ.old_poly_ring(x, y, z, order="ilex")
assert R.ideal(x, y).intersect(R.ideal(y**2 + y**2*z, z + z*x**3*y)) == \
R.ideal(y**2, y*z, x*z)
def test_quotient():
# SCA, example 1.8.13
R = QQ.old_poly_ring(x, y, z)
assert R.ideal(x, y).quotient(R.ideal(y**2, z)) == R.ideal(x, y)
def test_reduction():
from sympy.polys.distributedmodules import sdm_nf_buchberger_reduced
R = QQ.old_poly_ring(x, y)
I = R.ideal(x**5, y)
e = R.convert(x**3 + y**2)
assert I.reduce_element(e) == e
assert I.reduce_element(e, NF=sdm_nf_buchberger_reduced) == R.convert(x**3)

View File

@ -0,0 +1,408 @@
"""Test modules.py code."""
from sympy.polys.agca.modules import FreeModule, ModuleOrder, FreeModulePolyRing
from sympy.polys import CoercionFailed, QQ, lex, grlex, ilex, ZZ
from sympy.abc import x, y, z
from sympy.testing.pytest import raises
from sympy.core.numbers import Rational
def test_FreeModuleElement():
M = QQ.old_poly_ring(x).free_module(3)
e = M.convert([1, x, x**2])
f = [QQ.old_poly_ring(x).convert(1), QQ.old_poly_ring(x).convert(x), QQ.old_poly_ring(x).convert(x**2)]
assert list(e) == f
assert f[0] == e[0]
assert f[1] == e[1]
assert f[2] == e[2]
raises(IndexError, lambda: e[3])
g = M.convert([x, 0, 0])
assert e + g == M.convert([x + 1, x, x**2])
assert f + g == M.convert([x + 1, x, x**2])
assert -e == M.convert([-1, -x, -x**2])
assert e - g == M.convert([1 - x, x, x**2])
assert e != g
assert M.convert([x, x, x]) / QQ.old_poly_ring(x).convert(x) == [1, 1, 1]
R = QQ.old_poly_ring(x, order="ilex")
assert R.free_module(1).convert([x]) / R.convert(x) == [1]
def test_FreeModule():
M1 = FreeModule(QQ.old_poly_ring(x), 2)
assert M1 == FreeModule(QQ.old_poly_ring(x), 2)
assert M1 != FreeModule(QQ.old_poly_ring(y), 2)
assert M1 != FreeModule(QQ.old_poly_ring(x), 3)
M2 = FreeModule(QQ.old_poly_ring(x, order="ilex"), 2)
assert [x, 1] in M1
assert [x] not in M1
assert [2, y] not in M1
assert [1/(x + 1), 2] not in M1
e = M1.convert([x, x**2 + 1])
X = QQ.old_poly_ring(x).convert(x)
assert e == [X, X**2 + 1]
assert e == [x, x**2 + 1]
assert 2*e == [2*x, 2*x**2 + 2]
assert e*2 == [2*x, 2*x**2 + 2]
assert e/2 == [x/2, (x**2 + 1)/2]
assert x*e == [x**2, x**3 + x]
assert e*x == [x**2, x**3 + x]
assert X*e == [x**2, x**3 + x]
assert e*X == [x**2, x**3 + x]
assert [x, 1] in M2
assert [x] not in M2
assert [2, y] not in M2
assert [1/(x + 1), 2] in M2
e = M2.convert([x, x**2 + 1])
X = QQ.old_poly_ring(x, order="ilex").convert(x)
assert e == [X, X**2 + 1]
assert e == [x, x**2 + 1]
assert 2*e == [2*x, 2*x**2 + 2]
assert e*2 == [2*x, 2*x**2 + 2]
assert e/2 == [x/2, (x**2 + 1)/2]
assert x*e == [x**2, x**3 + x]
assert e*x == [x**2, x**3 + x]
assert e/(1 + x) == [x/(1 + x), (x**2 + 1)/(1 + x)]
assert X*e == [x**2, x**3 + x]
assert e*X == [x**2, x**3 + x]
M3 = FreeModule(QQ.old_poly_ring(x, y), 2)
assert M3.convert(e) == M3.convert([x, x**2 + 1])
assert not M3.is_submodule(0)
assert not M3.is_zero()
raises(NotImplementedError, lambda: ZZ.old_poly_ring(x).free_module(2))
raises(NotImplementedError, lambda: FreeModulePolyRing(ZZ, 2))
raises(CoercionFailed, lambda: M1.convert(QQ.old_poly_ring(x).free_module(3)
.convert([1, 2, 3])))
raises(CoercionFailed, lambda: M3.convert(1))
def test_ModuleOrder():
o1 = ModuleOrder(lex, grlex, False)
o2 = ModuleOrder(ilex, lex, False)
assert o1 == ModuleOrder(lex, grlex, False)
assert (o1 != ModuleOrder(lex, grlex, False)) is False
assert o1 != o2
assert o1((1, 2, 3)) == (1, (5, (2, 3)))
assert o2((1, 2, 3)) == (-1, (2, 3))
def test_SubModulePolyRing_global():
R = QQ.old_poly_ring(x, y)
F = R.free_module(3)
Fd = F.submodule([1, 0, 0], [1, 2, 0], [1, 2, 3])
M = F.submodule([x**2 + y**2, 1, 0], [x, y, 1])
assert F == Fd
assert Fd == F
assert F != M
assert M != F
assert Fd != M
assert M != Fd
assert Fd == F.submodule(*F.basis())
assert Fd.is_full_module()
assert not M.is_full_module()
assert not Fd.is_zero()
assert not M.is_zero()
assert Fd.submodule().is_zero()
assert M.contains([x**2 + y**2 + x, 1 + y, 1])
assert not M.contains([x**2 + y**2 + x, 1 + y, 2])
assert M.contains([y**2, 1 - x*y, -x])
assert not F.submodule([1 + x, 0, 0]) == F.submodule([1, 0, 0])
assert F.submodule([1, 0, 0], [0, 1, 0]).union(F.submodule([0, 0, 1])) == F
assert not M.is_submodule(0)
m = F.convert([x**2 + y**2, 1, 0])
n = M.convert(m)
assert m.module is F
assert n.module is M
raises(ValueError, lambda: M.submodule([1, 0, 0]))
raises(TypeError, lambda: M.union(1))
raises(ValueError, lambda: M.union(R.free_module(1).submodule([x])))
assert F.submodule([x, x, x]) != F.submodule([x, x, x], order="ilex")
def test_SubModulePolyRing_local():
R = QQ.old_poly_ring(x, y, order=ilex)
F = R.free_module(3)
Fd = F.submodule([1 + x, 0, 0], [1 + y, 2 + 2*y, 0], [1, 2, 3])
M = F.submodule([x**2 + y**2, 1, 0], [x, y, 1])
assert F == Fd
assert Fd == F
assert F != M
assert M != F
assert Fd != M
assert M != Fd
assert Fd == F.submodule(*F.basis())
assert Fd.is_full_module()
assert not M.is_full_module()
assert not Fd.is_zero()
assert not M.is_zero()
assert Fd.submodule().is_zero()
assert M.contains([x**2 + y**2 + x, 1 + y, 1])
assert not M.contains([x**2 + y**2 + x, 1 + y, 2])
assert M.contains([y**2, 1 - x*y, -x])
assert F.submodule([1 + x, 0, 0]) == F.submodule([1, 0, 0])
assert F.submodule(
[1, 0, 0], [0, 1, 0]).union(F.submodule([0, 0, 1 + x*y])) == F
raises(ValueError, lambda: M.submodule([1, 0, 0]))
def test_SubModulePolyRing_nontriv_global():
R = QQ.old_poly_ring(x, y, z)
F = R.free_module(1)
def contains(I, f):
return F.submodule(*[[g] for g in I]).contains([f])
assert contains([x, y], x)
assert contains([x, y], x + y)
assert not contains([x, y], 1)
assert not contains([x, y], z)
assert contains([x**2 + y, x**2 + x], x - y)
assert not contains([x + y + z, x*y + x*z + y*z, x*y*z], x**2)
assert contains([x + y + z, x*y + x*z + y*z, x*y*z], x**3)
assert contains([x + y + z, x*y + x*z + y*z, x*y*z], x**4)
assert not contains([x + y + z, x*y + x*z + y*z, x*y*z], x*y**2)
assert contains([x + y + z, x*y + x*z + y*z, x*y*z], x**4 + y**3 + 2*z*y*x)
assert contains([x + y + z, x*y + x*z + y*z, x*y*z], x*y*z)
assert contains([x, 1 + x + y, 5 - 7*y], 1)
assert contains(
[x**3 + y**3, y**3 + z**3, z**3 + x**3, x**2*y + x**2*z + y**2*z],
x**3)
assert not contains(
[x**3 + y**3, y**3 + z**3, z**3 + x**3, x**2*y + x**2*z + y**2*z],
x**2 + y**2)
# compare local order
assert not contains([x*(1 + x + y), y*(1 + z)], x)
assert not contains([x*(1 + x + y), y*(1 + z)], x + y)
def test_SubModulePolyRing_nontriv_local():
R = QQ.old_poly_ring(x, y, z, order=ilex)
F = R.free_module(1)
def contains(I, f):
return F.submodule(*[[g] for g in I]).contains([f])
assert contains([x, y], x)
assert contains([x, y], x + y)
assert not contains([x, y], 1)
assert not contains([x, y], z)
assert contains([x**2 + y, x**2 + x], x - y)
assert not contains([x + y + z, x*y + x*z + y*z, x*y*z], x**2)
assert contains([x*(1 + x + y), y*(1 + z)], x)
assert contains([x*(1 + x + y), y*(1 + z)], x + y)
def test_syzygy():
R = QQ.old_poly_ring(x, y, z)
M = R.free_module(1).submodule([x*y], [y*z], [x*z])
S = R.free_module(3).submodule([0, x, -y], [z, -x, 0])
assert M.syzygy_module() == S
M2 = M / ([x*y*z],)
S2 = R.free_module(3).submodule([z, 0, 0], [0, x, 0], [0, 0, y])
assert M2.syzygy_module() == S2
F = R.free_module(3)
assert F.submodule(*F.basis()).syzygy_module() == F.submodule()
R2 = QQ.old_poly_ring(x, y, z) / [x*y*z]
M3 = R2.free_module(1).submodule([x*y], [y*z], [x*z])
S3 = R2.free_module(3).submodule([z, 0, 0], [0, x, 0], [0, 0, y])
assert M3.syzygy_module() == S3
def test_in_terms_of_generators():
R = QQ.old_poly_ring(x, order="ilex")
M = R.free_module(2).submodule([2*x, 0], [1, 2])
assert M.in_terms_of_generators(
[x, x]) == [R.convert(Rational(1, 4)), R.convert(x/2)]
raises(ValueError, lambda: M.in_terms_of_generators([1, 0]))
M = R.free_module(2) / ([x, 0], [1, 1])
SM = M.submodule([1, x])
assert SM.in_terms_of_generators([2, 0]) == [R.convert(-2/(x - 1))]
R = QQ.old_poly_ring(x, y) / [x**2 - y**2]
M = R.free_module(2)
SM = M.submodule([x, 0], [0, y])
assert SM.in_terms_of_generators(
[x**2, x**2]) == [R.convert(x), R.convert(y)]
def test_QuotientModuleElement():
R = QQ.old_poly_ring(x)
F = R.free_module(3)
N = F.submodule([1, x, x**2])
M = F/N
e = M.convert([x**2, 2, 0])
assert M.convert([x + 1, x**2 + x, x**3 + x**2]) == 0
assert e == [x**2, 2, 0] + N == F.convert([x**2, 2, 0]) + N == \
M.convert(F.convert([x**2, 2, 0]))
assert M.convert([x**2 + 1, 2*x + 2, x**2]) == e + [0, x, 0] == \
e + M.convert([0, x, 0]) == e + F.convert([0, x, 0])
assert M.convert([x**2 + 1, 2, x**2]) == e - [0, x, 0] == \
e - M.convert([0, x, 0]) == e - F.convert([0, x, 0])
assert M.convert([0, 2, 0]) == M.convert([x**2, 4, 0]) - e == \
[x**2, 4, 0] - e == F.convert([x**2, 4, 0]) - e
assert M.convert([x**3 + x**2, 2*x + 2, 0]) == (1 + x)*e == \
R.convert(1 + x)*e == e*(1 + x) == e*R.convert(1 + x)
assert -e == [-x**2, -2, 0]
f = [x, x, 0] + N
assert M.convert([1, 1, 0]) == f / x == f / R.convert(x)
M2 = F/[(2, 2*x, 2*x**2), (0, 0, 1)]
G = R.free_module(2)
M3 = G/[[1, x]]
M4 = F.submodule([1, x, x**2], [1, 0, 0]) / N
raises(CoercionFailed, lambda: M.convert(G.convert([1, x])))
raises(CoercionFailed, lambda: M.convert(M3.convert([1, x])))
raises(CoercionFailed, lambda: M.convert(M2.convert([1, x, x])))
assert M2.convert(M.convert([2, x, x**2])) == [2, x, 0]
assert M.convert(M4.convert([2, 0, 0])) == [2, 0, 0]
def test_QuotientModule():
R = QQ.old_poly_ring(x)
F = R.free_module(3)
N = F.submodule([1, x, x**2])
M = F/N
assert M != F
assert M != N
assert M == F / [(1, x, x**2)]
assert not M.is_zero()
assert (F / F.basis()).is_zero()
SQ = F.submodule([1, x, x**2], [2, 0, 0]) / N
assert SQ == M.submodule([2, x, x**2])
assert SQ != M.submodule([2, 1, 0])
assert SQ != M
assert M.is_submodule(SQ)
assert not SQ.is_full_module()
raises(ValueError, lambda: N/F)
raises(ValueError, lambda: F.submodule([2, 0, 0]) / N)
raises(ValueError, lambda: R.free_module(2)/F)
raises(CoercionFailed, lambda: F.convert(M.convert([1, x, x**2])))
M1 = F / [[1, 1, 1]]
M2 = M1.submodule([1, 0, 0], [0, 1, 0])
assert M1 == M2
def test_ModulesQuotientRing():
R = QQ.old_poly_ring(x, y, order=(("lex", x), ("ilex", y))) / [x**2 + 1]
M1 = R.free_module(2)
assert M1 == R.free_module(2)
assert M1 != QQ.old_poly_ring(x).free_module(2)
assert M1 != R.free_module(3)
assert [x, 1] in M1
assert [x] not in M1
assert [1/(R.convert(x) + 1), 2] in M1
assert [1, 2/(1 + y)] in M1
assert [1, 2/y] not in M1
assert M1.convert([x**2, y]) == [-1, y]
F = R.free_module(3)
Fd = F.submodule([x**2, 0, 0], [1, 2, 0], [1, 2, 3])
M = F.submodule([x**2 + y**2, 1, 0], [x, y, 1])
assert F == Fd
assert Fd == F
assert F != M
assert M != F
assert Fd != M
assert M != Fd
assert Fd == F.submodule(*F.basis())
assert Fd.is_full_module()
assert not M.is_full_module()
assert not Fd.is_zero()
assert not M.is_zero()
assert Fd.submodule().is_zero()
assert M.contains([x**2 + y**2 + x, -x**2 + y, 1])
assert not M.contains([x**2 + y**2 + x, 1 + y, 2])
assert M.contains([y**2, 1 - x*y, -x])
assert F.submodule([x, 0, 0]) == F.submodule([1, 0, 0])
assert not F.submodule([y, 0, 0]) == F.submodule([1, 0, 0])
assert F.submodule([1, 0, 0], [0, 1, 0]).union(F.submodule([0, 0, 1])) == F
assert not M.is_submodule(0)
def test_module_mul():
R = QQ.old_poly_ring(x)
M = R.free_module(2)
S1 = M.submodule([x, 0], [0, x])
S2 = M.submodule([x**2, 0], [0, x**2])
I = R.ideal(x)
assert I*M == M*I == S1 == x*M == M*x
assert I*S1 == S2 == x*S1
def test_intersection():
# SCA, example 2.8.5
F = QQ.old_poly_ring(x, y).free_module(2)
M1 = F.submodule([x, y], [y, 1])
M2 = F.submodule([0, y - 1], [x, 1], [y, x])
I = F.submodule([x, y], [y**2 - y, y - 1], [x*y + y, x + 1])
I1, rel1, rel2 = M1.intersect(M2, relations=True)
assert I1 == M2.intersect(M1) == I
for i, g in enumerate(I1.gens):
assert g == sum(c*x for c, x in zip(rel1[i], M1.gens)) \
== sum(d*y for d, y in zip(rel2[i], M2.gens))
assert F.submodule([x, y]).intersect(F.submodule([y, x])).is_zero()
def test_quotient():
# SCA, example 2.8.6
R = QQ.old_poly_ring(x, y, z)
F = R.free_module(2)
assert F.submodule([x*y, x*z], [y*z, x*y]).module_quotient(
F.submodule([y, z], [z, y])) == QQ.old_poly_ring(x, y, z).ideal(x**2*y**2 - x*y*z**2)
assert F.submodule([x, y]).module_quotient(F.submodule()).is_whole_ring()
M = F.submodule([x**2, x**2], [y**2, y**2])
N = F.submodule([x + y, x + y])
q, rel = M.module_quotient(N, relations=True)
assert q == R.ideal(y**2, x - y)
for i, g in enumerate(q.gens):
assert g*N.gens[0] == sum(c*x for c, x in zip(rel[i], M.gens))
def test_groebner_extendend():
M = QQ.old_poly_ring(x, y, z).free_module(3).submodule([x + 1, y, 1], [x*y, z, z**2])
G, R = M._groebner_vec(extended=True)
for i, g in enumerate(G):
assert g == sum(c*gen for c, gen in zip(R[i], M.gens))