passagemath-modules 10.6.31rc3__cp314-cp314-musllinux_1_2_x86_64.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.
Potentially problematic release.
This version of passagemath-modules might be problematic. Click here for more details.
- passagemath_modules-10.6.31rc3.dist-info/METADATA +281 -0
- passagemath_modules-10.6.31rc3.dist-info/RECORD +808 -0
- passagemath_modules-10.6.31rc3.dist-info/WHEEL +5 -0
- passagemath_modules-10.6.31rc3.dist-info/top_level.txt +2 -0
- passagemath_modules.libs/libgcc_s-0cd532bd.so.1 +0 -0
- passagemath_modules.libs/libgfortran-2c33b284.so.5.0.0 +0 -0
- passagemath_modules.libs/libgmp-0e7fc84e.so.10.5.0 +0 -0
- passagemath_modules.libs/libgsl-42cda06f.so.28.0.0 +0 -0
- passagemath_modules.libs/libmpc-d8ebe4b5.so.3.3.1 +0 -0
- passagemath_modules.libs/libmpfr-aaecbfc0.so.6.2.1 +0 -0
- passagemath_modules.libs/libopenblasp-r0-905cb27d.3.29.so +0 -0
- passagemath_modules.libs/libquadmath-bb76a5fc.so.0.0.0 +0 -0
- sage/algebras/all__sagemath_modules.py +20 -0
- sage/algebras/catalog.py +148 -0
- sage/algebras/clifford_algebra.py +3107 -0
- sage/algebras/clifford_algebra_element.cpython-314-x86_64-linux-musl.so +0 -0
- sage/algebras/clifford_algebra_element.pxd +16 -0
- sage/algebras/clifford_algebra_element.pyx +997 -0
- sage/algebras/commutative_dga.py +4252 -0
- sage/algebras/exterior_algebra_groebner.cpython-314-x86_64-linux-musl.so +0 -0
- sage/algebras/exterior_algebra_groebner.pxd +55 -0
- sage/algebras/exterior_algebra_groebner.pyx +727 -0
- sage/algebras/finite_dimensional_algebras/all.py +2 -0
- sage/algebras/finite_dimensional_algebras/finite_dimensional_algebra.py +1029 -0
- sage/algebras/finite_dimensional_algebras/finite_dimensional_algebra_element.cpython-314-x86_64-linux-musl.so +0 -0
- sage/algebras/finite_dimensional_algebras/finite_dimensional_algebra_element.pxd +12 -0
- sage/algebras/finite_dimensional_algebras/finite_dimensional_algebra_element.pyx +706 -0
- sage/algebras/finite_dimensional_algebras/finite_dimensional_algebra_ideal.py +196 -0
- sage/algebras/finite_dimensional_algebras/finite_dimensional_algebra_morphism.py +255 -0
- sage/algebras/finite_gca.py +528 -0
- sage/algebras/group_algebra.py +232 -0
- sage/algebras/lie_algebras/abelian.py +197 -0
- sage/algebras/lie_algebras/affine_lie_algebra.py +1213 -0
- sage/algebras/lie_algebras/all.py +25 -0
- sage/algebras/lie_algebras/all__sagemath_modules.py +1 -0
- sage/algebras/lie_algebras/bch.py +177 -0
- sage/algebras/lie_algebras/bgg_dual_module.py +1184 -0
- sage/algebras/lie_algebras/bgg_resolution.py +232 -0
- sage/algebras/lie_algebras/center_uea.py +767 -0
- sage/algebras/lie_algebras/classical_lie_algebra.py +2516 -0
- sage/algebras/lie_algebras/examples.py +683 -0
- sage/algebras/lie_algebras/free_lie_algebra.py +973 -0
- sage/algebras/lie_algebras/heisenberg.py +820 -0
- sage/algebras/lie_algebras/lie_algebra.py +1562 -0
- sage/algebras/lie_algebras/lie_algebra_element.cpython-314-x86_64-linux-musl.so +0 -0
- sage/algebras/lie_algebras/lie_algebra_element.pxd +68 -0
- sage/algebras/lie_algebras/lie_algebra_element.pyx +2122 -0
- sage/algebras/lie_algebras/morphism.py +661 -0
- sage/algebras/lie_algebras/nilpotent_lie_algebra.py +457 -0
- sage/algebras/lie_algebras/onsager.py +1324 -0
- sage/algebras/lie_algebras/poincare_birkhoff_witt.py +816 -0
- sage/algebras/lie_algebras/quotient.py +462 -0
- sage/algebras/lie_algebras/rank_two_heisenberg_virasoro.py +355 -0
- sage/algebras/lie_algebras/representation.py +1040 -0
- sage/algebras/lie_algebras/structure_coefficients.py +459 -0
- sage/algebras/lie_algebras/subalgebra.py +967 -0
- sage/algebras/lie_algebras/symplectic_derivation.py +289 -0
- sage/algebras/lie_algebras/verma_module.py +1630 -0
- sage/algebras/lie_algebras/virasoro.py +1186 -0
- sage/algebras/octonion_algebra.cpython-314-x86_64-linux-musl.so +0 -0
- sage/algebras/octonion_algebra.pxd +20 -0
- sage/algebras/octonion_algebra.pyx +987 -0
- sage/algebras/orlik_solomon.py +907 -0
- sage/algebras/orlik_terao.py +779 -0
- sage/algebras/steenrod/all.py +7 -0
- sage/algebras/steenrod/steenrod_algebra.py +4258 -0
- sage/algebras/steenrod/steenrod_algebra_bases.py +1179 -0
- sage/algebras/steenrod/steenrod_algebra_misc.py +1167 -0
- sage/algebras/steenrod/steenrod_algebra_mult.py +954 -0
- sage/algebras/weyl_algebra.py +1126 -0
- sage/all__sagemath_modules.py +62 -0
- sage/calculus/all__sagemath_modules.py +19 -0
- sage/calculus/expr.py +205 -0
- sage/calculus/integration.cpython-314-x86_64-linux-musl.so +0 -0
- sage/calculus/integration.pyx +698 -0
- sage/calculus/interpolation.cpython-314-x86_64-linux-musl.so +0 -0
- sage/calculus/interpolation.pxd +13 -0
- sage/calculus/interpolation.pyx +387 -0
- sage/calculus/interpolators.cpython-314-x86_64-linux-musl.so +0 -0
- sage/calculus/interpolators.pyx +326 -0
- sage/calculus/ode.cpython-314-x86_64-linux-musl.so +0 -0
- sage/calculus/ode.pxd +5 -0
- sage/calculus/ode.pyx +610 -0
- sage/calculus/riemann.cpython-314-x86_64-linux-musl.so +0 -0
- sage/calculus/riemann.pyx +1521 -0
- sage/calculus/test_sympy.py +201 -0
- sage/calculus/transforms/all.py +7 -0
- sage/calculus/transforms/dft.py +844 -0
- sage/calculus/transforms/dwt.cpython-314-x86_64-linux-musl.so +0 -0
- sage/calculus/transforms/dwt.pxd +7 -0
- sage/calculus/transforms/dwt.pyx +160 -0
- sage/calculus/transforms/fft.cpython-314-x86_64-linux-musl.so +0 -0
- sage/calculus/transforms/fft.pxd +12 -0
- sage/calculus/transforms/fft.pyx +487 -0
- sage/calculus/wester.py +662 -0
- sage/coding/abstract_code.py +1108 -0
- sage/coding/ag_code.py +868 -0
- sage/coding/ag_code_decoders.cpython-314-x86_64-linux-musl.so +0 -0
- sage/coding/ag_code_decoders.pyx +2639 -0
- sage/coding/all.py +15 -0
- sage/coding/bch_code.py +494 -0
- sage/coding/binary_code.cpython-314-x86_64-linux-musl.so +0 -0
- sage/coding/binary_code.pxd +124 -0
- sage/coding/binary_code.pyx +4139 -0
- sage/coding/bounds_catalog.py +43 -0
- sage/coding/channel.py +819 -0
- sage/coding/channels_catalog.py +29 -0
- sage/coding/code_bounds.py +755 -0
- sage/coding/code_constructions.py +804 -0
- sage/coding/codes_catalog.py +111 -0
- sage/coding/cyclic_code.py +1329 -0
- sage/coding/databases.py +316 -0
- sage/coding/decoder.py +373 -0
- sage/coding/decoders_catalog.py +88 -0
- sage/coding/delsarte_bounds.py +709 -0
- sage/coding/encoder.py +390 -0
- sage/coding/encoders_catalog.py +64 -0
- sage/coding/extended_code.py +468 -0
- sage/coding/gabidulin_code.py +1058 -0
- sage/coding/golay_code.py +404 -0
- sage/coding/goppa_code.py +441 -0
- sage/coding/grs_code.py +2371 -0
- sage/coding/guava.py +107 -0
- sage/coding/guruswami_sudan/all.py +1 -0
- sage/coding/guruswami_sudan/gs_decoder.py +897 -0
- sage/coding/guruswami_sudan/interpolation.py +409 -0
- sage/coding/guruswami_sudan/utils.py +176 -0
- sage/coding/hamming_code.py +176 -0
- sage/coding/information_set_decoder.py +1032 -0
- sage/coding/kasami_codes.cpython-314-x86_64-linux-musl.so +0 -0
- sage/coding/kasami_codes.pyx +351 -0
- sage/coding/linear_code.py +3067 -0
- sage/coding/linear_code_no_metric.py +1354 -0
- sage/coding/linear_rank_metric.py +961 -0
- sage/coding/parity_check_code.py +353 -0
- sage/coding/punctured_code.py +719 -0
- sage/coding/reed_muller_code.py +999 -0
- sage/coding/self_dual_codes.py +942 -0
- sage/coding/source_coding/all.py +2 -0
- sage/coding/source_coding/huffman.py +553 -0
- sage/coding/subfield_subcode.py +423 -0
- sage/coding/two_weight_db.py +399 -0
- sage/combinat/all__sagemath_modules.py +7 -0
- sage/combinat/cartesian_product.py +347 -0
- sage/combinat/family.py +11 -0
- sage/combinat/free_module.py +1977 -0
- sage/combinat/root_system/all.py +147 -0
- sage/combinat/root_system/ambient_space.py +527 -0
- sage/combinat/root_system/associahedron.py +471 -0
- sage/combinat/root_system/braid_move_calculator.py +143 -0
- sage/combinat/root_system/braid_orbit.cpython-314-x86_64-linux-musl.so +0 -0
- sage/combinat/root_system/braid_orbit.pyx +144 -0
- sage/combinat/root_system/branching_rules.py +2301 -0
- sage/combinat/root_system/cartan_matrix.py +1245 -0
- sage/combinat/root_system/cartan_type.py +3069 -0
- sage/combinat/root_system/coxeter_group.py +162 -0
- sage/combinat/root_system/coxeter_matrix.py +1261 -0
- sage/combinat/root_system/coxeter_type.py +681 -0
- sage/combinat/root_system/dynkin_diagram.py +900 -0
- sage/combinat/root_system/extended_affine_weyl_group.py +2993 -0
- sage/combinat/root_system/fundamental_group.py +795 -0
- sage/combinat/root_system/hecke_algebra_representation.py +1203 -0
- sage/combinat/root_system/integrable_representations.py +1227 -0
- sage/combinat/root_system/non_symmetric_macdonald_polynomials.py +1965 -0
- sage/combinat/root_system/pieri_factors.py +1147 -0
- sage/combinat/root_system/plot.py +1615 -0
- sage/combinat/root_system/root_lattice_realization_algebras.py +1214 -0
- sage/combinat/root_system/root_lattice_realizations.py +4628 -0
- sage/combinat/root_system/root_space.py +487 -0
- sage/combinat/root_system/root_system.py +882 -0
- sage/combinat/root_system/type_A.py +348 -0
- sage/combinat/root_system/type_A_affine.py +227 -0
- sage/combinat/root_system/type_A_infinity.py +241 -0
- sage/combinat/root_system/type_B.py +347 -0
- sage/combinat/root_system/type_BC_affine.py +287 -0
- sage/combinat/root_system/type_B_affine.py +216 -0
- sage/combinat/root_system/type_C.py +317 -0
- sage/combinat/root_system/type_C_affine.py +188 -0
- sage/combinat/root_system/type_D.py +357 -0
- sage/combinat/root_system/type_D_affine.py +208 -0
- sage/combinat/root_system/type_E.py +641 -0
- sage/combinat/root_system/type_E_affine.py +231 -0
- sage/combinat/root_system/type_F.py +387 -0
- sage/combinat/root_system/type_F_affine.py +137 -0
- sage/combinat/root_system/type_G.py +293 -0
- sage/combinat/root_system/type_G_affine.py +132 -0
- sage/combinat/root_system/type_H.py +105 -0
- sage/combinat/root_system/type_I.py +110 -0
- sage/combinat/root_system/type_Q.py +150 -0
- sage/combinat/root_system/type_affine.py +509 -0
- sage/combinat/root_system/type_dual.py +704 -0
- sage/combinat/root_system/type_folded.py +301 -0
- sage/combinat/root_system/type_marked.py +748 -0
- sage/combinat/root_system/type_reducible.py +601 -0
- sage/combinat/root_system/type_relabel.py +730 -0
- sage/combinat/root_system/type_super_A.py +837 -0
- sage/combinat/root_system/weight_lattice_realizations.py +1188 -0
- sage/combinat/root_system/weight_space.py +639 -0
- sage/combinat/root_system/weyl_characters.py +2238 -0
- sage/crypto/__init__.py +4 -0
- sage/crypto/all.py +28 -0
- sage/crypto/block_cipher/all.py +7 -0
- sage/crypto/block_cipher/des.py +1065 -0
- sage/crypto/block_cipher/miniaes.py +2171 -0
- sage/crypto/block_cipher/present.py +909 -0
- sage/crypto/block_cipher/sdes.py +1527 -0
- sage/crypto/boolean_function.cpython-314-x86_64-linux-musl.so +0 -0
- sage/crypto/boolean_function.pxd +10 -0
- sage/crypto/boolean_function.pyx +1487 -0
- sage/crypto/cipher.py +78 -0
- sage/crypto/classical.py +3668 -0
- sage/crypto/classical_cipher.py +569 -0
- sage/crypto/cryptosystem.py +387 -0
- sage/crypto/key_exchange/all.py +7 -0
- sage/crypto/key_exchange/catalog.py +24 -0
- sage/crypto/key_exchange/diffie_hellman.py +323 -0
- sage/crypto/key_exchange/key_exchange_scheme.py +107 -0
- sage/crypto/lattice.py +312 -0
- sage/crypto/lfsr.py +295 -0
- sage/crypto/lwe.py +840 -0
- sage/crypto/mq/__init__.py +4 -0
- sage/crypto/mq/mpolynomialsystemgenerator.py +204 -0
- sage/crypto/mq/rijndael_gf.py +2345 -0
- sage/crypto/mq/sbox.py +7 -0
- sage/crypto/mq/sr.py +3344 -0
- sage/crypto/public_key/all.py +5 -0
- sage/crypto/public_key/blum_goldwasser.py +776 -0
- sage/crypto/sbox.cpython-314-x86_64-linux-musl.so +0 -0
- sage/crypto/sbox.pyx +2090 -0
- sage/crypto/sboxes.py +2090 -0
- sage/crypto/stream.py +390 -0
- sage/crypto/stream_cipher.py +297 -0
- sage/crypto/util.py +519 -0
- sage/ext/all__sagemath_modules.py +1 -0
- sage/ext/interpreters/__init__.py +1 -0
- sage/ext/interpreters/all__sagemath_modules.py +2 -0
- sage/ext/interpreters/wrapper_cc.cpython-314-x86_64-linux-musl.so +0 -0
- sage/ext/interpreters/wrapper_cc.pxd +30 -0
- sage/ext/interpreters/wrapper_cc.pyx +252 -0
- sage/ext/interpreters/wrapper_cdf.cpython-314-x86_64-linux-musl.so +0 -0
- sage/ext/interpreters/wrapper_cdf.pxd +26 -0
- sage/ext/interpreters/wrapper_cdf.pyx +245 -0
- sage/ext/interpreters/wrapper_rdf.cpython-314-x86_64-linux-musl.so +0 -0
- sage/ext/interpreters/wrapper_rdf.pxd +23 -0
- sage/ext/interpreters/wrapper_rdf.pyx +221 -0
- sage/ext/interpreters/wrapper_rr.cpython-314-x86_64-linux-musl.so +0 -0
- sage/ext/interpreters/wrapper_rr.pxd +28 -0
- sage/ext/interpreters/wrapper_rr.pyx +335 -0
- sage/geometry/all__sagemath_modules.py +5 -0
- sage/geometry/toric_lattice.py +1745 -0
- sage/geometry/toric_lattice_element.cpython-314-x86_64-linux-musl.so +0 -0
- sage/geometry/toric_lattice_element.pyx +432 -0
- sage/groups/abelian_gps/abelian_group.py +1925 -0
- sage/groups/abelian_gps/abelian_group_element.py +164 -0
- sage/groups/abelian_gps/all__sagemath_modules.py +5 -0
- sage/groups/abelian_gps/dual_abelian_group.py +421 -0
- sage/groups/abelian_gps/dual_abelian_group_element.py +179 -0
- sage/groups/abelian_gps/element_base.py +341 -0
- sage/groups/abelian_gps/values.py +488 -0
- sage/groups/additive_abelian/additive_abelian_group.py +476 -0
- sage/groups/additive_abelian/additive_abelian_wrapper.py +857 -0
- sage/groups/additive_abelian/all.py +4 -0
- sage/groups/additive_abelian/qmodnz.py +231 -0
- sage/groups/additive_abelian/qmodnz_element.py +349 -0
- sage/groups/affine_gps/affine_group.py +535 -0
- sage/groups/affine_gps/all.py +1 -0
- sage/groups/affine_gps/catalog.py +17 -0
- sage/groups/affine_gps/euclidean_group.py +246 -0
- sage/groups/affine_gps/group_element.py +562 -0
- sage/groups/all__sagemath_modules.py +12 -0
- sage/groups/galois_group.py +479 -0
- sage/groups/matrix_gps/all.py +4 -0
- sage/groups/matrix_gps/all__sagemath_modules.py +13 -0
- sage/groups/matrix_gps/catalog.py +26 -0
- sage/groups/matrix_gps/coxeter_group.py +927 -0
- sage/groups/matrix_gps/finitely_generated.py +487 -0
- sage/groups/matrix_gps/group_element.cpython-314-x86_64-linux-musl.so +0 -0
- sage/groups/matrix_gps/group_element.pxd +11 -0
- sage/groups/matrix_gps/group_element.pyx +431 -0
- sage/groups/matrix_gps/linear.py +440 -0
- sage/groups/matrix_gps/matrix_group.py +617 -0
- sage/groups/matrix_gps/named_group.py +296 -0
- sage/groups/matrix_gps/orthogonal.py +544 -0
- sage/groups/matrix_gps/symplectic.py +251 -0
- sage/groups/matrix_gps/unitary.py +436 -0
- sage/groups/misc_gps/all__sagemath_modules.py +1 -0
- sage/groups/misc_gps/argument_groups.py +1905 -0
- sage/groups/misc_gps/imaginary_groups.py +479 -0
- sage/groups/perm_gps/all__sagemath_modules.py +1 -0
- sage/groups/perm_gps/partn_ref/all__sagemath_modules.py +1 -0
- sage/groups/perm_gps/partn_ref/refinement_binary.cpython-314-x86_64-linux-musl.so +0 -0
- sage/groups/perm_gps/partn_ref/refinement_binary.pxd +41 -0
- sage/groups/perm_gps/partn_ref/refinement_binary.pyx +1167 -0
- sage/groups/perm_gps/partn_ref/refinement_matrices.cpython-314-x86_64-linux-musl.so +0 -0
- sage/groups/perm_gps/partn_ref/refinement_matrices.pxd +31 -0
- sage/groups/perm_gps/partn_ref/refinement_matrices.pyx +385 -0
- sage/homology/algebraic_topological_model.py +595 -0
- sage/homology/all.py +2 -0
- sage/homology/all__sagemath_modules.py +8 -0
- sage/homology/chain_complex.py +2148 -0
- sage/homology/chain_complex_homspace.py +165 -0
- sage/homology/chain_complex_morphism.py +629 -0
- sage/homology/chain_homotopy.py +604 -0
- sage/homology/chains.py +653 -0
- sage/homology/free_resolution.py +923 -0
- sage/homology/graded_resolution.py +567 -0
- sage/homology/hochschild_complex.py +756 -0
- sage/homology/homology_group.py +188 -0
- sage/homology/homology_morphism.py +422 -0
- sage/homology/homology_vector_space_with_basis.py +1454 -0
- sage/homology/koszul_complex.py +169 -0
- sage/homology/matrix_utils.py +205 -0
- sage/libs/all__sagemath_modules.py +1 -0
- sage/libs/gsl/__init__.py +1 -0
- sage/libs/gsl/airy.pxd +56 -0
- sage/libs/gsl/all.pxd +66 -0
- sage/libs/gsl/array.cpython-314-x86_64-linux-musl.so +0 -0
- sage/libs/gsl/array.pxd +5 -0
- sage/libs/gsl/array.pyx +102 -0
- sage/libs/gsl/bessel.pxd +208 -0
- sage/libs/gsl/blas.pxd +116 -0
- sage/libs/gsl/blas_types.pxd +34 -0
- sage/libs/gsl/block.pxd +52 -0
- sage/libs/gsl/chebyshev.pxd +37 -0
- sage/libs/gsl/clausen.pxd +12 -0
- sage/libs/gsl/combination.pxd +47 -0
- sage/libs/gsl/complex.pxd +151 -0
- sage/libs/gsl/coulomb.pxd +30 -0
- sage/libs/gsl/coupling.pxd +21 -0
- sage/libs/gsl/dawson.pxd +12 -0
- sage/libs/gsl/debye.pxd +24 -0
- sage/libs/gsl/dilog.pxd +14 -0
- sage/libs/gsl/eigen.pxd +46 -0
- sage/libs/gsl/elementary.pxd +12 -0
- sage/libs/gsl/ellint.pxd +48 -0
- sage/libs/gsl/elljac.pxd +8 -0
- sage/libs/gsl/erf.pxd +32 -0
- sage/libs/gsl/errno.pxd +26 -0
- sage/libs/gsl/exp.pxd +44 -0
- sage/libs/gsl/expint.pxd +44 -0
- sage/libs/gsl/fermi_dirac.pxd +44 -0
- sage/libs/gsl/fft.pxd +121 -0
- sage/libs/gsl/fit.pxd +50 -0
- sage/libs/gsl/gamma.pxd +94 -0
- sage/libs/gsl/gegenbauer.pxd +26 -0
- sage/libs/gsl/histogram.pxd +176 -0
- sage/libs/gsl/hyperg.pxd +52 -0
- sage/libs/gsl/integration.pxd +69 -0
- sage/libs/gsl/interp.pxd +109 -0
- sage/libs/gsl/laguerre.pxd +24 -0
- sage/libs/gsl/lambert.pxd +16 -0
- sage/libs/gsl/legendre.pxd +90 -0
- sage/libs/gsl/linalg.pxd +185 -0
- sage/libs/gsl/log.pxd +26 -0
- sage/libs/gsl/math.pxd +43 -0
- sage/libs/gsl/matrix.pxd +143 -0
- sage/libs/gsl/matrix_complex.pxd +130 -0
- sage/libs/gsl/min.pxd +67 -0
- sage/libs/gsl/monte.pxd +56 -0
- sage/libs/gsl/ntuple.pxd +32 -0
- sage/libs/gsl/odeiv.pxd +70 -0
- sage/libs/gsl/permutation.pxd +78 -0
- sage/libs/gsl/poly.pxd +40 -0
- sage/libs/gsl/pow_int.pxd +12 -0
- sage/libs/gsl/psi.pxd +28 -0
- sage/libs/gsl/qrng.pxd +29 -0
- sage/libs/gsl/random.pxd +257 -0
- sage/libs/gsl/rng.pxd +100 -0
- sage/libs/gsl/roots.pxd +72 -0
- sage/libs/gsl/sort.pxd +36 -0
- sage/libs/gsl/statistics.pxd +59 -0
- sage/libs/gsl/sum.pxd +55 -0
- sage/libs/gsl/synchrotron.pxd +16 -0
- sage/libs/gsl/transport.pxd +24 -0
- sage/libs/gsl/trig.pxd +58 -0
- sage/libs/gsl/types.pxd +137 -0
- sage/libs/gsl/vector.pxd +101 -0
- sage/libs/gsl/vector_complex.pxd +83 -0
- sage/libs/gsl/wavelet.pxd +49 -0
- sage/libs/gsl/zeta.pxd +28 -0
- sage/libs/mpc/__init__.pxd +114 -0
- sage/libs/mpc/types.pxd +28 -0
- sage/libs/mpfr/__init__.pxd +299 -0
- sage/libs/mpfr/types.pxd +26 -0
- sage/libs/mpmath/__init__.py +1 -0
- sage/libs/mpmath/all.py +27 -0
- sage/libs/mpmath/all__sagemath_modules.py +1 -0
- sage/libs/mpmath/utils.cpython-314-x86_64-linux-musl.so +0 -0
- sage/libs/mpmath/utils.pxd +4 -0
- sage/libs/mpmath/utils.pyx +319 -0
- sage/matrix/action.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matrix/action.pxd +26 -0
- sage/matrix/action.pyx +596 -0
- sage/matrix/all.py +9 -0
- sage/matrix/args.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matrix/args.pxd +144 -0
- sage/matrix/args.pyx +1668 -0
- sage/matrix/benchmark.py +1258 -0
- sage/matrix/berlekamp_massey.py +95 -0
- sage/matrix/compute_J_ideal.py +926 -0
- sage/matrix/constructor.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matrix/constructor.pyx +750 -0
- sage/matrix/docs.py +430 -0
- sage/matrix/echelon_matrix.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matrix/echelon_matrix.pyx +155 -0
- sage/matrix/matrix.pxd +2 -0
- sage/matrix/matrix0.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matrix/matrix0.pxd +68 -0
- sage/matrix/matrix0.pyx +6324 -0
- sage/matrix/matrix1.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matrix/matrix1.pxd +8 -0
- sage/matrix/matrix1.pyx +2851 -0
- sage/matrix/matrix2.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matrix/matrix2.pxd +25 -0
- sage/matrix/matrix2.pyx +20181 -0
- sage/matrix/matrix_cdv.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matrix/matrix_cdv.pxd +4 -0
- sage/matrix/matrix_cdv.pyx +93 -0
- sage/matrix/matrix_complex_double_dense.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matrix/matrix_complex_double_dense.pxd +5 -0
- sage/matrix/matrix_complex_double_dense.pyx +98 -0
- sage/matrix/matrix_dense.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matrix/matrix_dense.pxd +5 -0
- sage/matrix/matrix_dense.pyx +343 -0
- sage/matrix/matrix_domain_dense.pxd +5 -0
- sage/matrix/matrix_domain_sparse.pxd +5 -0
- sage/matrix/matrix_double_dense.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matrix/matrix_double_dense.pxd +7 -0
- sage/matrix/matrix_double_dense.pyx +3906 -0
- sage/matrix/matrix_double_sparse.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matrix/matrix_double_sparse.pxd +6 -0
- sage/matrix/matrix_double_sparse.pyx +248 -0
- sage/matrix/matrix_generic_dense.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matrix/matrix_generic_dense.pxd +7 -0
- sage/matrix/matrix_generic_dense.pyx +354 -0
- sage/matrix/matrix_generic_sparse.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matrix/matrix_generic_sparse.pxd +7 -0
- sage/matrix/matrix_generic_sparse.pyx +461 -0
- sage/matrix/matrix_laurent_mpolynomial_dense.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matrix/matrix_laurent_mpolynomial_dense.pxd +5 -0
- sage/matrix/matrix_laurent_mpolynomial_dense.pyx +115 -0
- sage/matrix/matrix_misc.py +313 -0
- sage/matrix/matrix_numpy_dense.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matrix/matrix_numpy_dense.pxd +14 -0
- sage/matrix/matrix_numpy_dense.pyx +450 -0
- sage/matrix/matrix_numpy_integer_dense.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matrix/matrix_numpy_integer_dense.pxd +7 -0
- sage/matrix/matrix_numpy_integer_dense.pyx +59 -0
- sage/matrix/matrix_polynomial_dense.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matrix/matrix_polynomial_dense.pxd +5 -0
- sage/matrix/matrix_polynomial_dense.pyx +5341 -0
- sage/matrix/matrix_real_double_dense.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matrix/matrix_real_double_dense.pxd +7 -0
- sage/matrix/matrix_real_double_dense.pyx +122 -0
- sage/matrix/matrix_space.py +2848 -0
- sage/matrix/matrix_sparse.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matrix/matrix_sparse.pxd +5 -0
- sage/matrix/matrix_sparse.pyx +1222 -0
- sage/matrix/matrix_window.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matrix/matrix_window.pxd +37 -0
- sage/matrix/matrix_window.pyx +242 -0
- sage/matrix/misc_mpfr.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matrix/misc_mpfr.pyx +80 -0
- sage/matrix/operation_table.py +1182 -0
- sage/matrix/special.py +3666 -0
- sage/matrix/strassen.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matrix/strassen.pyx +851 -0
- sage/matrix/symplectic_basis.py +541 -0
- sage/matrix/template.pxd +6 -0
- sage/matrix/tests.py +71 -0
- sage/matroids/advanced.py +77 -0
- sage/matroids/all.py +13 -0
- sage/matroids/basis_exchange_matroid.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matroids/basis_exchange_matroid.pxd +96 -0
- sage/matroids/basis_exchange_matroid.pyx +2344 -0
- sage/matroids/basis_matroid.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matroids/basis_matroid.pxd +45 -0
- sage/matroids/basis_matroid.pyx +1217 -0
- sage/matroids/catalog.py +44 -0
- sage/matroids/chow_ring.py +473 -0
- sage/matroids/chow_ring_ideal.py +849 -0
- sage/matroids/circuit_closures_matroid.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matroids/circuit_closures_matroid.pxd +16 -0
- sage/matroids/circuit_closures_matroid.pyx +559 -0
- sage/matroids/circuits_matroid.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matroids/circuits_matroid.pxd +38 -0
- sage/matroids/circuits_matroid.pyx +947 -0
- sage/matroids/constructor.py +1086 -0
- sage/matroids/database_collections.py +365 -0
- sage/matroids/database_matroids.py +5338 -0
- sage/matroids/dual_matroid.py +583 -0
- sage/matroids/extension.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matroids/extension.pxd +34 -0
- sage/matroids/extension.pyx +519 -0
- sage/matroids/flats_matroid.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matroids/flats_matroid.pxd +28 -0
- sage/matroids/flats_matroid.pyx +715 -0
- sage/matroids/gammoid.py +600 -0
- sage/matroids/graphic_matroid.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matroids/graphic_matroid.pxd +39 -0
- sage/matroids/graphic_matroid.pyx +2024 -0
- sage/matroids/lean_matrix.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matroids/lean_matrix.pxd +126 -0
- sage/matroids/lean_matrix.pyx +3667 -0
- sage/matroids/linear_matroid.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matroids/linear_matroid.pxd +180 -0
- sage/matroids/linear_matroid.pyx +6649 -0
- sage/matroids/matroid.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matroids/matroid.pxd +243 -0
- sage/matroids/matroid.pyx +8759 -0
- sage/matroids/matroids_catalog.py +190 -0
- sage/matroids/matroids_plot_helpers.py +890 -0
- sage/matroids/minor_matroid.py +480 -0
- sage/matroids/minorfix.h +9 -0
- sage/matroids/named_matroids.py +5 -0
- sage/matroids/rank_matroid.py +268 -0
- sage/matroids/set_system.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matroids/set_system.pxd +38 -0
- sage/matroids/set_system.pyx +800 -0
- sage/matroids/transversal_matroid.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matroids/transversal_matroid.pxd +14 -0
- sage/matroids/transversal_matroid.pyx +893 -0
- sage/matroids/union_matroid.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matroids/union_matroid.pxd +20 -0
- sage/matroids/union_matroid.pyx +331 -0
- sage/matroids/unpickling.cpython-314-x86_64-linux-musl.so +0 -0
- sage/matroids/unpickling.pyx +843 -0
- sage/matroids/utilities.py +809 -0
- sage/misc/all__sagemath_modules.py +20 -0
- sage/misc/c3.cpython-314-x86_64-linux-musl.so +0 -0
- sage/misc/c3.pyx +238 -0
- sage/misc/compat.py +87 -0
- sage/misc/element_with_label.py +173 -0
- sage/misc/func_persist.py +79 -0
- sage/misc/pickle_old.cpython-314-x86_64-linux-musl.so +0 -0
- sage/misc/pickle_old.pyx +19 -0
- sage/misc/proof.py +7 -0
- sage/misc/replace_dot_all.py +472 -0
- sage/misc/sagedoc_conf.py +168 -0
- sage/misc/sphinxify.py +167 -0
- sage/misc/test_class_pickling.py +85 -0
- sage/modules/all.py +42 -0
- sage/modules/complex_double_vector.py +25 -0
- sage/modules/diamond_cutting.py +380 -0
- sage/modules/fg_pid/all.py +1 -0
- sage/modules/fg_pid/fgp_element.py +456 -0
- sage/modules/fg_pid/fgp_module.py +2091 -0
- sage/modules/fg_pid/fgp_morphism.py +550 -0
- sage/modules/filtered_vector_space.py +1271 -0
- sage/modules/finite_submodule_iter.cpython-314-x86_64-linux-musl.so +0 -0
- sage/modules/finite_submodule_iter.pxd +27 -0
- sage/modules/finite_submodule_iter.pyx +452 -0
- sage/modules/fp_graded/all.py +1 -0
- sage/modules/fp_graded/element.py +346 -0
- sage/modules/fp_graded/free_element.py +298 -0
- sage/modules/fp_graded/free_homspace.py +53 -0
- sage/modules/fp_graded/free_module.py +1060 -0
- sage/modules/fp_graded/free_morphism.py +217 -0
- sage/modules/fp_graded/homspace.py +563 -0
- sage/modules/fp_graded/module.py +1340 -0
- sage/modules/fp_graded/morphism.py +1990 -0
- sage/modules/fp_graded/steenrod/all.py +1 -0
- sage/modules/fp_graded/steenrod/homspace.py +65 -0
- sage/modules/fp_graded/steenrod/module.py +477 -0
- sage/modules/fp_graded/steenrod/morphism.py +404 -0
- sage/modules/fp_graded/steenrod/profile.py +241 -0
- sage/modules/free_module.py +8447 -0
- sage/modules/free_module_element.cpython-314-x86_64-linux-musl.so +0 -0
- sage/modules/free_module_element.pxd +22 -0
- sage/modules/free_module_element.pyx +5445 -0
- sage/modules/free_module_homspace.py +369 -0
- sage/modules/free_module_integer.py +896 -0
- sage/modules/free_module_morphism.py +823 -0
- sage/modules/free_module_pseudohomspace.py +352 -0
- sage/modules/free_module_pseudomorphism.py +578 -0
- sage/modules/free_quadratic_module.py +1706 -0
- sage/modules/free_quadratic_module_integer_symmetric.py +1790 -0
- sage/modules/matrix_morphism.py +1745 -0
- sage/modules/misc.py +103 -0
- sage/modules/module_functors.py +192 -0
- sage/modules/multi_filtered_vector_space.py +719 -0
- sage/modules/ore_module.py +2208 -0
- sage/modules/ore_module_element.py +178 -0
- sage/modules/ore_module_homspace.py +147 -0
- sage/modules/ore_module_morphism.py +968 -0
- sage/modules/quotient_module.py +699 -0
- sage/modules/real_double_vector.py +22 -0
- sage/modules/submodule.py +255 -0
- sage/modules/tensor_operations.py +567 -0
- sage/modules/torsion_quadratic_module.py +1352 -0
- sage/modules/tutorial_free_modules.py +248 -0
- sage/modules/vector_complex_double_dense.cpython-314-x86_64-linux-musl.so +0 -0
- sage/modules/vector_complex_double_dense.pxd +6 -0
- sage/modules/vector_complex_double_dense.pyx +117 -0
- sage/modules/vector_double_dense.cpython-314-x86_64-linux-musl.so +0 -0
- sage/modules/vector_double_dense.pxd +6 -0
- sage/modules/vector_double_dense.pyx +604 -0
- sage/modules/vector_integer_dense.cpython-314-x86_64-linux-musl.so +0 -0
- sage/modules/vector_integer_dense.pxd +15 -0
- sage/modules/vector_integer_dense.pyx +361 -0
- sage/modules/vector_integer_sparse.cpython-314-x86_64-linux-musl.so +0 -0
- sage/modules/vector_integer_sparse.pxd +29 -0
- sage/modules/vector_integer_sparse.pyx +406 -0
- sage/modules/vector_modn_dense.cpython-314-x86_64-linux-musl.so +0 -0
- sage/modules/vector_modn_dense.pxd +12 -0
- sage/modules/vector_modn_dense.pyx +394 -0
- sage/modules/vector_modn_sparse.cpython-314-x86_64-linux-musl.so +0 -0
- sage/modules/vector_modn_sparse.pxd +21 -0
- sage/modules/vector_modn_sparse.pyx +298 -0
- sage/modules/vector_numpy_dense.cpython-314-x86_64-linux-musl.so +0 -0
- sage/modules/vector_numpy_dense.pxd +15 -0
- sage/modules/vector_numpy_dense.pyx +304 -0
- sage/modules/vector_numpy_integer_dense.cpython-314-x86_64-linux-musl.so +0 -0
- sage/modules/vector_numpy_integer_dense.pxd +7 -0
- sage/modules/vector_numpy_integer_dense.pyx +54 -0
- sage/modules/vector_rational_dense.cpython-314-x86_64-linux-musl.so +0 -0
- sage/modules/vector_rational_dense.pxd +15 -0
- sage/modules/vector_rational_dense.pyx +387 -0
- sage/modules/vector_rational_sparse.cpython-314-x86_64-linux-musl.so +0 -0
- sage/modules/vector_rational_sparse.pxd +30 -0
- sage/modules/vector_rational_sparse.pyx +413 -0
- sage/modules/vector_real_double_dense.cpython-314-x86_64-linux-musl.so +0 -0
- sage/modules/vector_real_double_dense.pxd +6 -0
- sage/modules/vector_real_double_dense.pyx +126 -0
- sage/modules/vector_space_homspace.py +430 -0
- sage/modules/vector_space_morphism.py +989 -0
- sage/modules/with_basis/all.py +15 -0
- sage/modules/with_basis/cell_module.py +494 -0
- sage/modules/with_basis/indexed_element.cpython-314-x86_64-linux-musl.so +0 -0
- sage/modules/with_basis/indexed_element.pxd +13 -0
- sage/modules/with_basis/indexed_element.pyx +1058 -0
- sage/modules/with_basis/invariant.py +1075 -0
- sage/modules/with_basis/morphism.py +1636 -0
- sage/modules/with_basis/representation.py +2939 -0
- sage/modules/with_basis/subquotient.py +685 -0
- sage/numerical/all__sagemath_modules.py +6 -0
- sage/numerical/gauss_legendre.cpython-314-x86_64-linux-musl.so +0 -0
- sage/numerical/gauss_legendre.pyx +381 -0
- sage/numerical/optimize.py +910 -0
- sage/probability/all.py +10 -0
- sage/probability/probability_distribution.cpython-314-x86_64-linux-musl.so +0 -0
- sage/probability/probability_distribution.pyx +1242 -0
- sage/probability/random_variable.py +411 -0
- sage/quadratic_forms/all.py +4 -0
- sage/quadratic_forms/all__sagemath_modules.py +15 -0
- sage/quadratic_forms/binary_qf.py +2042 -0
- sage/quadratic_forms/bqf_class_group.py +748 -0
- sage/quadratic_forms/constructions.py +93 -0
- sage/quadratic_forms/count_local_2.cpython-314-x86_64-linux-musl.so +0 -0
- sage/quadratic_forms/count_local_2.pyx +365 -0
- sage/quadratic_forms/extras.py +195 -0
- sage/quadratic_forms/quadratic_form.py +1753 -0
- sage/quadratic_forms/quadratic_form__count_local_2.py +221 -0
- sage/quadratic_forms/quadratic_form__equivalence_testing.py +708 -0
- sage/quadratic_forms/quadratic_form__evaluate.cpython-314-x86_64-linux-musl.so +0 -0
- sage/quadratic_forms/quadratic_form__evaluate.pyx +139 -0
- sage/quadratic_forms/quadratic_form__local_density_congruence.py +977 -0
- sage/quadratic_forms/quadratic_form__local_field_invariants.py +1072 -0
- sage/quadratic_forms/quadratic_form__neighbors.py +424 -0
- sage/quadratic_forms/quadratic_form__reduction_theory.py +488 -0
- sage/quadratic_forms/quadratic_form__split_local_covering.py +416 -0
- sage/quadratic_forms/quadratic_form__ternary_Tornaria.py +657 -0
- sage/quadratic_forms/quadratic_form__theta.py +352 -0
- sage/quadratic_forms/quadratic_form__variable_substitutions.py +370 -0
- sage/quadratic_forms/random_quadraticform.py +209 -0
- sage/quadratic_forms/ternary.cpython-314-x86_64-linux-musl.so +0 -0
- sage/quadratic_forms/ternary.pyx +1154 -0
- sage/quadratic_forms/ternary_qf.py +2027 -0
- sage/rings/all__sagemath_modules.py +28 -0
- sage/rings/asymptotic/all__sagemath_modules.py +1 -0
- sage/rings/asymptotic/misc.py +1252 -0
- sage/rings/cc.py +4 -0
- sage/rings/cfinite_sequence.py +1306 -0
- sage/rings/complex_conversion.cpython-314-x86_64-linux-musl.so +0 -0
- sage/rings/complex_conversion.pxd +8 -0
- sage/rings/complex_conversion.pyx +23 -0
- sage/rings/complex_double.cpython-314-x86_64-linux-musl.so +0 -0
- sage/rings/complex_double.pxd +21 -0
- sage/rings/complex_double.pyx +2654 -0
- sage/rings/complex_mpc.cpython-314-x86_64-linux-musl.so +0 -0
- sage/rings/complex_mpc.pxd +21 -0
- sage/rings/complex_mpc.pyx +2576 -0
- sage/rings/complex_mpfr.cpython-314-x86_64-linux-musl.so +0 -0
- sage/rings/complex_mpfr.pxd +18 -0
- sage/rings/complex_mpfr.pyx +3602 -0
- sage/rings/derivation.py +2334 -0
- sage/rings/finite_rings/all__sagemath_modules.py +1 -0
- sage/rings/finite_rings/maps_finite_field.py +191 -0
- sage/rings/function_field/all__sagemath_modules.py +8 -0
- sage/rings/function_field/derivations.py +102 -0
- sage/rings/function_field/derivations_rational.py +132 -0
- sage/rings/function_field/differential.py +853 -0
- sage/rings/function_field/divisor.py +1107 -0
- sage/rings/function_field/drinfeld_modules/action.py +199 -0
- sage/rings/function_field/drinfeld_modules/all.py +1 -0
- sage/rings/function_field/drinfeld_modules/charzero_drinfeld_module.py +673 -0
- sage/rings/function_field/drinfeld_modules/drinfeld_module.py +2087 -0
- sage/rings/function_field/drinfeld_modules/finite_drinfeld_module.py +1131 -0
- sage/rings/function_field/drinfeld_modules/homset.py +420 -0
- sage/rings/function_field/drinfeld_modules/morphism.py +820 -0
- sage/rings/function_field/hermite_form_polynomial.cpython-314-x86_64-linux-musl.so +0 -0
- sage/rings/function_field/hermite_form_polynomial.pyx +188 -0
- sage/rings/function_field/khuri_makdisi.cpython-314-x86_64-linux-musl.so +0 -0
- sage/rings/function_field/khuri_makdisi.pyx +935 -0
- sage/rings/invariants/all.py +4 -0
- sage/rings/invariants/invariant_theory.py +4597 -0
- sage/rings/invariants/reconstruction.py +395 -0
- sage/rings/polynomial/all__sagemath_modules.py +17 -0
- sage/rings/polynomial/integer_valued_polynomials.py +1230 -0
- sage/rings/polynomial/laurent_polynomial_mpair.cpython-314-x86_64-linux-musl.so +0 -0
- sage/rings/polynomial/laurent_polynomial_mpair.pxd +15 -0
- sage/rings/polynomial/laurent_polynomial_mpair.pyx +2023 -0
- sage/rings/polynomial/ore_function_element.py +952 -0
- sage/rings/polynomial/ore_function_field.py +1028 -0
- sage/rings/polynomial/ore_polynomial_element.cpython-314-x86_64-linux-musl.so +0 -0
- sage/rings/polynomial/ore_polynomial_element.pxd +48 -0
- sage/rings/polynomial/ore_polynomial_element.pyx +3145 -0
- sage/rings/polynomial/ore_polynomial_ring.py +1334 -0
- sage/rings/polynomial/polynomial_real_mpfr_dense.cpython-314-x86_64-linux-musl.so +0 -0
- sage/rings/polynomial/polynomial_real_mpfr_dense.pyx +788 -0
- sage/rings/polynomial/q_integer_valued_polynomials.py +1264 -0
- sage/rings/polynomial/skew_polynomial_element.cpython-314-x86_64-linux-musl.so +0 -0
- sage/rings/polynomial/skew_polynomial_element.pxd +9 -0
- sage/rings/polynomial/skew_polynomial_element.pyx +684 -0
- sage/rings/polynomial/skew_polynomial_finite_field.cpython-314-x86_64-linux-musl.so +0 -0
- sage/rings/polynomial/skew_polynomial_finite_field.pxd +19 -0
- sage/rings/polynomial/skew_polynomial_finite_field.pyx +1093 -0
- sage/rings/polynomial/skew_polynomial_finite_order.cpython-314-x86_64-linux-musl.so +0 -0
- sage/rings/polynomial/skew_polynomial_finite_order.pxd +10 -0
- sage/rings/polynomial/skew_polynomial_finite_order.pyx +567 -0
- sage/rings/polynomial/skew_polynomial_ring.py +908 -0
- sage/rings/real_double_element_gsl.cpython-314-x86_64-linux-musl.so +0 -0
- sage/rings/real_double_element_gsl.pxd +8 -0
- sage/rings/real_double_element_gsl.pyx +794 -0
- sage/rings/real_field.py +58 -0
- sage/rings/real_mpfr.cpython-314-x86_64-linux-musl.so +0 -0
- sage/rings/real_mpfr.pxd +29 -0
- sage/rings/real_mpfr.pyx +6122 -0
- sage/rings/ring_extension.cpython-314-x86_64-linux-musl.so +0 -0
- sage/rings/ring_extension.pxd +42 -0
- sage/rings/ring_extension.pyx +2779 -0
- sage/rings/ring_extension_conversion.cpython-314-x86_64-linux-musl.so +0 -0
- sage/rings/ring_extension_conversion.pxd +16 -0
- sage/rings/ring_extension_conversion.pyx +462 -0
- sage/rings/ring_extension_element.cpython-314-x86_64-linux-musl.so +0 -0
- sage/rings/ring_extension_element.pxd +21 -0
- sage/rings/ring_extension_element.pyx +1635 -0
- sage/rings/ring_extension_homset.py +64 -0
- sage/rings/ring_extension_morphism.cpython-314-x86_64-linux-musl.so +0 -0
- sage/rings/ring_extension_morphism.pxd +35 -0
- sage/rings/ring_extension_morphism.pyx +920 -0
- sage/schemes/all__sagemath_modules.py +1 -0
- sage/schemes/projective/all__sagemath_modules.py +1 -0
- sage/schemes/projective/coherent_sheaf.py +300 -0
- sage/schemes/projective/cohomology.py +510 -0
- sage/stats/all.py +15 -0
- sage/stats/basic_stats.py +489 -0
- sage/stats/distributions/all.py +7 -0
- sage/stats/distributions/catalog.py +34 -0
- sage/stats/distributions/dgs.h +50 -0
- sage/stats/distributions/dgs.pxd +111 -0
- sage/stats/distributions/dgs_bern.h +400 -0
- sage/stats/distributions/dgs_gauss.h +614 -0
- sage/stats/distributions/dgs_misc.h +104 -0
- sage/stats/distributions/discrete_gaussian_integer.cpython-314-x86_64-linux-musl.so +0 -0
- sage/stats/distributions/discrete_gaussian_integer.pxd +14 -0
- sage/stats/distributions/discrete_gaussian_integer.pyx +498 -0
- sage/stats/distributions/discrete_gaussian_lattice.py +908 -0
- sage/stats/distributions/discrete_gaussian_polynomial.py +141 -0
- sage/stats/hmm/all.py +15 -0
- sage/stats/hmm/chmm.cpython-314-x86_64-linux-musl.so +0 -0
- sage/stats/hmm/chmm.pyx +1595 -0
- sage/stats/hmm/distributions.cpython-314-x86_64-linux-musl.so +0 -0
- sage/stats/hmm/distributions.pxd +29 -0
- sage/stats/hmm/distributions.pyx +531 -0
- sage/stats/hmm/hmm.cpython-314-x86_64-linux-musl.so +0 -0
- sage/stats/hmm/hmm.pxd +17 -0
- sage/stats/hmm/hmm.pyx +1388 -0
- sage/stats/hmm/util.cpython-314-x86_64-linux-musl.so +0 -0
- sage/stats/hmm/util.pxd +7 -0
- sage/stats/hmm/util.pyx +165 -0
- sage/stats/intlist.cpython-314-x86_64-linux-musl.so +0 -0
- sage/stats/intlist.pxd +14 -0
- sage/stats/intlist.pyx +588 -0
- sage/stats/r.py +49 -0
- sage/stats/time_series.cpython-314-x86_64-linux-musl.so +0 -0
- sage/stats/time_series.pxd +6 -0
- sage/stats/time_series.pyx +2546 -0
- sage/tensor/all.py +2 -0
- sage/tensor/modules/all.py +8 -0
- sage/tensor/modules/alternating_contr_tensor.py +761 -0
- sage/tensor/modules/comp.py +5598 -0
- sage/tensor/modules/ext_pow_free_module.py +824 -0
- sage/tensor/modules/finite_rank_free_module.py +3589 -0
- sage/tensor/modules/format_utilities.py +333 -0
- sage/tensor/modules/free_module_alt_form.py +858 -0
- sage/tensor/modules/free_module_automorphism.py +1207 -0
- sage/tensor/modules/free_module_basis.py +1074 -0
- sage/tensor/modules/free_module_element.py +284 -0
- sage/tensor/modules/free_module_homset.py +652 -0
- sage/tensor/modules/free_module_linear_group.py +564 -0
- sage/tensor/modules/free_module_morphism.py +1581 -0
- sage/tensor/modules/free_module_tensor.py +3289 -0
- sage/tensor/modules/reflexive_module.py +386 -0
- sage/tensor/modules/tensor_free_module.py +780 -0
- sage/tensor/modules/tensor_free_submodule.py +538 -0
- sage/tensor/modules/tensor_free_submodule_basis.py +140 -0
- sage/tensor/modules/tensor_with_indices.py +1043 -0
|
@@ -0,0 +1,3145 @@
|
|
|
1
|
+
# sage_setup: distribution = sagemath-modules
|
|
2
|
+
# sage.doctest: needs sage.combinat
|
|
3
|
+
r"""
|
|
4
|
+
Univariate Ore polynomials
|
|
5
|
+
|
|
6
|
+
This module provides the
|
|
7
|
+
:class:`~sage.rings.polynomial.skew_polynomial_element.OrePolynomial`,
|
|
8
|
+
which constructs a single univariate Ore polynomial over a commutative
|
|
9
|
+
base equipped with an endomorphism and/or a derivation.
|
|
10
|
+
It provides generic implementation of standard arithmetical operations
|
|
11
|
+
on Ore polynomials as addition, multiplication, gcd, lcm, etc.
|
|
12
|
+
|
|
13
|
+
The generic implementation of dense Ore polynomials is
|
|
14
|
+
:class:`~sage.rings.polynomial.ore_polynomial_element.OrePolynomial_generic_dense`.
|
|
15
|
+
The classes
|
|
16
|
+
:class:`~sage.rings.polynomial.ore_polynomial_element.ConstantOrePolynomialSection`
|
|
17
|
+
and :class:`~sage.rings.polynomial.ore_polynomial_element.OrePolynomialBaseringInjection`
|
|
18
|
+
handle conversion from an Ore polynomial ring to its base ring and vice versa.
|
|
19
|
+
|
|
20
|
+
AUTHORS:
|
|
21
|
+
|
|
22
|
+
- Xavier Caruso (2020-05)
|
|
23
|
+
"""
|
|
24
|
+
|
|
25
|
+
# ***************************************************************************
|
|
26
|
+
# Copyright (C) 2020 Xavier Caruso <xavier.caruso@normalesup.org>
|
|
27
|
+
#
|
|
28
|
+
# This program is free software: you can redistribute it and/or modify
|
|
29
|
+
# it under the terms of the GNU General Public License as published by
|
|
30
|
+
# the Free Software Foundation, either version 2 of the License, or
|
|
31
|
+
# (at your option) any later version.
|
|
32
|
+
# https://www.gnu.org/licenses/
|
|
33
|
+
# ***************************************************************************
|
|
34
|
+
|
|
35
|
+
import re
|
|
36
|
+
from cysignals.signals cimport sig_check
|
|
37
|
+
from sage.structure.element import coerce_binop
|
|
38
|
+
|
|
39
|
+
from sage.rings.infinity import infinity
|
|
40
|
+
from sage.structure.element cimport Element, RingElement, AlgebraElement
|
|
41
|
+
from sage.structure.parent cimport Parent
|
|
42
|
+
from sage.categories.homset import Hom
|
|
43
|
+
from sage.rings.ring import _Fields
|
|
44
|
+
from sage.rings.integer cimport Integer
|
|
45
|
+
from cpython.object cimport PyObject_RichCompare
|
|
46
|
+
from sage.categories.map cimport Map
|
|
47
|
+
from sage.rings.morphism cimport Morphism
|
|
48
|
+
from sage.rings.polynomial.polynomial_element cimport _dict_to_list
|
|
49
|
+
|
|
50
|
+
|
|
51
|
+
cdef class OrePolynomial(AlgebraElement):
|
|
52
|
+
r"""
|
|
53
|
+
Abstract base class for Ore polynomials.
|
|
54
|
+
|
|
55
|
+
This class must be inherited from and have key methods overridden.
|
|
56
|
+
|
|
57
|
+
.. RUBRIC:: Definition
|
|
58
|
+
|
|
59
|
+
Let `R` be a commutative ring equipped with an automorphism `\sigma`
|
|
60
|
+
and a `\sigma`-derivation `\partial`.
|
|
61
|
+
|
|
62
|
+
An Ore polynomial is given by the equation:
|
|
63
|
+
|
|
64
|
+
.. MATH::
|
|
65
|
+
|
|
66
|
+
F(X) = a_{n} X^{n} + \cdots + a_0,
|
|
67
|
+
|
|
68
|
+
where the coefficients `a_i \in R` and `X` is a formal variable.
|
|
69
|
+
|
|
70
|
+
Addition between two Ore polynomials is defined by the usual addition
|
|
71
|
+
operation and the modified multiplication is defined by the rule
|
|
72
|
+
`X a = \sigma(a) X + \partial(a)` for all `a` in `R`.
|
|
73
|
+
Ore polynomials are thus non-commutative and the degree of a product
|
|
74
|
+
is equal to the sum of the degrees of the factors.
|
|
75
|
+
|
|
76
|
+
Let `a` and `b` be two Ore polynomials in the same ring `S`.
|
|
77
|
+
The *right (resp. left) Euclidean division* of `a` by `b` is a couple
|
|
78
|
+
`(q,r)` of elements in `S` such that
|
|
79
|
+
|
|
80
|
+
- `a = q b + r` (resp. `a = b q + r`)
|
|
81
|
+
|
|
82
|
+
- the degree of `r` is less than the degree of `b`
|
|
83
|
+
|
|
84
|
+
`q` (resp. `r`) is called the *quotient* (resp. the remainder)
|
|
85
|
+
of this Euclidean division.
|
|
86
|
+
|
|
87
|
+
.. RUBRIC:: Properties
|
|
88
|
+
|
|
89
|
+
Keeping the previous notation, if the leading coefficient of `b`
|
|
90
|
+
is a unit (e.g. if `b` is monic) then the quotient and the remainder
|
|
91
|
+
in the *right* Euclidean division exist and are unique.
|
|
92
|
+
|
|
93
|
+
The same result holds for the *left* Euclidean division if in addition
|
|
94
|
+
the twisting morphism defining the Ore polynomial ring is invertible.
|
|
95
|
+
|
|
96
|
+
EXAMPLES:
|
|
97
|
+
|
|
98
|
+
We illustrate some functionalities implemented in this class.
|
|
99
|
+
|
|
100
|
+
We create the Ore polynomial ring (here the derivation is zero)::
|
|
101
|
+
|
|
102
|
+
sage: R.<t> = ZZ[]
|
|
103
|
+
sage: sigma = R.hom([t+1])
|
|
104
|
+
sage: S.<x> = R['x',sigma]; S
|
|
105
|
+
Ore Polynomial Ring in x over Univariate Polynomial Ring in t over Integer Ring
|
|
106
|
+
twisted by t |--> t + 1
|
|
107
|
+
|
|
108
|
+
and some elements in it::
|
|
109
|
+
|
|
110
|
+
sage: a = t + x + 1; a
|
|
111
|
+
x + t + 1
|
|
112
|
+
sage: b = S([t^2,t+1,1]); b
|
|
113
|
+
x^2 + (t + 1)*x + t^2
|
|
114
|
+
sage: c = S.random_element(degree=3,monic=True)
|
|
115
|
+
sage: c.parent() is S
|
|
116
|
+
True
|
|
117
|
+
|
|
118
|
+
Ring operations are supported::
|
|
119
|
+
|
|
120
|
+
sage: a + b
|
|
121
|
+
x^2 + (t + 2)*x + t^2 + t + 1
|
|
122
|
+
sage: a - b
|
|
123
|
+
-x^2 - t*x - t^2 + t + 1
|
|
124
|
+
|
|
125
|
+
sage: a * b
|
|
126
|
+
x^3 + (2*t + 3)*x^2 + (2*t^2 + 4*t + 2)*x + t^3 + t^2
|
|
127
|
+
sage: b * a
|
|
128
|
+
x^3 + (2*t + 4)*x^2 + (2*t^2 + 3*t + 2)*x + t^3 + t^2
|
|
129
|
+
sage: a * b == b * a
|
|
130
|
+
False
|
|
131
|
+
|
|
132
|
+
sage: b^2
|
|
133
|
+
x^4 + (2*t + 4)*x^3 + (3*t^2 + 7*t + 6)*x^2
|
|
134
|
+
+ (2*t^3 + 4*t^2 + 3*t + 1)*x + t^4
|
|
135
|
+
sage: b^2 == b*b
|
|
136
|
+
True
|
|
137
|
+
|
|
138
|
+
Sage also implements arithmetic over Ore polynomial rings. You will find
|
|
139
|
+
below a short panorama::
|
|
140
|
+
|
|
141
|
+
sage: q,r = c.right_quo_rem(b)
|
|
142
|
+
sage: c == q*b + r
|
|
143
|
+
True
|
|
144
|
+
|
|
145
|
+
The operators ``//`` and ``%`` give respectively the quotient
|
|
146
|
+
and the remainder of the *right* Euclidean division::
|
|
147
|
+
|
|
148
|
+
sage: q == c // b
|
|
149
|
+
True
|
|
150
|
+
sage: r == c % b
|
|
151
|
+
True
|
|
152
|
+
|
|
153
|
+
Here we can see the effect of the operator evaluation compared to the usual
|
|
154
|
+
polynomial evaluation::
|
|
155
|
+
|
|
156
|
+
sage: a = x^2
|
|
157
|
+
sage: a(t)
|
|
158
|
+
doctest:...: FutureWarning: This class/method/function is marked as experimental.
|
|
159
|
+
It, its functionality or its interface might change without a formal deprecation.
|
|
160
|
+
See https://github.com/sagemath/sage/issues/13215 for details.
|
|
161
|
+
t + 2
|
|
162
|
+
|
|
163
|
+
Here is another example over a finite field::
|
|
164
|
+
|
|
165
|
+
sage: # needs sage.rings.finite_rings
|
|
166
|
+
sage: k.<t> = GF(5^3)
|
|
167
|
+
sage: Frob = k.frobenius_endomorphism()
|
|
168
|
+
sage: S.<x> = k['x',Frob]
|
|
169
|
+
sage: a = x^4 + (4*t + 1)*x^3 + (t^2 + 3*t + 3)*x^2 + (3*t^2 + 2*t + 2)*x + (3*t^2 + 3*t + 1)
|
|
170
|
+
sage: b = (2*t^2 + 3)*x^2 + (3*t^2 + 1)*x + 4*t + 2
|
|
171
|
+
sage: q, r = a.left_quo_rem(b)
|
|
172
|
+
sage: q
|
|
173
|
+
(4*t^2 + t + 1)*x^2 + (2*t^2 + 2*t + 2)*x + 2*t^2 + 4*t + 3
|
|
174
|
+
sage: r
|
|
175
|
+
(t + 2)*x + 3*t^2 + 2*t + 4
|
|
176
|
+
sage: a == b*q + r
|
|
177
|
+
True
|
|
178
|
+
|
|
179
|
+
Once we have Euclidean divisions, we have for free gcd and lcm
|
|
180
|
+
(at least if the base ring is a field)::
|
|
181
|
+
|
|
182
|
+
sage: # needs sage.rings.finite_rings
|
|
183
|
+
sage: a = (x + t) * (x + t^2)^2
|
|
184
|
+
sage: b = (x + t) * (t*x + t + 1) * (x + t^2)
|
|
185
|
+
sage: a.right_gcd(b)
|
|
186
|
+
x + t^2
|
|
187
|
+
sage: a.left_gcd(b)
|
|
188
|
+
x + t
|
|
189
|
+
|
|
190
|
+
The left lcm has the following meaning: given Ore polynomials `a` and `b`,
|
|
191
|
+
their left lcm is the least degree polynomial `c = ua = vb` for some Ore
|
|
192
|
+
polynomials `u, v`. Such a `c` always exist if the base ring is a field::
|
|
193
|
+
|
|
194
|
+
sage: c = a.left_lcm(b); c # needs sage.rings.finite_rings
|
|
195
|
+
x^5 + (4*t^2 + t + 3)*x^4 + (3*t^2 + 4*t)*x^3 + 2*t^2*x^2 + (2*t^2 + t)*x + 4*t^2 + 4
|
|
196
|
+
sage: c.is_right_divisible_by(a) # needs sage.rings.finite_rings
|
|
197
|
+
True
|
|
198
|
+
sage: c.is_right_divisible_by(b) # needs sage.rings.finite_rings
|
|
199
|
+
True
|
|
200
|
+
|
|
201
|
+
The right lcm is defined similarly as the least degree polynomial `c = au =
|
|
202
|
+
bv` for some `u,v`::
|
|
203
|
+
|
|
204
|
+
sage: d = a.right_lcm(b); d # needs sage.rings.finite_rings
|
|
205
|
+
x^5 + (t^2 + 1)*x^4 + (3*t^2 + 3*t + 3)*x^3 + (3*t^2 + t + 2)*x^2 + (4*t^2 + 3*t)*x + 4*t + 4
|
|
206
|
+
sage: d.is_left_divisible_by(a) # needs sage.rings.finite_rings
|
|
207
|
+
True
|
|
208
|
+
sage: d.is_left_divisible_by(b) # needs sage.rings.finite_rings
|
|
209
|
+
True
|
|
210
|
+
|
|
211
|
+
.. SEEALSO::
|
|
212
|
+
|
|
213
|
+
- :mod:`sage.rings.polynomial.ore_polynomial_ring`
|
|
214
|
+
"""
|
|
215
|
+
def __init__(self, parent, construct=False):
|
|
216
|
+
r"""
|
|
217
|
+
Initialize ``self``.
|
|
218
|
+
|
|
219
|
+
INPUT:
|
|
220
|
+
|
|
221
|
+
- ``parent`` -- parent of ``self``
|
|
222
|
+
|
|
223
|
+
- ``construct`` -- boolean (default: ``False``)
|
|
224
|
+
|
|
225
|
+
TESTS::
|
|
226
|
+
|
|
227
|
+
sage: R.<t> = ZZ[]
|
|
228
|
+
sage: sigma = R.hom([t+1])
|
|
229
|
+
sage: S.<x> = R['x',sigma]
|
|
230
|
+
sage: P = x + t
|
|
231
|
+
sage: TestSuite(P).run()
|
|
232
|
+
sage: Q = S([1, t, t+2])
|
|
233
|
+
sage: TestSuite(Q).run()
|
|
234
|
+
"""
|
|
235
|
+
AlgebraElement.__init__(self, parent)
|
|
236
|
+
|
|
237
|
+
cdef long _hash_c(self) noexcept:
|
|
238
|
+
raise NotImplementedError
|
|
239
|
+
|
|
240
|
+
def __hash__(self):
|
|
241
|
+
r"""
|
|
242
|
+
Return hash of ``self``.
|
|
243
|
+
|
|
244
|
+
EXAMPLES::
|
|
245
|
+
|
|
246
|
+
sage: R.<t> = QQ[]
|
|
247
|
+
sage: sigma = R.hom([t+1])
|
|
248
|
+
sage: S.<x> = R['x',sigma]
|
|
249
|
+
sage: a = 1 + x^4 + (t+1)*x^2 + t^2
|
|
250
|
+
sage: hash(a) == hash(a)
|
|
251
|
+
True
|
|
252
|
+
"""
|
|
253
|
+
return self._hash_c()
|
|
254
|
+
|
|
255
|
+
cpdef Integer degree(self):
|
|
256
|
+
r"""
|
|
257
|
+
Return the degree of ``self``.
|
|
258
|
+
|
|
259
|
+
By convention, the zero Ore polynomial has degree `-1`.
|
|
260
|
+
|
|
261
|
+
EXAMPLES::
|
|
262
|
+
|
|
263
|
+
sage: R.<t> = ZZ[]
|
|
264
|
+
sage: sigma = R.hom([t+1])
|
|
265
|
+
sage: S.<x> = R['x',sigma]
|
|
266
|
+
sage: a = x^2 + t*x^3 + t^2*x + 1
|
|
267
|
+
sage: a.degree()
|
|
268
|
+
3
|
|
269
|
+
sage: S.zero().degree()
|
|
270
|
+
-1
|
|
271
|
+
sage: S(5).degree()
|
|
272
|
+
0
|
|
273
|
+
"""
|
|
274
|
+
raise NotImplementedError
|
|
275
|
+
|
|
276
|
+
cdef OrePolynomial _new_c(self, list coeffs, Parent P, char check=0):
|
|
277
|
+
r"""
|
|
278
|
+
Fast creation of a new Ore polynomial.
|
|
279
|
+
|
|
280
|
+
.. NOTE::
|
|
281
|
+
|
|
282
|
+
Override this function in classes which inherit
|
|
283
|
+
from OrePolynomial.
|
|
284
|
+
"""
|
|
285
|
+
return P(coeffs)
|
|
286
|
+
|
|
287
|
+
cpdef OrePolynomial _new_constant_poly(self, RingElement a, Parent P, char check=0):
|
|
288
|
+
r"""
|
|
289
|
+
Fast creation of a new constant Ore polynomial.
|
|
290
|
+
|
|
291
|
+
EXAMPLES::
|
|
292
|
+
|
|
293
|
+
sage: # needs sage.rings.finite_rings
|
|
294
|
+
sage: from sage.rings.polynomial.ore_polynomial_element import OrePolynomialBaseringInjection
|
|
295
|
+
sage: k.<t> = GF(5^3)
|
|
296
|
+
sage: Frob = k.frobenius_endomorphism()
|
|
297
|
+
sage: S.<x> = k['x',Frob]
|
|
298
|
+
sage: OrePolynomialBaseringInjection(k, k['x', Frob]) #indirect doctest
|
|
299
|
+
Ore Polynomial base injection morphism:
|
|
300
|
+
From: Finite Field in t of size 5^3
|
|
301
|
+
To: Ore Polynomial Ring in x over Finite Field in t of size 5^3 twisted by t |--> t^5
|
|
302
|
+
"""
|
|
303
|
+
if a:
|
|
304
|
+
return self._new_c([a], P, check)
|
|
305
|
+
return self._new_c([], P)
|
|
306
|
+
|
|
307
|
+
def __setitem__(self, n, value):
|
|
308
|
+
r"""
|
|
309
|
+
Set the ``n``-th coefficient of ``self``.
|
|
310
|
+
|
|
311
|
+
This always raises an :exc:`IndexError`, since polynomials are immutable in
|
|
312
|
+
Sage.
|
|
313
|
+
|
|
314
|
+
EXAMPLES::
|
|
315
|
+
|
|
316
|
+
sage: # needs sage.rings.finite_rings
|
|
317
|
+
sage: k.<t> = GF(5^3)
|
|
318
|
+
sage: Frob = k.frobenius_endomorphism()
|
|
319
|
+
sage: S.<x> = k['x',Frob]
|
|
320
|
+
sage: a = x + t
|
|
321
|
+
sage: a[1] = t + 1
|
|
322
|
+
Traceback (most recent call last):
|
|
323
|
+
...
|
|
324
|
+
IndexError: Ore polynomials are immutable
|
|
325
|
+
"""
|
|
326
|
+
raise IndexError("Ore polynomials are immutable")
|
|
327
|
+
|
|
328
|
+
def square(self):
|
|
329
|
+
r"""
|
|
330
|
+
Return the square of ``self``.
|
|
331
|
+
|
|
332
|
+
EXAMPLES::
|
|
333
|
+
|
|
334
|
+
sage: R.<t> = QQ[]
|
|
335
|
+
sage: sigma = R.hom([t+1])
|
|
336
|
+
sage: S.<x> = R['x', sigma]
|
|
337
|
+
sage: a = x + t; a
|
|
338
|
+
x + t
|
|
339
|
+
sage: a.square()
|
|
340
|
+
x^2 + (2*t + 1)*x + t^2
|
|
341
|
+
sage: a.square() == a*a
|
|
342
|
+
True
|
|
343
|
+
|
|
344
|
+
sage: der = R.derivation()
|
|
345
|
+
sage: A.<d> = R['d', der]
|
|
346
|
+
sage: (d + t).square()
|
|
347
|
+
d^2 + 2*t*d + t^2 + 1
|
|
348
|
+
"""
|
|
349
|
+
return self * self
|
|
350
|
+
|
|
351
|
+
def constant_coefficient(self):
|
|
352
|
+
r"""
|
|
353
|
+
Return the constant coefficient (i.e., the coefficient of term
|
|
354
|
+
of degree `0`) of ``self``.
|
|
355
|
+
|
|
356
|
+
EXAMPLES::
|
|
357
|
+
|
|
358
|
+
sage: R.<t> = ZZ[]
|
|
359
|
+
sage: sigma = R.hom([t+1])
|
|
360
|
+
sage: S.<x> = R['x',sigma]
|
|
361
|
+
sage: a = x + t^2 + 2
|
|
362
|
+
sage: a.constant_coefficient()
|
|
363
|
+
t^2 + 2
|
|
364
|
+
"""
|
|
365
|
+
if self:
|
|
366
|
+
return self[0]
|
|
367
|
+
else:
|
|
368
|
+
return self.base_ring().zero()
|
|
369
|
+
|
|
370
|
+
def leading_coefficient(self):
|
|
371
|
+
r"""
|
|
372
|
+
Return the coefficient of the highest-degree monomial of ``self``.
|
|
373
|
+
|
|
374
|
+
EXAMPLES::
|
|
375
|
+
|
|
376
|
+
sage: R.<t> = ZZ[]
|
|
377
|
+
sage: sigma = R.hom([t+1])
|
|
378
|
+
sage: S.<x> = R['x',sigma]
|
|
379
|
+
sage: a = (t+1)*x^5 + t^2*x^3 + x
|
|
380
|
+
sage: a.leading_coefficient()
|
|
381
|
+
t + 1
|
|
382
|
+
|
|
383
|
+
By convention, the leading coefficient to the zero polynomial is
|
|
384
|
+
zero::
|
|
385
|
+
|
|
386
|
+
sage: S(0).leading_coefficient()
|
|
387
|
+
0
|
|
388
|
+
"""
|
|
389
|
+
cdef int d = self.degree()
|
|
390
|
+
if d == -1:
|
|
391
|
+
return self.base_ring()(0)
|
|
392
|
+
return self[d]
|
|
393
|
+
|
|
394
|
+
def is_unit(self):
|
|
395
|
+
r"""
|
|
396
|
+
Return ``True`` if this Ore polynomial is a unit.
|
|
397
|
+
|
|
398
|
+
When the base ring `R` is an integral domain, then an Ore polynomial `f`
|
|
399
|
+
is a unit if and only if degree of `f` is `0` and `f` is then a unit in
|
|
400
|
+
`R`.
|
|
401
|
+
|
|
402
|
+
.. NOTE::
|
|
403
|
+
|
|
404
|
+
The case when `R` is not an integral domain is not yet implemented.
|
|
405
|
+
|
|
406
|
+
EXAMPLES::
|
|
407
|
+
|
|
408
|
+
sage: R.<t> = ZZ[]
|
|
409
|
+
sage: sigma = R.hom([t+1])
|
|
410
|
+
sage: S.<x> = R['x',sigma]
|
|
411
|
+
sage: a = x + (t+1)*x^5 + t^2*x^3 - x^5
|
|
412
|
+
sage: a.is_unit()
|
|
413
|
+
False
|
|
414
|
+
"""
|
|
415
|
+
# TODO: Sage does not yet have support for finding order of
|
|
416
|
+
# automorphisms. Once that is available, general case can
|
|
417
|
+
# be implemented. Reference: http://bit.ly/29Vidu7
|
|
418
|
+
if self._parent.base_ring().is_integral_domain():
|
|
419
|
+
if self.degree() == 0 and self[0].is_unit():
|
|
420
|
+
return True
|
|
421
|
+
else:
|
|
422
|
+
return False
|
|
423
|
+
else:
|
|
424
|
+
raise NotImplementedError("is_unit is not implemented for Ore polynomial rings "
|
|
425
|
+
"over base rings which are not integral domains")
|
|
426
|
+
|
|
427
|
+
def is_nilpotent(self):
|
|
428
|
+
r"""
|
|
429
|
+
Check if ``self`` is nilpotent.
|
|
430
|
+
|
|
431
|
+
.. NOTE::
|
|
432
|
+
|
|
433
|
+
The paper "Nilpotents and units in skew polynomial rings
|
|
434
|
+
over commutative rings" by M. Rimmer and K.R. Pearson describes
|
|
435
|
+
a method to check whether a given skew polynomial is nilpotent.
|
|
436
|
+
That method however, requires one to know the order of the
|
|
437
|
+
automorphism which is not available in Sage. This method is thus
|
|
438
|
+
not yet implemented.
|
|
439
|
+
|
|
440
|
+
EXAMPLES::
|
|
441
|
+
|
|
442
|
+
sage: R.<t> = ZZ[]
|
|
443
|
+
sage: sigma = R.hom([t+1])
|
|
444
|
+
sage: S.<x> = R['x',sigma]
|
|
445
|
+
sage: x.is_nilpotent()
|
|
446
|
+
Traceback (most recent call last):
|
|
447
|
+
...
|
|
448
|
+
NotImplementedError
|
|
449
|
+
"""
|
|
450
|
+
raise NotImplementedError
|
|
451
|
+
|
|
452
|
+
def is_monic(self):
|
|
453
|
+
r"""
|
|
454
|
+
Return ``True`` if this Ore polynomial is monic.
|
|
455
|
+
|
|
456
|
+
The zero polynomial is by definition not monic.
|
|
457
|
+
|
|
458
|
+
EXAMPLES::
|
|
459
|
+
|
|
460
|
+
sage: R.<t> = ZZ[]
|
|
461
|
+
sage: sigma = R.hom([t+1])
|
|
462
|
+
sage: S.<x> = R['x',sigma]
|
|
463
|
+
sage: a = x + t
|
|
464
|
+
sage: a.is_monic()
|
|
465
|
+
True
|
|
466
|
+
sage: a = 0*x
|
|
467
|
+
sage: a.is_monic()
|
|
468
|
+
False
|
|
469
|
+
sage: a = t*x^3 + x^4 + (t+1)*x^2
|
|
470
|
+
sage: a.is_monic()
|
|
471
|
+
True
|
|
472
|
+
sage: a = (t^2 + 2*t)*x^2 + x^3 + t^10*x^5
|
|
473
|
+
sage: a.is_monic()
|
|
474
|
+
False
|
|
475
|
+
"""
|
|
476
|
+
return self.leading_coefficient() == 1
|
|
477
|
+
|
|
478
|
+
def left_monic(self):
|
|
479
|
+
r"""
|
|
480
|
+
Return the unique monic Ore polynomial `m` which divides this
|
|
481
|
+
polynomial on the left and has the same degree.
|
|
482
|
+
|
|
483
|
+
Given an Ore polynomial `P` of degree `n`, its left monic is given by
|
|
484
|
+
`P \cdot \sigma^{-n}(1/k)`, where `k` is the leading coefficient of
|
|
485
|
+
`P` and `\sigma` is the twisting morphism.
|
|
486
|
+
|
|
487
|
+
EXAMPLES::
|
|
488
|
+
|
|
489
|
+
sage: # needs sage.rings.finite_rings
|
|
490
|
+
sage: k.<t> = GF(5^3)
|
|
491
|
+
sage: Frob = k.frobenius_endomorphism()
|
|
492
|
+
sage: S.<x> = k['x',Frob]
|
|
493
|
+
sage: a = (3*t^2 + 3*t + 2)*x^3 + (2*t^2 + 3)*x^2 + (4*t^2 + t + 4)*x + 2*t^2 + 2
|
|
494
|
+
sage: b = a.left_monic(); b
|
|
495
|
+
x^3 + (4*t^2 + 3*t)*x^2 + (4*t + 2)*x + 2*t^2 + 4*t + 3
|
|
496
|
+
|
|
497
|
+
Check list::
|
|
498
|
+
|
|
499
|
+
sage: # needs sage.rings.finite_rings
|
|
500
|
+
sage: b.degree() == a.degree()
|
|
501
|
+
True
|
|
502
|
+
sage: a.is_left_divisible_by(b)
|
|
503
|
+
True
|
|
504
|
+
sage: twist = S.twisting_morphism(-a.degree())
|
|
505
|
+
sage: a == b * twist(a.leading_coefficient())
|
|
506
|
+
True
|
|
507
|
+
|
|
508
|
+
Note that `b` does not divide `a` on the right::
|
|
509
|
+
|
|
510
|
+
sage: a.is_right_divisible_by(b) # needs sage.rings.finite_rings
|
|
511
|
+
False
|
|
512
|
+
|
|
513
|
+
This function does not work if the leading coefficient is not a
|
|
514
|
+
unit::
|
|
515
|
+
|
|
516
|
+
sage: R.<t> = QQ[]
|
|
517
|
+
sage: der = R.derivation()
|
|
518
|
+
sage: S.<x> = R['x', der]
|
|
519
|
+
sage: a = t*x
|
|
520
|
+
sage: a.left_monic()
|
|
521
|
+
Traceback (most recent call last):
|
|
522
|
+
...
|
|
523
|
+
NotImplementedError: the leading coefficient is not a unit
|
|
524
|
+
"""
|
|
525
|
+
try:
|
|
526
|
+
a = self.base_ring()(~self.leading_coefficient())
|
|
527
|
+
except (ZeroDivisionError, TypeError):
|
|
528
|
+
raise NotImplementedError("the leading coefficient is not a unit")
|
|
529
|
+
cdef Morphism m = self._parent.twisting_morphism(-self.degree())
|
|
530
|
+
if m is None:
|
|
531
|
+
return self * a
|
|
532
|
+
return self * m(a)
|
|
533
|
+
|
|
534
|
+
def right_monic(self):
|
|
535
|
+
r"""
|
|
536
|
+
Return the unique monic Ore polynomial which divides this polynomial
|
|
537
|
+
on the right and has the same degree.
|
|
538
|
+
|
|
539
|
+
Given an Ore polynomial `P` of degree `n`, its right monic is given by
|
|
540
|
+
`(1/k) \cdot P`, where `k` is the leading coefficient of `P`.
|
|
541
|
+
|
|
542
|
+
EXAMPLES::
|
|
543
|
+
|
|
544
|
+
sage: # needs sage.rings.finite_rings
|
|
545
|
+
sage: k.<t> = GF(5^3)
|
|
546
|
+
sage: Frob = k.frobenius_endomorphism()
|
|
547
|
+
sage: S.<x> = k['x',Frob]
|
|
548
|
+
sage: a = (3*t^2 + 3*t + 2)*x^3 + (2*t^2 + 3)*x^2 + (4*t^2 + t + 4)*x + 2*t^2 + 2
|
|
549
|
+
sage: b = a.right_monic(); b
|
|
550
|
+
x^3 + (2*t^2 + 3*t + 4)*x^2 + (3*t^2 + 4*t + 1)*x + 2*t^2 + 4*t + 3
|
|
551
|
+
|
|
552
|
+
Check list::
|
|
553
|
+
|
|
554
|
+
sage: b.degree() == a.degree() # needs sage.rings.finite_rings
|
|
555
|
+
True
|
|
556
|
+
sage: a.is_right_divisible_by(b) # needs sage.rings.finite_rings
|
|
557
|
+
True
|
|
558
|
+
sage: a == a.leading_coefficient() * b # needs sage.rings.finite_rings
|
|
559
|
+
True
|
|
560
|
+
|
|
561
|
+
Note that `b` does not divide `a` on the right::
|
|
562
|
+
|
|
563
|
+
sage: a.is_left_divisible_by(b) # needs sage.rings.finite_rings
|
|
564
|
+
False
|
|
565
|
+
|
|
566
|
+
This function does not work if the leading coefficient is not a
|
|
567
|
+
unit::
|
|
568
|
+
|
|
569
|
+
sage: R.<t> = QQ[]
|
|
570
|
+
sage: der = R.derivation()
|
|
571
|
+
sage: S.<x> = R['x', der]
|
|
572
|
+
sage: a = t*x
|
|
573
|
+
sage: a.right_monic()
|
|
574
|
+
Traceback (most recent call last):
|
|
575
|
+
...
|
|
576
|
+
NotImplementedError: the leading coefficient is not a unit
|
|
577
|
+
"""
|
|
578
|
+
try:
|
|
579
|
+
a = self.base_ring()(~self.leading_coefficient())
|
|
580
|
+
except (ZeroDivisionError, TypeError):
|
|
581
|
+
raise NotImplementedError("the leading coefficient is not a unit")
|
|
582
|
+
return a * self
|
|
583
|
+
|
|
584
|
+
cpdef _mod_(self, other):
|
|
585
|
+
r"""
|
|
586
|
+
Return the remainder in the *right* Euclidean division of
|
|
587
|
+
``self`` by ``other``.
|
|
588
|
+
|
|
589
|
+
TESTS::
|
|
590
|
+
|
|
591
|
+
sage: R.<t> = ZZ[]
|
|
592
|
+
sage: sigma = R.hom([t+1])
|
|
593
|
+
sage: S.<x> = R['x',sigma]
|
|
594
|
+
sage: b = x^2 + 2*t*x + 2
|
|
595
|
+
sage: a = (x+t)*b + t*x + 1
|
|
596
|
+
sage: a % b
|
|
597
|
+
t*x + 1
|
|
598
|
+
|
|
599
|
+
sage: (a*t).right_quo_rem(b*t)
|
|
600
|
+
Traceback (most recent call last):
|
|
601
|
+
...
|
|
602
|
+
NotImplementedError: the leading coefficient of the divisor is not invertible
|
|
603
|
+
"""
|
|
604
|
+
return self.right_quo_rem(other)[1]
|
|
605
|
+
|
|
606
|
+
cpdef _floordiv_(self, right):
|
|
607
|
+
r"""
|
|
608
|
+
Return the quotient of the *right* Euclidean division of
|
|
609
|
+
``self`` by ``right``.
|
|
610
|
+
|
|
611
|
+
The algorithm fails if the leading coefficient of the divisor
|
|
612
|
+
(``right``) is not invertible.
|
|
613
|
+
|
|
614
|
+
TESTS::
|
|
615
|
+
|
|
616
|
+
sage: R.<t> = QQ[]
|
|
617
|
+
sage: sigma = R.hom([t+1])
|
|
618
|
+
sage: S.<x> = R['x',sigma]
|
|
619
|
+
sage: b = x^2 + t
|
|
620
|
+
sage: a = (x^2 + t*x + 1)*b + t^3*x
|
|
621
|
+
sage: a // b
|
|
622
|
+
x^2 + t*x + 1
|
|
623
|
+
|
|
624
|
+
sage: (t*a) // (t*b)
|
|
625
|
+
Traceback (most recent call last):
|
|
626
|
+
...
|
|
627
|
+
NotImplementedError: the leading coefficient of the divisor is not invertible
|
|
628
|
+
"""
|
|
629
|
+
q, _ = self.right_quo_rem(right)
|
|
630
|
+
return q
|
|
631
|
+
|
|
632
|
+
cpdef _div_(self, right):
|
|
633
|
+
r"""
|
|
634
|
+
Return the quotient of this Ore polynomial by ``right``
|
|
635
|
+
in the fraction field.
|
|
636
|
+
|
|
637
|
+
INPUT:
|
|
638
|
+
|
|
639
|
+
- ``right`` -- an Ore polynomial
|
|
640
|
+
|
|
641
|
+
EXAMPLES::
|
|
642
|
+
|
|
643
|
+
sage: R.<t> = GF(11)[]
|
|
644
|
+
sage: der = R.derivation()
|
|
645
|
+
sage: S.<x> = R['x', der]
|
|
646
|
+
sage: f = t/x
|
|
647
|
+
sage: f
|
|
648
|
+
(x + 10/t)^(-1) * t
|
|
649
|
+
sage: f.parent()
|
|
650
|
+
Ore Function Field in x over
|
|
651
|
+
Fraction Field of Univariate Polynomial Ring in t over Finite Field of size 11 twisted by d/dt
|
|
652
|
+
"""
|
|
653
|
+
parent = self.parent().fraction_field()
|
|
654
|
+
return parent(self) / parent(right)
|
|
655
|
+
|
|
656
|
+
def is_left_divisible_by(self, other):
|
|
657
|
+
r"""
|
|
658
|
+
Check if ``self`` is divisible by ``other`` on the left.
|
|
659
|
+
|
|
660
|
+
INPUT:
|
|
661
|
+
|
|
662
|
+
- ``other`` -- an Ore polynomial in the same ring as ``self``
|
|
663
|
+
|
|
664
|
+
OUTPUT: boolean
|
|
665
|
+
|
|
666
|
+
EXAMPLES::
|
|
667
|
+
|
|
668
|
+
sage: # needs sage.rings.finite_rings
|
|
669
|
+
sage: k.<t> = GF(5^3)
|
|
670
|
+
sage: Frob = k.frobenius_endomorphism()
|
|
671
|
+
sage: S.<x> = k['x',Frob]
|
|
672
|
+
sage: a = x^2 + t*x + t^2 + 3
|
|
673
|
+
sage: b = x^3 + (t + 1)*x^2 + 1
|
|
674
|
+
sage: c = a*b
|
|
675
|
+
sage: c.is_left_divisible_by(a)
|
|
676
|
+
True
|
|
677
|
+
sage: c.is_left_divisible_by(b)
|
|
678
|
+
False
|
|
679
|
+
|
|
680
|
+
Divisibility by `0` does not make sense::
|
|
681
|
+
|
|
682
|
+
sage: c.is_left_divisible_by(S(0)) # needs sage.rings.finite_rings
|
|
683
|
+
Traceback (most recent call last):
|
|
684
|
+
...
|
|
685
|
+
ZeroDivisionError: division by zero is not valid
|
|
686
|
+
"""
|
|
687
|
+
_, r = self.left_quo_rem(other)
|
|
688
|
+
return r.is_zero()
|
|
689
|
+
|
|
690
|
+
def is_right_divisible_by(self, other):
|
|
691
|
+
r"""
|
|
692
|
+
Check if ``self`` is divisible by ``other`` on the right.
|
|
693
|
+
|
|
694
|
+
INPUT:
|
|
695
|
+
|
|
696
|
+
- ``other`` -- an Ore polynomial in the same ring as ``self``
|
|
697
|
+
|
|
698
|
+
OUTPUT: boolean
|
|
699
|
+
|
|
700
|
+
EXAMPLES::
|
|
701
|
+
|
|
702
|
+
sage: # needs sage.rings.finite_rings
|
|
703
|
+
sage: k.<t> = GF(5^3)
|
|
704
|
+
sage: Frob = k.frobenius_endomorphism()
|
|
705
|
+
sage: S.<x> = k['x',Frob]
|
|
706
|
+
sage: a = x^2 + t*x + t^2 + 3
|
|
707
|
+
sage: b = x^3 + (t + 1)*x^2 + 1
|
|
708
|
+
sage: c = a*b
|
|
709
|
+
sage: c.is_right_divisible_by(a)
|
|
710
|
+
False
|
|
711
|
+
sage: c.is_right_divisible_by(b)
|
|
712
|
+
True
|
|
713
|
+
|
|
714
|
+
Divisibility by `0` does not make sense::
|
|
715
|
+
|
|
716
|
+
sage: c.is_right_divisible_by(S(0)) # needs sage.rings.finite_rings
|
|
717
|
+
Traceback (most recent call last):
|
|
718
|
+
...
|
|
719
|
+
ZeroDivisionError: division by zero is not valid
|
|
720
|
+
|
|
721
|
+
This function does not work if the leading coefficient of the divisor
|
|
722
|
+
is not a unit::
|
|
723
|
+
|
|
724
|
+
sage: R.<t> = QQ[]
|
|
725
|
+
sage: sigma = R.hom([t+1])
|
|
726
|
+
sage: S.<x> = R['x',sigma]
|
|
727
|
+
sage: a = x^2 + 2*x + t
|
|
728
|
+
sage: b = (t+1)*x + t^2
|
|
729
|
+
sage: c = a*b
|
|
730
|
+
sage: c.is_right_divisible_by(b)
|
|
731
|
+
Traceback (most recent call last):
|
|
732
|
+
...
|
|
733
|
+
NotImplementedError: the leading coefficient of the divisor is not invertible
|
|
734
|
+
"""
|
|
735
|
+
_, r = self.right_quo_rem(other)
|
|
736
|
+
return r.is_zero()
|
|
737
|
+
|
|
738
|
+
def left_divides(self, other):
|
|
739
|
+
r"""
|
|
740
|
+
Check if ``self`` divides ``other`` on the left.
|
|
741
|
+
|
|
742
|
+
INPUT:
|
|
743
|
+
|
|
744
|
+
- ``other`` -- an Ore polynomial in the same ring as ``self``
|
|
745
|
+
|
|
746
|
+
OUTPUT: boolean
|
|
747
|
+
|
|
748
|
+
EXAMPLES::
|
|
749
|
+
|
|
750
|
+
sage: # needs sage.rings.finite_rings
|
|
751
|
+
sage: k.<t> = GF(5^3)
|
|
752
|
+
sage: Frob = k.frobenius_endomorphism()
|
|
753
|
+
sage: S.<x> = k['x',Frob]
|
|
754
|
+
sage: a = x^2 + t*x + t^2 + 3
|
|
755
|
+
sage: b = x^3 + (t + 1)*x^2 + 1
|
|
756
|
+
sage: c = a * b
|
|
757
|
+
sage: a.left_divides(c)
|
|
758
|
+
True
|
|
759
|
+
sage: b.left_divides(c)
|
|
760
|
+
False
|
|
761
|
+
|
|
762
|
+
Divisibility by `0` does not make sense::
|
|
763
|
+
|
|
764
|
+
sage: S(0).left_divides(c) # needs sage.rings.finite_rings
|
|
765
|
+
Traceback (most recent call last):
|
|
766
|
+
...
|
|
767
|
+
ZeroDivisionError: division by zero is not valid
|
|
768
|
+
"""
|
|
769
|
+
_, r = other.left_quo_rem(self)
|
|
770
|
+
return r.is_zero()
|
|
771
|
+
|
|
772
|
+
def right_divides(self, other):
|
|
773
|
+
r"""
|
|
774
|
+
Check if ``self`` divides ``other`` on the right.
|
|
775
|
+
|
|
776
|
+
INPUT:
|
|
777
|
+
|
|
778
|
+
- ``other`` -- an Ore polynomial in the same ring as ``self``
|
|
779
|
+
|
|
780
|
+
OUTPUT: boolean
|
|
781
|
+
|
|
782
|
+
EXAMPLES::
|
|
783
|
+
|
|
784
|
+
sage: # needs sage.rings.finite_rings
|
|
785
|
+
sage: k.<t> = GF(5^3)
|
|
786
|
+
sage: Frob = k.frobenius_endomorphism()
|
|
787
|
+
sage: S.<x> = k['x',Frob]
|
|
788
|
+
sage: a = x^2 + t*x + t^2 + 3
|
|
789
|
+
sage: b = x^3 + (t + 1)*x^2 + 1
|
|
790
|
+
sage: c = a * b
|
|
791
|
+
sage: a.right_divides(c)
|
|
792
|
+
False
|
|
793
|
+
sage: b.right_divides(c)
|
|
794
|
+
True
|
|
795
|
+
|
|
796
|
+
Divisibility by `0` does not make sense::
|
|
797
|
+
|
|
798
|
+
sage: S(0).right_divides(c) # needs sage.rings.finite_rings
|
|
799
|
+
Traceback (most recent call last):
|
|
800
|
+
...
|
|
801
|
+
ZeroDivisionError: division by zero is not valid
|
|
802
|
+
|
|
803
|
+
This function does not work if the leading coefficient of the divisor
|
|
804
|
+
is not a unit::
|
|
805
|
+
|
|
806
|
+
sage: R.<t> = QQ[]
|
|
807
|
+
sage: sigma = R.hom([t+1])
|
|
808
|
+
sage: S.<x> = R['x',sigma]
|
|
809
|
+
sage: a = x^2 + 2*x + t
|
|
810
|
+
sage: b = (t+1)*x + t^2
|
|
811
|
+
sage: c = a*b
|
|
812
|
+
sage: b.right_divides(c)
|
|
813
|
+
Traceback (most recent call last):
|
|
814
|
+
...
|
|
815
|
+
NotImplementedError: the leading coefficient of the divisor is not invertible
|
|
816
|
+
"""
|
|
817
|
+
_, r = other.right_quo_rem(self)
|
|
818
|
+
return r.is_zero()
|
|
819
|
+
|
|
820
|
+
@coerce_binop
|
|
821
|
+
def left_xgcd(self, other, monic=True):
|
|
822
|
+
r"""
|
|
823
|
+
Return the left gcd of ``self`` and ``other`` along with the
|
|
824
|
+
coefficients for the linear combination.
|
|
825
|
+
|
|
826
|
+
If `a` is ``self`` and `b` is ``other``, then there are Ore polynomials
|
|
827
|
+
`u` and `v` such that `g = a u + b v`, where `g` is the left gcd of `a`
|
|
828
|
+
and `b`. This method returns `(g, u, v)`.
|
|
829
|
+
|
|
830
|
+
INPUT:
|
|
831
|
+
|
|
832
|
+
- ``other`` -- an Ore polynomial in the same ring as ``self``
|
|
833
|
+
|
|
834
|
+
- ``monic`` -- boolean (default: ``True``); return whether the left gcd
|
|
835
|
+
should be normalized to be monic
|
|
836
|
+
|
|
837
|
+
OUTPUT:
|
|
838
|
+
|
|
839
|
+
- The left gcd of ``self`` and ``other``, that is an Ore polynomial
|
|
840
|
+
`g` with the following property: any Ore polynomial is
|
|
841
|
+
divisible on the left by `g` iff it is divisible on the left
|
|
842
|
+
by both ``self`` and ``other``.
|
|
843
|
+
If monic is ``True``, `g` is in addition monic. (With this
|
|
844
|
+
extra condition, it is uniquely determined.)
|
|
845
|
+
|
|
846
|
+
- Two Ore polynomials `u` and `v` such that:
|
|
847
|
+
|
|
848
|
+
.. MATH::
|
|
849
|
+
|
|
850
|
+
g = a \cdot u + b \cdot v,
|
|
851
|
+
|
|
852
|
+
where `s` is ``self`` and `b` is ``other``.
|
|
853
|
+
|
|
854
|
+
.. NOTE::
|
|
855
|
+
|
|
856
|
+
Works only if following two conditions are fulfilled
|
|
857
|
+
(otherwise left gcd do not exist in general):
|
|
858
|
+
1) the base ring is a field and
|
|
859
|
+
2) the twisting morphism is bijective.
|
|
860
|
+
|
|
861
|
+
EXAMPLES::
|
|
862
|
+
|
|
863
|
+
sage: # needs sage.rings.finite_rings
|
|
864
|
+
sage: k.<t> = GF(5^3)
|
|
865
|
+
sage: Frob = k.frobenius_endomorphism()
|
|
866
|
+
sage: S.<x> = k['x',Frob]
|
|
867
|
+
sage: a = (x + t) * (x^2 + t*x + 1)
|
|
868
|
+
sage: b = 2 * (x + t) * (x^3 + (t+1)*x^2 + t^2)
|
|
869
|
+
sage: g,u,v = a.left_xgcd(b); g
|
|
870
|
+
x + t
|
|
871
|
+
sage: a*u + b*v == g
|
|
872
|
+
True
|
|
873
|
+
|
|
874
|
+
Specifying ``monic=False``, we *can* get a nonmonic gcd::
|
|
875
|
+
|
|
876
|
+
sage: g,u,v = a.left_xgcd(b, monic=False); g # needs sage.rings.finite_rings
|
|
877
|
+
2*t*x + 4*t + 2
|
|
878
|
+
sage: a*u + b*v == g # needs sage.rings.finite_rings
|
|
879
|
+
True
|
|
880
|
+
|
|
881
|
+
The base ring must be a field::
|
|
882
|
+
|
|
883
|
+
sage: R.<t> = QQ[]
|
|
884
|
+
sage: sigma = R.hom([t+1])
|
|
885
|
+
sage: S.<x> = R['x',sigma]
|
|
886
|
+
sage: a = (x + t) * (x^2 + t*x + 1)
|
|
887
|
+
sage: b = 2 * (x + t) * (x^3 + (t+1)*x^2 + t^2)
|
|
888
|
+
sage: a.left_xgcd(b)
|
|
889
|
+
Traceback (most recent call last):
|
|
890
|
+
...
|
|
891
|
+
TypeError: the base ring must be a field
|
|
892
|
+
|
|
893
|
+
And the twisting morphism must be bijective::
|
|
894
|
+
|
|
895
|
+
sage: FR = R.fraction_field()
|
|
896
|
+
sage: f = FR.hom([FR(t)^2])
|
|
897
|
+
sage: S.<x> = FR['x',f]
|
|
898
|
+
sage: a = (x + t) * (x^2 + t*x + 1)
|
|
899
|
+
sage: b = 2 * (x + t) * (x^3 + (t+1)*x^2 + t^2)
|
|
900
|
+
sage: a.left_xgcd(b)
|
|
901
|
+
Traceback (most recent call last):
|
|
902
|
+
...
|
|
903
|
+
NotImplementedError: inversion of the twisting morphism Ring endomorphism of Fraction Field of Univariate Polynomial Ring in t over Rational Field
|
|
904
|
+
Defn: t |--> t^2
|
|
905
|
+
"""
|
|
906
|
+
if self.base_ring() not in _Fields:
|
|
907
|
+
raise TypeError("the base ring must be a field")
|
|
908
|
+
cdef OrePolynomial G = self
|
|
909
|
+
cdef OrePolynomial U = self._parent.one()
|
|
910
|
+
cdef OrePolynomial V, V1, Q, R, T
|
|
911
|
+
cdef Morphism m
|
|
912
|
+
if not other:
|
|
913
|
+
V = self._parent.zero()
|
|
914
|
+
else:
|
|
915
|
+
V1 = self._parent.zero()
|
|
916
|
+
V3 = other
|
|
917
|
+
while V3:
|
|
918
|
+
Q, R = G._left_quo_rem(V3)
|
|
919
|
+
T = U - V1 * Q
|
|
920
|
+
U = V1
|
|
921
|
+
G = V3
|
|
922
|
+
V1 = T
|
|
923
|
+
V3 = R
|
|
924
|
+
V = G - self * U
|
|
925
|
+
V, _ = V._left_quo_rem(other)
|
|
926
|
+
if monic:
|
|
927
|
+
lc = ~G.leading_coefficient()
|
|
928
|
+
m = self._parent.twisting_morphism(-G.degree())
|
|
929
|
+
if m is not None:
|
|
930
|
+
lc = m(lc)
|
|
931
|
+
G = G * lc
|
|
932
|
+
U = U * lc
|
|
933
|
+
V = V * lc
|
|
934
|
+
return G, U, V
|
|
935
|
+
|
|
936
|
+
cdef _left_quo_rem(self, OrePolynomial other):
|
|
937
|
+
r"""
|
|
938
|
+
Return the quotient and remainder of the left Euclidean
|
|
939
|
+
division of ``self`` by ``other`` (C implementation).
|
|
940
|
+
|
|
941
|
+
Must be implemented in subclasses.
|
|
942
|
+
"""
|
|
943
|
+
raise NotImplementedError("left Euclidean division is not implemented")
|
|
944
|
+
|
|
945
|
+
@coerce_binop
|
|
946
|
+
def left_quo_rem(self, other):
|
|
947
|
+
r"""
|
|
948
|
+
Return the quotient and remainder of the left Euclidean
|
|
949
|
+
division of ``self`` by ``other``.
|
|
950
|
+
|
|
951
|
+
INPUT:
|
|
952
|
+
|
|
953
|
+
- ``other`` -- an Ore polynomial in the same ring as ``self``
|
|
954
|
+
|
|
955
|
+
OUTPUT:
|
|
956
|
+
|
|
957
|
+
- the quotient and the remainder of the left Euclidean
|
|
958
|
+
division of this Ore polynomial by ``other``
|
|
959
|
+
|
|
960
|
+
.. NOTE::
|
|
961
|
+
|
|
962
|
+
This will fail if the leading coefficient of ``other`` is not a unit
|
|
963
|
+
or if Sage can't invert the twisting morphism.
|
|
964
|
+
|
|
965
|
+
EXAMPLES::
|
|
966
|
+
|
|
967
|
+
sage: # needs sage.rings.finite_rings
|
|
968
|
+
sage: k.<t> = GF(5^3)
|
|
969
|
+
sage: Frob = k.frobenius_endomorphism()
|
|
970
|
+
sage: S.<x> = k['x',Frob]
|
|
971
|
+
sage: a = (3*t^2 + 3*t + 2)*x^3 + (2*t^2 + 3)*x^2 + (4*t^2 + t + 4)*x + 2*t^2 + 2
|
|
972
|
+
sage: b = (3*t^2 + 4*t + 2)*x^2 + (2*t^2 + 4*t + 3)*x + 2*t^2 + t + 1
|
|
973
|
+
sage: q,r = a.left_quo_rem(b)
|
|
974
|
+
sage: a == b*q + r
|
|
975
|
+
True
|
|
976
|
+
|
|
977
|
+
In the following example, Sage does not know the inverse
|
|
978
|
+
of the twisting morphism::
|
|
979
|
+
|
|
980
|
+
sage: R.<t> = QQ[]
|
|
981
|
+
sage: K = R.fraction_field()
|
|
982
|
+
sage: sigma = K.hom([(t+1)/(t-1)])
|
|
983
|
+
sage: S.<x> = K['x',sigma]
|
|
984
|
+
sage: a = (-2*t^2 - t + 1)*x^3 + (-t^2 + t)*x^2 + (-12*t - 2)*x - t^2 - 95*t + 1
|
|
985
|
+
sage: b = x^2 + (5*t - 6)*x - 4*t^2 + 4*t - 1
|
|
986
|
+
sage: a.left_quo_rem(b)
|
|
987
|
+
Traceback (most recent call last):
|
|
988
|
+
...
|
|
989
|
+
NotImplementedError: inversion of the twisting morphism Ring endomorphism of Fraction Field of Univariate Polynomial Ring in t over Rational Field
|
|
990
|
+
Defn: t |--> (t + 1)/(t - 1)
|
|
991
|
+
"""
|
|
992
|
+
if not other:
|
|
993
|
+
raise ZeroDivisionError("division by zero is not valid")
|
|
994
|
+
return self._left_quo_rem(other)
|
|
995
|
+
|
|
996
|
+
cdef _right_quo_rem(self, OrePolynomial other):
|
|
997
|
+
r"""
|
|
998
|
+
Return the quotient and remainder of the right Euclidean
|
|
999
|
+
division of ``self`` by ``other`` (C implementation).
|
|
1000
|
+
|
|
1001
|
+
Must be implemented in subclasses.
|
|
1002
|
+
"""
|
|
1003
|
+
raise NotImplementedError("right Euclidean division is not implemented")
|
|
1004
|
+
|
|
1005
|
+
@coerce_binop
|
|
1006
|
+
def right_quo_rem(self, other):
|
|
1007
|
+
r"""
|
|
1008
|
+
Return the quotient and remainder of the right Euclidean
|
|
1009
|
+
division of ``self`` by ``other``.
|
|
1010
|
+
|
|
1011
|
+
INPUT:
|
|
1012
|
+
|
|
1013
|
+
- ``other`` -- an Ore polynomial in the same ring as ``self``
|
|
1014
|
+
|
|
1015
|
+
OUTPUT:
|
|
1016
|
+
|
|
1017
|
+
- the quotient and the remainder of the right Euclidean
|
|
1018
|
+
division of this Ore polynomial by ``other``
|
|
1019
|
+
|
|
1020
|
+
.. NOTE::
|
|
1021
|
+
|
|
1022
|
+
This will fail if the leading coefficient of the divisor
|
|
1023
|
+
is not a unit.
|
|
1024
|
+
|
|
1025
|
+
EXAMPLES::
|
|
1026
|
+
|
|
1027
|
+
sage: R.<t> = ZZ[]
|
|
1028
|
+
sage: sigma = R.hom([t+1])
|
|
1029
|
+
sage: S.<x> = R['x',sigma]
|
|
1030
|
+
sage: a = S.random_element(degree=4)
|
|
1031
|
+
sage: b = S.random_element(monic=True)
|
|
1032
|
+
sage: q,r = a.right_quo_rem(b)
|
|
1033
|
+
sage: a == q*b + r
|
|
1034
|
+
True
|
|
1035
|
+
|
|
1036
|
+
The leading coefficient of the divisor need to be invertible::
|
|
1037
|
+
|
|
1038
|
+
sage: a.right_quo_rem(S(0))
|
|
1039
|
+
Traceback (most recent call last):
|
|
1040
|
+
...
|
|
1041
|
+
ZeroDivisionError: division by zero is not valid
|
|
1042
|
+
sage: c = S.random_element()
|
|
1043
|
+
sage: while not c or c.leading_coefficient().is_unit():
|
|
1044
|
+
....: c = S.random_element()
|
|
1045
|
+
sage: while a.degree() < c.degree():
|
|
1046
|
+
....: a = S.random_element(degree=4)
|
|
1047
|
+
sage: a.right_quo_rem(c)
|
|
1048
|
+
Traceback (most recent call last):
|
|
1049
|
+
...
|
|
1050
|
+
NotImplementedError: the leading coefficient of the divisor is not invertible
|
|
1051
|
+
"""
|
|
1052
|
+
if not other:
|
|
1053
|
+
raise ZeroDivisionError("division by zero is not valid")
|
|
1054
|
+
return self._right_quo_rem(other)
|
|
1055
|
+
|
|
1056
|
+
@coerce_binop
|
|
1057
|
+
def right_xgcd(self, other, monic=True):
|
|
1058
|
+
r"""
|
|
1059
|
+
Return the right gcd of ``self`` and ``other`` along with the
|
|
1060
|
+
coefficients for the linear combination.
|
|
1061
|
+
|
|
1062
|
+
If `a` is ``self`` and `b` is ``other``, then there are Ore polynomials
|
|
1063
|
+
`u` and `v` such that `g = u a + v b`, where `g` is the right gcd of `a`
|
|
1064
|
+
and `b`. This method returns `(g, u, v)`.
|
|
1065
|
+
|
|
1066
|
+
INPUT:
|
|
1067
|
+
|
|
1068
|
+
- ``other`` -- an Ore polynomial in the same ring as ``self``
|
|
1069
|
+
|
|
1070
|
+
- ``monic`` -- boolean (default: ``True``); return whether the right gcd
|
|
1071
|
+
should be normalized to be monic
|
|
1072
|
+
|
|
1073
|
+
OUTPUT:
|
|
1074
|
+
|
|
1075
|
+
- The right gcd of ``self`` and ``other``, that is an Ore polynomial
|
|
1076
|
+
`g` with the following property: any Ore polynomial is
|
|
1077
|
+
divisible on the right by `g` iff it is divisible on the right
|
|
1078
|
+
by both ``self`` and ``other``.
|
|
1079
|
+
If monic is ``True``, `g` is in addition monic. (With this
|
|
1080
|
+
extra condition, it is uniquely determined.)
|
|
1081
|
+
|
|
1082
|
+
- Two Ore polynomials `u` and `v` such that:
|
|
1083
|
+
|
|
1084
|
+
.. MATH::
|
|
1085
|
+
|
|
1086
|
+
g = u \cdot a + v \cdot b
|
|
1087
|
+
|
|
1088
|
+
where `a` is ``self`` and `b` is ``other``.
|
|
1089
|
+
|
|
1090
|
+
.. NOTE::
|
|
1091
|
+
|
|
1092
|
+
Works only if the base ring is a field (otherwise right
|
|
1093
|
+
gcd do not exist in general).
|
|
1094
|
+
|
|
1095
|
+
EXAMPLES::
|
|
1096
|
+
|
|
1097
|
+
sage: # needs sage.rings.finite_rings
|
|
1098
|
+
sage: k.<t> = GF(5^3)
|
|
1099
|
+
sage: Frob = k.frobenius_endomorphism()
|
|
1100
|
+
sage: S.<x> = k['x',Frob]
|
|
1101
|
+
sage: a = (x^2 + t*x + 1) * (x + t)
|
|
1102
|
+
sage: b = 2 * (x^3 + (t+1)*x^2 + t^2) * (x + t)
|
|
1103
|
+
sage: g,u,v = a.right_xgcd(b); g
|
|
1104
|
+
x + t
|
|
1105
|
+
sage: u*a + v*b == g
|
|
1106
|
+
True
|
|
1107
|
+
|
|
1108
|
+
Specifying ``monic=False``, we *can* get a nonmonic gcd::
|
|
1109
|
+
|
|
1110
|
+
sage: g,u,v = a.right_xgcd(b, monic=False); g # needs sage.rings.finite_rings
|
|
1111
|
+
(4*t^2 + 4*t + 1)*x + 4*t^2 + 4*t + 3
|
|
1112
|
+
sage: u*a + v*b == g # needs sage.rings.finite_rings
|
|
1113
|
+
True
|
|
1114
|
+
|
|
1115
|
+
The base ring must be a field::
|
|
1116
|
+
|
|
1117
|
+
sage: R.<t> = QQ[]
|
|
1118
|
+
sage: sigma = R.hom([t+1])
|
|
1119
|
+
sage: S.<x> = R['x',sigma]
|
|
1120
|
+
sage: a = (x^2 + t*x + 1) * (x + t)
|
|
1121
|
+
sage: b = 2 * (x^3 + (t+1)*x^2 + t^2) * (x + t)
|
|
1122
|
+
sage: a.right_xgcd(b)
|
|
1123
|
+
Traceback (most recent call last):
|
|
1124
|
+
...
|
|
1125
|
+
TypeError: the base ring must be a field
|
|
1126
|
+
"""
|
|
1127
|
+
if self.base_ring() not in _Fields:
|
|
1128
|
+
raise TypeError("the base ring must be a field")
|
|
1129
|
+
cdef OrePolynomial G = self
|
|
1130
|
+
cdef OrePolynomial U = self._parent.one()
|
|
1131
|
+
cdef OrePolynomial V, V1, V3, Q, R, T
|
|
1132
|
+
if other.is_zero():
|
|
1133
|
+
V = self._parent.zero()
|
|
1134
|
+
else:
|
|
1135
|
+
V1 = self._parent.zero()
|
|
1136
|
+
V3 = other
|
|
1137
|
+
while not V3.is_zero():
|
|
1138
|
+
Q, R = G._right_quo_rem(V3)
|
|
1139
|
+
T = U - Q * V1
|
|
1140
|
+
U = V1
|
|
1141
|
+
G = V3
|
|
1142
|
+
V1 = T
|
|
1143
|
+
V3 = R
|
|
1144
|
+
V = G - U * self
|
|
1145
|
+
V, _ = V._right_quo_rem(other)
|
|
1146
|
+
if monic:
|
|
1147
|
+
lc = ~G.leading_coefficient()
|
|
1148
|
+
G = lc * G
|
|
1149
|
+
U = lc * U
|
|
1150
|
+
V = lc * V
|
|
1151
|
+
return G, U, V
|
|
1152
|
+
|
|
1153
|
+
@coerce_binop
|
|
1154
|
+
def right_gcd(self, other, monic=True):
|
|
1155
|
+
r"""
|
|
1156
|
+
Return the right gcd of ``self`` and ``other``.
|
|
1157
|
+
|
|
1158
|
+
INPUT:
|
|
1159
|
+
|
|
1160
|
+
- ``other`` -- an Ore polynomial in the same ring as ``self``
|
|
1161
|
+
|
|
1162
|
+
- ``monic`` -- boolean (default: ``True``); return whether the right gcd
|
|
1163
|
+
should be normalized to be monic
|
|
1164
|
+
|
|
1165
|
+
OUTPUT:
|
|
1166
|
+
|
|
1167
|
+
The right gcd of ``self`` and ``other``, that is an Ore polynomial
|
|
1168
|
+
`g` with the following property: any Ore polynomial is
|
|
1169
|
+
divisible on the right by `g` iff it is divisible on the right
|
|
1170
|
+
by both ``self`` and ``other``.
|
|
1171
|
+
If monic is ``True``, `g` is in addition monic. (With this
|
|
1172
|
+
extra condition, it is uniquely determined.)
|
|
1173
|
+
|
|
1174
|
+
.. NOTE::
|
|
1175
|
+
|
|
1176
|
+
Works only if the base ring is a field (otherwise right
|
|
1177
|
+
gcd do not exist in general).
|
|
1178
|
+
|
|
1179
|
+
EXAMPLES::
|
|
1180
|
+
|
|
1181
|
+
sage: # needs sage.rings.finite_rings
|
|
1182
|
+
sage: k.<t> = GF(5^3)
|
|
1183
|
+
sage: Frob = k.frobenius_endomorphism()
|
|
1184
|
+
sage: S.<x> = k['x',Frob]
|
|
1185
|
+
sage: a = (x^2 + t*x + 1) * (x + t)
|
|
1186
|
+
sage: b = 2 * (x^3 + (t+1)*x^2 + t^2) * (x + t)
|
|
1187
|
+
sage: a.right_gcd(b)
|
|
1188
|
+
x + t
|
|
1189
|
+
|
|
1190
|
+
Specifying ``monic=False``, we *can* get a nonmonic gcd::
|
|
1191
|
+
|
|
1192
|
+
sage: a.right_gcd(b,monic=False) # needs sage.rings.finite_rings
|
|
1193
|
+
(4*t^2 + 4*t + 1)*x + 4*t^2 + 4*t + 3
|
|
1194
|
+
|
|
1195
|
+
The base ring need to be a field::
|
|
1196
|
+
|
|
1197
|
+
sage: R.<t> = QQ[]
|
|
1198
|
+
sage: sigma = R.hom([t+1])
|
|
1199
|
+
sage: S.<x> = R['x',sigma]
|
|
1200
|
+
sage: a = (x^2 + t*x + 1) * (x + t)
|
|
1201
|
+
sage: b = 2 * (x^3 + (t+1)*x^2 + t^2) * (x + t)
|
|
1202
|
+
sage: a.right_gcd(b)
|
|
1203
|
+
Traceback (most recent call last):
|
|
1204
|
+
...
|
|
1205
|
+
TypeError: the base ring must be a field
|
|
1206
|
+
"""
|
|
1207
|
+
if self.base_ring() not in _Fields:
|
|
1208
|
+
raise TypeError("the base ring must be a field")
|
|
1209
|
+
if other.is_zero():
|
|
1210
|
+
return self
|
|
1211
|
+
cdef OrePolynomial A = self
|
|
1212
|
+
cdef OrePolynomial B = other
|
|
1213
|
+
while not B.is_zero():
|
|
1214
|
+
A, B = B, A % B
|
|
1215
|
+
if monic:
|
|
1216
|
+
A = A.right_monic()
|
|
1217
|
+
return A
|
|
1218
|
+
|
|
1219
|
+
@coerce_binop
|
|
1220
|
+
def left_gcd(self, other, monic=True):
|
|
1221
|
+
r"""
|
|
1222
|
+
Return the left gcd of ``self`` and ``other``.
|
|
1223
|
+
|
|
1224
|
+
INPUT:
|
|
1225
|
+
|
|
1226
|
+
- ``other`` -- an Ore polynomial in the same ring as ``self``
|
|
1227
|
+
|
|
1228
|
+
- ``monic`` -- boolean (default: ``True``); return whether the left gcd
|
|
1229
|
+
should be normalized to be monic
|
|
1230
|
+
|
|
1231
|
+
OUTPUT:
|
|
1232
|
+
|
|
1233
|
+
The left gcd of ``self`` and ``other``, that is an Ore polynomial
|
|
1234
|
+
`g` with the following property: any Ore polynomial is
|
|
1235
|
+
divisible on the left by `g` iff it is divisible on the left
|
|
1236
|
+
by both ``self`` and ``other``.
|
|
1237
|
+
If monic is ``True``, `g` is in addition monic. (With this
|
|
1238
|
+
extra condition, it is uniquely determined.)
|
|
1239
|
+
|
|
1240
|
+
.. NOTE::
|
|
1241
|
+
|
|
1242
|
+
Works only if following two conditions are fulfilled
|
|
1243
|
+
(otherwise left gcd do not exist in general):
|
|
1244
|
+
1) the base ring is a field and
|
|
1245
|
+
2) the twisting morphism is bijective.
|
|
1246
|
+
|
|
1247
|
+
EXAMPLES::
|
|
1248
|
+
|
|
1249
|
+
sage: # needs sage.rings.finite_rings
|
|
1250
|
+
sage: k.<t> = GF(5^3)
|
|
1251
|
+
sage: Frob = k.frobenius_endomorphism()
|
|
1252
|
+
sage: S.<x> = k['x',Frob]
|
|
1253
|
+
sage: a = (x + t) * (x^2 + t*x + 1)
|
|
1254
|
+
sage: b = 2 * (x + t) * (x^3 + (t+1)*x^2 + t^2)
|
|
1255
|
+
sage: a.left_gcd(b)
|
|
1256
|
+
x + t
|
|
1257
|
+
|
|
1258
|
+
Specifying ``monic=False``, we *can* get a nonmonic gcd::
|
|
1259
|
+
|
|
1260
|
+
sage: a.left_gcd(b,monic=False) # needs sage.rings.finite_rings
|
|
1261
|
+
2*t*x + 4*t + 2
|
|
1262
|
+
|
|
1263
|
+
The base ring needs to be a field::
|
|
1264
|
+
|
|
1265
|
+
sage: # needs sage.rings.finite_rings
|
|
1266
|
+
sage: R.<t> = QQ[]
|
|
1267
|
+
sage: sigma = R.hom([t + 1])
|
|
1268
|
+
sage: S.<x> = R['x',sigma]
|
|
1269
|
+
sage: a = (x + t) * (x^2 + t*x + 1)
|
|
1270
|
+
sage: b = 2 * (x + t) * (x^3 + (t+1)*x^2 + t^2)
|
|
1271
|
+
sage: a.left_gcd(b)
|
|
1272
|
+
Traceback (most recent call last):
|
|
1273
|
+
...
|
|
1274
|
+
TypeError: the base ring must be a field
|
|
1275
|
+
|
|
1276
|
+
And the twisting morphism needs to be bijective::
|
|
1277
|
+
|
|
1278
|
+
sage: # needs sage.rings.finite_rings
|
|
1279
|
+
sage: FR = R.fraction_field()
|
|
1280
|
+
sage: f = FR.hom([FR(t)^2])
|
|
1281
|
+
sage: S.<x> = FR['x',f]
|
|
1282
|
+
sage: a = (x + t) * (x^2 + t*x + 1)
|
|
1283
|
+
sage: b = 2 * (x + t) * (x^3 + (t+1)*x^2 + t^2)
|
|
1284
|
+
sage: a.left_gcd(b)
|
|
1285
|
+
Traceback (most recent call last):
|
|
1286
|
+
...
|
|
1287
|
+
NotImplementedError: inversion of the twisting morphism Ring endomorphism
|
|
1288
|
+
of Fraction Field of Univariate Polynomial Ring in t over Rational Field
|
|
1289
|
+
Defn: t |--> t^2
|
|
1290
|
+
"""
|
|
1291
|
+
if self.base_ring() not in _Fields:
|
|
1292
|
+
raise TypeError("the base ring must be a field")
|
|
1293
|
+
if other.is_zero():
|
|
1294
|
+
return self
|
|
1295
|
+
cdef OrePolynomial A_, A = self
|
|
1296
|
+
cdef OrePolynomial B = other
|
|
1297
|
+
while not B.is_zero():
|
|
1298
|
+
A_ = A
|
|
1299
|
+
A = B
|
|
1300
|
+
_, B = A_._left_quo_rem(B)
|
|
1301
|
+
if monic:
|
|
1302
|
+
A = A.left_monic()
|
|
1303
|
+
return A
|
|
1304
|
+
|
|
1305
|
+
cdef OrePolynomial _left_lcm_cofactor(self, OrePolynomial other):
|
|
1306
|
+
r"""
|
|
1307
|
+
Return an Ore polynomial `U` such that `U P = c L`
|
|
1308
|
+
where `P` is this Ore polynomial (``self``), `L`
|
|
1309
|
+
is the left lcm of `P` and ``other`` and `c` is a
|
|
1310
|
+
constant
|
|
1311
|
+
|
|
1312
|
+
TESTS::
|
|
1313
|
+
|
|
1314
|
+
sage: # needs sage.misc.cython sage.rings.finite_rings
|
|
1315
|
+
sage: cython(
|
|
1316
|
+
....: '''
|
|
1317
|
+
....: from sage.rings.polynomial.ore_polynomial_element cimport OrePolynomial
|
|
1318
|
+
....: def left_lcm_cofactor(OrePolynomial P, OrePolynomial Q):
|
|
1319
|
+
....: return P._left_lcm_cofactor(Q)
|
|
1320
|
+
....: ''')
|
|
1321
|
+
sage: k.<a> = GF(7^5)
|
|
1322
|
+
sage: Frob = k.frobenius_endomorphism(3)
|
|
1323
|
+
sage: S.<x> = k['x', Frob]
|
|
1324
|
+
sage: D = S.random_element(degree=2)
|
|
1325
|
+
sage: P = S.random_element(degree=2) * D
|
|
1326
|
+
sage: Q = S.random_element(degree=2) * D
|
|
1327
|
+
sage: L = P.left_lcm(Q)
|
|
1328
|
+
sage: U = left_lcm_cofactor(P, Q)
|
|
1329
|
+
sage: (U*P).right_monic() == L
|
|
1330
|
+
True
|
|
1331
|
+
"""
|
|
1332
|
+
cdef OrePolynomial Q, R, T
|
|
1333
|
+
cdef OrePolynomial U = <OrePolynomial>self._parent.one()
|
|
1334
|
+
cdef OrePolynomial V = <OrePolynomial>self._parent.zero()
|
|
1335
|
+
while other:
|
|
1336
|
+
Q, R = self._right_quo_rem(other)
|
|
1337
|
+
T = U - Q * V
|
|
1338
|
+
U = V
|
|
1339
|
+
V = T
|
|
1340
|
+
self = other
|
|
1341
|
+
other = R
|
|
1342
|
+
return V
|
|
1343
|
+
|
|
1344
|
+
@coerce_binop
|
|
1345
|
+
def left_xlcm(self, other, monic=True):
|
|
1346
|
+
r"""
|
|
1347
|
+
Return the left lcm `L` of ``self`` and ``other`` together
|
|
1348
|
+
with two Ore polynomials `U` and `V` such that
|
|
1349
|
+
|
|
1350
|
+
.. MATH::
|
|
1351
|
+
|
|
1352
|
+
U \cdot \text{self} = V \cdot \text{other} = L.
|
|
1353
|
+
|
|
1354
|
+
EXAMPLES::
|
|
1355
|
+
|
|
1356
|
+
sage: # needs sage.rings.finite_rings
|
|
1357
|
+
sage: k.<t> = GF(5^3)
|
|
1358
|
+
sage: Frob = k.frobenius_endomorphism()
|
|
1359
|
+
sage: S.<x> = k['x',Frob]
|
|
1360
|
+
sage: P = (x + t^2) * (x + t)
|
|
1361
|
+
sage: Q = 2 * (x^2 + t + 1) * (x * t)
|
|
1362
|
+
sage: L, U, V = P.left_xlcm(Q)
|
|
1363
|
+
sage: L
|
|
1364
|
+
x^5 + (2*t^2 + t + 4)*x^4 + (3*t^2 + 4)*x^3 + (3*t^2 + 3*t + 2)*x^2 + (t^2 + t + 2)*x
|
|
1365
|
+
|
|
1366
|
+
sage: U * P == L # needs sage.rings.finite_rings
|
|
1367
|
+
True
|
|
1368
|
+
sage: V * Q == L # needs sage.rings.finite_rings
|
|
1369
|
+
True
|
|
1370
|
+
"""
|
|
1371
|
+
if self.base_ring() not in _Fields:
|
|
1372
|
+
raise TypeError("the base ring must be a field")
|
|
1373
|
+
if self.is_zero() or other.is_zero():
|
|
1374
|
+
raise ZeroDivisionError("division by zero is not valid")
|
|
1375
|
+
cdef OrePolynomial V1 = self._left_lcm_cofactor(other)
|
|
1376
|
+
cdef OrePolynomial L = V1 * self
|
|
1377
|
+
if monic:
|
|
1378
|
+
s = ~(L.leading_coefficient())
|
|
1379
|
+
L = s * L
|
|
1380
|
+
V1 = s * V1
|
|
1381
|
+
return L, V1, L // other
|
|
1382
|
+
|
|
1383
|
+
cdef OrePolynomial _right_lcm_cofactor(self, OrePolynomial other):
|
|
1384
|
+
r"""
|
|
1385
|
+
Return an Ore polynomial `U` such that `P U = L c`
|
|
1386
|
+
where `P` is this Ore polynomial (``self``), `L`
|
|
1387
|
+
is the right lcm of `P` and ``other`` and `c` is a
|
|
1388
|
+
constant
|
|
1389
|
+
|
|
1390
|
+
TESTS::
|
|
1391
|
+
|
|
1392
|
+
sage: # needs sage.misc.cython sage.rings.finite_rings
|
|
1393
|
+
sage: cython(
|
|
1394
|
+
....: '''
|
|
1395
|
+
....: from sage.rings.polynomial.ore_polynomial_element cimport OrePolynomial
|
|
1396
|
+
....: def right_lcm_cofactor(OrePolynomial P, OrePolynomial Q):
|
|
1397
|
+
....: return P._right_lcm_cofactor(Q)
|
|
1398
|
+
....: ''')
|
|
1399
|
+
sage: k.<a> = GF(7^5)
|
|
1400
|
+
sage: Frob = k.frobenius_endomorphism(3)
|
|
1401
|
+
sage: S.<x> = k['x', Frob]
|
|
1402
|
+
sage: D = S.random_element(degree=2)
|
|
1403
|
+
sage: P = D * S.random_element(degree=2)
|
|
1404
|
+
sage: Q = D * S.random_element(degree=2)
|
|
1405
|
+
sage: L = P.right_lcm(Q)
|
|
1406
|
+
sage: U = right_lcm_cofactor(P, Q)
|
|
1407
|
+
sage: (P*U).left_monic() == L
|
|
1408
|
+
True
|
|
1409
|
+
"""
|
|
1410
|
+
cdef OrePolynomial Q, R, T
|
|
1411
|
+
cdef OrePolynomial U = <OrePolynomial>self._parent.one()
|
|
1412
|
+
cdef OrePolynomial V = <OrePolynomial>self._parent.zero()
|
|
1413
|
+
while other:
|
|
1414
|
+
Q, R = self._left_quo_rem(other)
|
|
1415
|
+
T = U - V * Q
|
|
1416
|
+
U = V
|
|
1417
|
+
V = T
|
|
1418
|
+
self = other
|
|
1419
|
+
other = R
|
|
1420
|
+
return V
|
|
1421
|
+
|
|
1422
|
+
@coerce_binop
|
|
1423
|
+
def right_xlcm(self, other, monic=True):
|
|
1424
|
+
r"""
|
|
1425
|
+
Return the right lcm `L` of ``self`` and ``other`` together
|
|
1426
|
+
with two Ore polynomials `U` and `V` such that
|
|
1427
|
+
|
|
1428
|
+
.. MATH::
|
|
1429
|
+
|
|
1430
|
+
\text{self} \cdot U = \text{other} \cdot V = L.
|
|
1431
|
+
|
|
1432
|
+
INPUT:
|
|
1433
|
+
|
|
1434
|
+
- ``other`` -- an Ore polynomial in the same ring as ``self``
|
|
1435
|
+
|
|
1436
|
+
- ``monic`` -- boolean (default: ``True``); whether the right lcm
|
|
1437
|
+
should be normalized to be monic
|
|
1438
|
+
|
|
1439
|
+
EXAMPLES::
|
|
1440
|
+
|
|
1441
|
+
sage: # needs sage.rings.finite_rings
|
|
1442
|
+
sage: k.<t> = GF(5^3)
|
|
1443
|
+
sage: Frob = k.frobenius_endomorphism()
|
|
1444
|
+
sage: S.<x> = k['x',Frob]
|
|
1445
|
+
sage: P = (x + t) * (x + t^2)
|
|
1446
|
+
sage: Q = 2 * (x + t) * (x^2 + t + 1)
|
|
1447
|
+
sage: L, U, V = P.right_xlcm(Q)
|
|
1448
|
+
sage: L
|
|
1449
|
+
x^4 + (2*t^2 + t + 2)*x^3 + (3*t^2 + 4*t + 1)*x^2 + (3*t^2 + 4*t + 1)*x + t^2 + 4
|
|
1450
|
+
sage: P * U == L
|
|
1451
|
+
True
|
|
1452
|
+
sage: Q * V == L
|
|
1453
|
+
True
|
|
1454
|
+
"""
|
|
1455
|
+
if self.base_ring() not in _Fields:
|
|
1456
|
+
raise TypeError("the base ring must be a field")
|
|
1457
|
+
if self.is_zero() or other.is_zero():
|
|
1458
|
+
raise ZeroDivisionError("division by zero is not valid")
|
|
1459
|
+
cdef OrePolynomial V1 = self._right_lcm_cofactor(other)
|
|
1460
|
+
cdef OrePolynomial L = self * V1
|
|
1461
|
+
if monic:
|
|
1462
|
+
s = self.base_ring()(~L.leading_coefficient())
|
|
1463
|
+
s = self._parent.twisting_morphism(-L.degree())(s)
|
|
1464
|
+
L = L * s
|
|
1465
|
+
V1 = V1 * s
|
|
1466
|
+
W1, _ = L._left_quo_rem(other)
|
|
1467
|
+
return L, V1, W1
|
|
1468
|
+
|
|
1469
|
+
@coerce_binop
|
|
1470
|
+
def left_lcm(self, other, monic=True):
|
|
1471
|
+
r"""
|
|
1472
|
+
Return the left lcm of ``self`` and ``other``.
|
|
1473
|
+
|
|
1474
|
+
INPUT:
|
|
1475
|
+
|
|
1476
|
+
- ``other`` -- an Ore polynomial in the same ring as ``self``
|
|
1477
|
+
|
|
1478
|
+
- ``monic`` -- boolean (default: ``True``); return whether the left lcm
|
|
1479
|
+
should be normalized to be monic
|
|
1480
|
+
|
|
1481
|
+
OUTPUT:
|
|
1482
|
+
|
|
1483
|
+
The left lcm of ``self`` and ``other``, that is an Ore polynomial
|
|
1484
|
+
`l` with the following property: any Ore polynomial is a left multiple of `l` (right divisible by `l`)
|
|
1485
|
+
iff it is a left multiple of both ``self`` and ``other`` (right divisible by ``self`` and ``other``).
|
|
1486
|
+
If monic is ``True``, `l` is in addition monic. (With this
|
|
1487
|
+
extra condition, it is uniquely determined.)
|
|
1488
|
+
|
|
1489
|
+
.. NOTE::
|
|
1490
|
+
|
|
1491
|
+
Works only if the base ring is a field (otherwise left
|
|
1492
|
+
lcm do not exist in general).
|
|
1493
|
+
|
|
1494
|
+
EXAMPLES::
|
|
1495
|
+
|
|
1496
|
+
sage: # needs sage.rings.finite_rings
|
|
1497
|
+
sage: k.<t> = GF(5^3)
|
|
1498
|
+
sage: Frob = k.frobenius_endomorphism()
|
|
1499
|
+
sage: S.<x> = k['x',Frob]
|
|
1500
|
+
sage: a = (x + t^2) * (x + t)
|
|
1501
|
+
sage: b = 2 * (x^2 + t + 1) * (x * t)
|
|
1502
|
+
sage: c = a.left_lcm(b); c
|
|
1503
|
+
x^5 + (2*t^2 + t + 4)*x^4 + (3*t^2 + 4)*x^3 + (3*t^2 + 3*t + 2)*x^2 + (t^2 + t + 2)*x
|
|
1504
|
+
sage: c.is_right_divisible_by(a)
|
|
1505
|
+
True
|
|
1506
|
+
sage: c.is_right_divisible_by(b)
|
|
1507
|
+
True
|
|
1508
|
+
sage: a.degree() + b.degree() == c.degree() + a.right_gcd(b).degree()
|
|
1509
|
+
True
|
|
1510
|
+
|
|
1511
|
+
Specifying ``monic=False``, we *can* get a nonmonic lcm::
|
|
1512
|
+
|
|
1513
|
+
sage: a.left_lcm(b,monic=False) # needs sage.rings.finite_rings
|
|
1514
|
+
(t^2 + t)*x^5 + (4*t^2 + 4*t + 1)*x^4 + (t + 1)*x^3 + (t^2 + 2)*x^2 + (3*t + 4)*x
|
|
1515
|
+
|
|
1516
|
+
The base ring needs to be a field::
|
|
1517
|
+
|
|
1518
|
+
sage: R.<t> = QQ[]
|
|
1519
|
+
sage: sigma = R.hom([t+1])
|
|
1520
|
+
sage: S.<x> = R['x',sigma]
|
|
1521
|
+
sage: a = (x + t^2) * (x + t)
|
|
1522
|
+
sage: b = 2 * (x^2 + t + 1) * (x * t)
|
|
1523
|
+
sage: a.left_lcm(b)
|
|
1524
|
+
Traceback (most recent call last):
|
|
1525
|
+
...
|
|
1526
|
+
TypeError: the base ring must be a field
|
|
1527
|
+
"""
|
|
1528
|
+
if self.base_ring() not in _Fields:
|
|
1529
|
+
raise TypeError("the base ring must be a field")
|
|
1530
|
+
if self.is_zero() or other.is_zero():
|
|
1531
|
+
raise ZeroDivisionError("division by zero is not valid")
|
|
1532
|
+
L = self._left_lcm_cofactor(other) * self
|
|
1533
|
+
if monic:
|
|
1534
|
+
L = L.right_monic()
|
|
1535
|
+
return L
|
|
1536
|
+
|
|
1537
|
+
@coerce_binop
|
|
1538
|
+
def right_lcm(self, other, monic=True):
|
|
1539
|
+
r"""
|
|
1540
|
+
Return the right lcm of ``self`` and ``other``.
|
|
1541
|
+
|
|
1542
|
+
INPUT:
|
|
1543
|
+
|
|
1544
|
+
- ``other`` -- an Ore polynomial in the same ring as ``self``
|
|
1545
|
+
|
|
1546
|
+
- ``monic`` -- boolean (default: ``True``); return whether the right lcm
|
|
1547
|
+
should be normalized to be monic
|
|
1548
|
+
|
|
1549
|
+
OUTPUT:
|
|
1550
|
+
|
|
1551
|
+
The right lcm of ``self`` and ``other``, that is an Ore polynomial
|
|
1552
|
+
`l` with the following property: any Ore polynomial is a right multiple of `g` (left divisible by `l`)
|
|
1553
|
+
iff it is a right multiple of both ``self`` and ``other`` (left divisible by ``self`` and ``other``).
|
|
1554
|
+
If monic is ``True``, `g` is in addition monic. (With this
|
|
1555
|
+
extra condition, it is uniquely determined.)
|
|
1556
|
+
|
|
1557
|
+
.. NOTE::
|
|
1558
|
+
|
|
1559
|
+
Works only if two following conditions are fulfilled
|
|
1560
|
+
(otherwise right lcm do not exist in general):
|
|
1561
|
+
1) the base ring is a field and 2) the twisting morphism on
|
|
1562
|
+
this field is bijective.
|
|
1563
|
+
|
|
1564
|
+
EXAMPLES::
|
|
1565
|
+
|
|
1566
|
+
sage: # needs sage.rings.finite_rings
|
|
1567
|
+
sage: k.<t> = GF(5^3)
|
|
1568
|
+
sage: Frob = k.frobenius_endomorphism()
|
|
1569
|
+
sage: S.<x> = k['x',Frob]
|
|
1570
|
+
sage: a = (x + t) * (x + t^2)
|
|
1571
|
+
sage: b = 2 * (x + t) * (x^2 + t + 1)
|
|
1572
|
+
sage: c = a.right_lcm(b); c
|
|
1573
|
+
x^4 + (2*t^2 + t + 2)*x^3 + (3*t^2 + 4*t + 1)*x^2 + (3*t^2 + 4*t + 1)*x + t^2 + 4
|
|
1574
|
+
sage: c.is_left_divisible_by(a)
|
|
1575
|
+
True
|
|
1576
|
+
sage: c.is_left_divisible_by(b)
|
|
1577
|
+
True
|
|
1578
|
+
sage: a.degree() + b.degree() == c.degree() + a.left_gcd(b).degree()
|
|
1579
|
+
True
|
|
1580
|
+
|
|
1581
|
+
Specifying ``monic=False``, we *can* get a nonmonic gcd::
|
|
1582
|
+
|
|
1583
|
+
sage: a.right_lcm(b,monic=False) # needs sage.rings.finite_rings
|
|
1584
|
+
2*t*x^4 + (3*t + 1)*x^3 + (4*t^2 + 4*t + 3)*x^2
|
|
1585
|
+
+ (3*t^2 + 4*t + 2)*x + 3*t^2 + 2*t + 3
|
|
1586
|
+
|
|
1587
|
+
The base ring needs to be a field::
|
|
1588
|
+
|
|
1589
|
+
sage: R.<t> = QQ[]
|
|
1590
|
+
sage: sigma = R.hom([t+1])
|
|
1591
|
+
sage: S.<x> = R['x',sigma]
|
|
1592
|
+
sage: a = (x + t) * (x + t^2)
|
|
1593
|
+
sage: b = 2 * (x + t) * (x^2 + t + 1)
|
|
1594
|
+
sage: a.right_lcm(b)
|
|
1595
|
+
Traceback (most recent call last):
|
|
1596
|
+
...
|
|
1597
|
+
TypeError: the base ring must be a field
|
|
1598
|
+
|
|
1599
|
+
And the twisting morphism needs to be bijective::
|
|
1600
|
+
|
|
1601
|
+
sage: FR = R.fraction_field()
|
|
1602
|
+
sage: f = FR.hom([FR(t)^2])
|
|
1603
|
+
sage: S.<x> = FR['x',f]
|
|
1604
|
+
sage: a = (x + t) * (x + t^2)
|
|
1605
|
+
sage: b = 2 * (x + t) * (x^2 + t + 1)
|
|
1606
|
+
sage: a.right_lcm(b)
|
|
1607
|
+
Traceback (most recent call last):
|
|
1608
|
+
...
|
|
1609
|
+
NotImplementedError: inversion of the twisting morphism Ring endomorphism of
|
|
1610
|
+
Fraction Field of Univariate Polynomial Ring in t over Rational Field
|
|
1611
|
+
Defn: t |--> t^2
|
|
1612
|
+
"""
|
|
1613
|
+
if self.base_ring() not in _Fields:
|
|
1614
|
+
raise TypeError("the base ring must be a field")
|
|
1615
|
+
if self.is_zero() or other.is_zero():
|
|
1616
|
+
raise ZeroDivisionError("division by zero is not valid")
|
|
1617
|
+
L = self * self._right_lcm_cofactor(other)
|
|
1618
|
+
if monic:
|
|
1619
|
+
L = L.left_monic()
|
|
1620
|
+
return L
|
|
1621
|
+
|
|
1622
|
+
def _repr_(self, name=None):
|
|
1623
|
+
r"""
|
|
1624
|
+
Return string representation of this Ore polynomial.
|
|
1625
|
+
|
|
1626
|
+
INPUT:
|
|
1627
|
+
|
|
1628
|
+
- ``name`` -- the name of the variable (default: the
|
|
1629
|
+
name given when the Ore polynomial ring was created)
|
|
1630
|
+
|
|
1631
|
+
EXAMPLES::
|
|
1632
|
+
|
|
1633
|
+
sage: R.<t> = QQ[]
|
|
1634
|
+
sage: sigma = R.hom([t+1])
|
|
1635
|
+
sage: S.<x> = R['x',sigma]
|
|
1636
|
+
sage: a = t^2 + 1/2*x*t
|
|
1637
|
+
sage: a._repr_()
|
|
1638
|
+
'(1/2*t + 1/2)*x + t^2'
|
|
1639
|
+
sage: a._repr_(name='y')
|
|
1640
|
+
'(1/2*t + 1/2)*y + t^2'
|
|
1641
|
+
"""
|
|
1642
|
+
s = " "
|
|
1643
|
+
m = self.degree() + 1
|
|
1644
|
+
if name is None:
|
|
1645
|
+
name = self.parent().variable_name()
|
|
1646
|
+
atomic_repr = self.parent().base_ring()._repr_option('element_is_atomic')
|
|
1647
|
+
coeffs = self.list()
|
|
1648
|
+
for n in reversed(range(m)):
|
|
1649
|
+
x = coeffs[n]
|
|
1650
|
+
if x:
|
|
1651
|
+
if n < m - 1:
|
|
1652
|
+
s += " + "
|
|
1653
|
+
x = y = repr(x)
|
|
1654
|
+
if y.find("-") == 0:
|
|
1655
|
+
y = y[1:]
|
|
1656
|
+
if not atomic_repr and n > 0 and (y.find("+") != -1 or y.find("-") != -1):
|
|
1657
|
+
x = "(%s)" % x
|
|
1658
|
+
if n > 1:
|
|
1659
|
+
var = "*%s^%s" % (name, n)
|
|
1660
|
+
elif n == 1:
|
|
1661
|
+
var = "*%s" % name
|
|
1662
|
+
else:
|
|
1663
|
+
var = ""
|
|
1664
|
+
s += "%s%s" % (x, var)
|
|
1665
|
+
s = s.replace(" + -", " - ")
|
|
1666
|
+
s = re.sub(r' 1(\.0+)?\*', ' ', s)
|
|
1667
|
+
s = re.sub(r' -1(\.0+)?\*', ' -', s)
|
|
1668
|
+
if s == " ":
|
|
1669
|
+
return "0"
|
|
1670
|
+
return s[1:]
|
|
1671
|
+
|
|
1672
|
+
def _latex_(self, name=None):
|
|
1673
|
+
r"""
|
|
1674
|
+
Return a latex representation of this Ore polynomial.
|
|
1675
|
+
|
|
1676
|
+
INPUT:
|
|
1677
|
+
|
|
1678
|
+
- ``name`` -- the name of the variable (default: the
|
|
1679
|
+
name given when the Ore polynomial ring was created)
|
|
1680
|
+
|
|
1681
|
+
EXAMPLES::
|
|
1682
|
+
|
|
1683
|
+
sage: R.<t> = QQ[]
|
|
1684
|
+
sage: sigma = R.hom([t+1])
|
|
1685
|
+
sage: S.<x> = R['x',sigma]
|
|
1686
|
+
sage: a = t^2 + 1/2*x*t
|
|
1687
|
+
sage: a._latex_()
|
|
1688
|
+
'\\left(\\frac{1}{2} t + \\frac{1}{2}\\right) x + t^{2}'
|
|
1689
|
+
sage: a._latex_(name='y')
|
|
1690
|
+
'\\left(\\frac{1}{2} t + \\frac{1}{2}\\right) y + t^{2}'
|
|
1691
|
+
"""
|
|
1692
|
+
s = " "
|
|
1693
|
+
coeffs = self.list()
|
|
1694
|
+
m = len(coeffs)
|
|
1695
|
+
if name is None:
|
|
1696
|
+
name = self.parent().latex_variable_names()[0]
|
|
1697
|
+
atomic_repr = self.parent().base_ring()._repr_option('element_is_atomic')
|
|
1698
|
+
for n in reversed(range(m)):
|
|
1699
|
+
x = self[n]
|
|
1700
|
+
x = y = x._latex_()
|
|
1701
|
+
if x != '0':
|
|
1702
|
+
if n != m - 1:
|
|
1703
|
+
s += " + "
|
|
1704
|
+
if y.find("-") == 0:
|
|
1705
|
+
y = y[1:]
|
|
1706
|
+
if not atomic_repr and n > 0 and (y.find("+") != -1 or y.find("-") != -1):
|
|
1707
|
+
x = "\\left(%s\\right)" % x
|
|
1708
|
+
if n > 1:
|
|
1709
|
+
var = "|%s^{%s}" % (name, n)
|
|
1710
|
+
elif n == 1:
|
|
1711
|
+
var = "|%s" % name
|
|
1712
|
+
else:
|
|
1713
|
+
var = ""
|
|
1714
|
+
s += "%s %s" % (x, var)
|
|
1715
|
+
s = s.replace(" + -", " - ")
|
|
1716
|
+
s = re.sub(r" 1(\.0+)? \|", " ", s)
|
|
1717
|
+
s = re.sub(r" -1(\.0+)? \|", " -", s)
|
|
1718
|
+
s = s.replace("|", "")
|
|
1719
|
+
if s == " ":
|
|
1720
|
+
return "0"
|
|
1721
|
+
return s[1:].lstrip().rstrip()
|
|
1722
|
+
|
|
1723
|
+
def _is_atomic(self):
|
|
1724
|
+
r"""
|
|
1725
|
+
Check ``self`` is a single monomial whose leading coefficient
|
|
1726
|
+
is atomic in the base ring.
|
|
1727
|
+
|
|
1728
|
+
EXAMPLES::
|
|
1729
|
+
|
|
1730
|
+
sage: R.<t> = ZZ[]
|
|
1731
|
+
sage: sigma = R.hom([t+1])
|
|
1732
|
+
sage: S.<x> = R['x',sigma]
|
|
1733
|
+
sage: S([t+1])._is_atomic()
|
|
1734
|
+
False
|
|
1735
|
+
sage: S([1])._is_atomic()
|
|
1736
|
+
True
|
|
1737
|
+
"""
|
|
1738
|
+
return (self.degree() == self.valuation() and
|
|
1739
|
+
self.leading_coefficient()._is_atomic())
|
|
1740
|
+
|
|
1741
|
+
def __bool__(self):
|
|
1742
|
+
r"""
|
|
1743
|
+
Test whether ``self`` is nonzero.
|
|
1744
|
+
|
|
1745
|
+
EXAMPLES::
|
|
1746
|
+
|
|
1747
|
+
sage: R.<t> = ZZ[]
|
|
1748
|
+
sage: sigma = R.hom([t+1])
|
|
1749
|
+
sage: S.<x> = R['x',sigma]
|
|
1750
|
+
sage: a = x + 1
|
|
1751
|
+
sage: bool(a)
|
|
1752
|
+
True
|
|
1753
|
+
sage: b = S.zero()
|
|
1754
|
+
sage: bool(b)
|
|
1755
|
+
False
|
|
1756
|
+
"""
|
|
1757
|
+
return self.degree() > -1
|
|
1758
|
+
|
|
1759
|
+
def base_ring(self):
|
|
1760
|
+
r"""
|
|
1761
|
+
Return the base ring of ``self``.
|
|
1762
|
+
|
|
1763
|
+
EXAMPLES::
|
|
1764
|
+
|
|
1765
|
+
sage: R.<t> = ZZ[]
|
|
1766
|
+
sage: sigma = R.hom([t+1])
|
|
1767
|
+
sage: S.<x> = R['x',sigma]
|
|
1768
|
+
sage: a = S.random_element()
|
|
1769
|
+
sage: a.base_ring()
|
|
1770
|
+
Univariate Polynomial Ring in t over Integer Ring
|
|
1771
|
+
sage: a.base_ring() is R
|
|
1772
|
+
True
|
|
1773
|
+
"""
|
|
1774
|
+
return self.parent().base_ring()
|
|
1775
|
+
|
|
1776
|
+
def shift(self, n):
|
|
1777
|
+
r"""
|
|
1778
|
+
Return ``self`` multiplied on the right by the power `x^n`.
|
|
1779
|
+
|
|
1780
|
+
If `n` is negative, terms below `x^n` will be discarded.
|
|
1781
|
+
|
|
1782
|
+
EXAMPLES::
|
|
1783
|
+
|
|
1784
|
+
sage: R.<t> = QQ[]
|
|
1785
|
+
sage: sigma = R.hom([t+1])
|
|
1786
|
+
sage: S.<x> = R['x',sigma]
|
|
1787
|
+
sage: a = x^5 + t^4*x^4 + t^2*x^2 + t^10
|
|
1788
|
+
sage: a.shift(0)
|
|
1789
|
+
x^5 + t^4*x^4 + t^2*x^2 + t^10
|
|
1790
|
+
sage: a.shift(-1)
|
|
1791
|
+
x^4 + t^4*x^3 + t^2*x
|
|
1792
|
+
sage: a.shift(-5)
|
|
1793
|
+
1
|
|
1794
|
+
sage: a.shift(2)
|
|
1795
|
+
x^7 + t^4*x^6 + t^2*x^4 + t^10*x^2
|
|
1796
|
+
|
|
1797
|
+
One can also use the infix shift operator::
|
|
1798
|
+
|
|
1799
|
+
sage: a >> 2
|
|
1800
|
+
x^3 + t^4*x^2 + t^2
|
|
1801
|
+
sage: a << 2
|
|
1802
|
+
x^7 + t^4*x^6 + t^2*x^4 + t^10*x^2
|
|
1803
|
+
"""
|
|
1804
|
+
if n == 0 or self.degree() < 0:
|
|
1805
|
+
return self
|
|
1806
|
+
if n > 0:
|
|
1807
|
+
return self._parent(n * [self.base_ring().zero()] + self.list(), check=False)
|
|
1808
|
+
if n < 0:
|
|
1809
|
+
if n > self.degree():
|
|
1810
|
+
return self._parent([])
|
|
1811
|
+
else:
|
|
1812
|
+
return self._parent(self.list()[-n:], check=False)
|
|
1813
|
+
|
|
1814
|
+
def __lshift__(self, k):
|
|
1815
|
+
r"""
|
|
1816
|
+
Return ``self`` multiplied on the right by the power `x^k`.
|
|
1817
|
+
|
|
1818
|
+
EXAMPLES::
|
|
1819
|
+
|
|
1820
|
+
sage: R.<t> = QQ[]
|
|
1821
|
+
sage: sigma = R.hom([t+1])
|
|
1822
|
+
sage: S.<x> = R['x',sigma]
|
|
1823
|
+
sage: a = x^5 + t^4*x^4 + t^2*x^2 + t^10
|
|
1824
|
+
sage: a << 2
|
|
1825
|
+
x^7 + t^4*x^6 + t^2*x^4 + t^10*x^2
|
|
1826
|
+
"""
|
|
1827
|
+
return self.shift(k)
|
|
1828
|
+
|
|
1829
|
+
def __rshift__(self, k):
|
|
1830
|
+
r"""
|
|
1831
|
+
Return ``self`` multiplied on the right by the power `x^(-k)`.
|
|
1832
|
+
|
|
1833
|
+
If `n` is negative, terms below `x^n` will be discarded.
|
|
1834
|
+
|
|
1835
|
+
EXAMPLES::
|
|
1836
|
+
|
|
1837
|
+
sage: R.<t> = QQ[]
|
|
1838
|
+
sage: sigma = R.hom([t+1])
|
|
1839
|
+
sage: S.<x> = R['x',sigma]
|
|
1840
|
+
sage: a = x^5 + t^4*x^4 + t^2*x^2 + t^10
|
|
1841
|
+
sage: a >> 2
|
|
1842
|
+
x^3 + t^4*x^2 + t^2
|
|
1843
|
+
"""
|
|
1844
|
+
return self.shift(-k)
|
|
1845
|
+
|
|
1846
|
+
def change_variable_name(self, var):
|
|
1847
|
+
r"""
|
|
1848
|
+
Change the name of the variable of ``self``.
|
|
1849
|
+
|
|
1850
|
+
This will create the Ore polynomial ring with the new name but same
|
|
1851
|
+
base ring, twisting morphism and twisting derivation. The returned
|
|
1852
|
+
Ore polynomial will be an element of that Ore polynomial ring.
|
|
1853
|
+
|
|
1854
|
+
INPUT:
|
|
1855
|
+
|
|
1856
|
+
- ``var`` -- the name of the new variable
|
|
1857
|
+
|
|
1858
|
+
EXAMPLES::
|
|
1859
|
+
|
|
1860
|
+
sage: R.<t> = ZZ[]
|
|
1861
|
+
sage: sigma = R.hom([t+1])
|
|
1862
|
+
sage: S.<x> = R['x', sigma]
|
|
1863
|
+
sage: a = x^3 + (2*t + 1)*x + t^2 + 3*t + 5
|
|
1864
|
+
sage: b = a.change_variable_name('y'); b
|
|
1865
|
+
y^3 + (2*t + 1)*y + t^2 + 3*t + 5
|
|
1866
|
+
|
|
1867
|
+
Note that a new parent is created at the same time::
|
|
1868
|
+
|
|
1869
|
+
sage: b.parent()
|
|
1870
|
+
Ore Polynomial Ring in y over Univariate Polynomial Ring in t over Integer Ring
|
|
1871
|
+
twisted by t |--> t + 1
|
|
1872
|
+
"""
|
|
1873
|
+
R = self._parent.change_var(var)
|
|
1874
|
+
return R(self.list())
|
|
1875
|
+
|
|
1876
|
+
def is_term(self):
|
|
1877
|
+
r"""
|
|
1878
|
+
Return ``True`` if ``self`` is an element of the base ring times a
|
|
1879
|
+
power of the generator.
|
|
1880
|
+
|
|
1881
|
+
EXAMPLES::
|
|
1882
|
+
|
|
1883
|
+
sage: R.<t> = ZZ[]
|
|
1884
|
+
sage: sigma = R.hom([t+1])
|
|
1885
|
+
sage: S.<x> = R['x',sigma]
|
|
1886
|
+
sage: x.is_term()
|
|
1887
|
+
True
|
|
1888
|
+
sage: R(1).is_term()
|
|
1889
|
+
True
|
|
1890
|
+
sage: (3*x^5).is_term()
|
|
1891
|
+
True
|
|
1892
|
+
sage: (1+3*x^5).is_term()
|
|
1893
|
+
False
|
|
1894
|
+
|
|
1895
|
+
If you want to test that ``self`` also has leading coefficient 1, use
|
|
1896
|
+
:meth:`is_monomial()` instead::
|
|
1897
|
+
|
|
1898
|
+
sage: (3*x^5).is_monomial()
|
|
1899
|
+
False
|
|
1900
|
+
"""
|
|
1901
|
+
return len(self.exponents()) == 1
|
|
1902
|
+
|
|
1903
|
+
def is_monomial(self):
|
|
1904
|
+
r"""
|
|
1905
|
+
Return ``True`` if ``self`` is a monomial, i.e., a power of
|
|
1906
|
+
the generator.
|
|
1907
|
+
|
|
1908
|
+
EXAMPLES::
|
|
1909
|
+
|
|
1910
|
+
sage: R.<t> = ZZ[]
|
|
1911
|
+
sage: sigma = R.hom([t+1])
|
|
1912
|
+
sage: S.<x> = R['x',sigma]
|
|
1913
|
+
sage: x.is_monomial()
|
|
1914
|
+
True
|
|
1915
|
+
sage: (x+1).is_monomial()
|
|
1916
|
+
False
|
|
1917
|
+
sage: (x^2).is_monomial()
|
|
1918
|
+
True
|
|
1919
|
+
sage: S(1).is_monomial()
|
|
1920
|
+
True
|
|
1921
|
+
|
|
1922
|
+
The coefficient must be 1::
|
|
1923
|
+
|
|
1924
|
+
sage: (2*x^5).is_monomial()
|
|
1925
|
+
False
|
|
1926
|
+
sage: S(t).is_monomial()
|
|
1927
|
+
False
|
|
1928
|
+
|
|
1929
|
+
To allow a non-1 leading coefficient, use is_term()::
|
|
1930
|
+
|
|
1931
|
+
sage: (2*x^5).is_term()
|
|
1932
|
+
True
|
|
1933
|
+
sage: S(t).is_term()
|
|
1934
|
+
True
|
|
1935
|
+
"""
|
|
1936
|
+
return self.is_term() and self.leading_coefficient() == 1
|
|
1937
|
+
|
|
1938
|
+
cpdef list coefficients(self, sparse=True):
|
|
1939
|
+
r"""
|
|
1940
|
+
Return the coefficients of the monomials appearing in ``self``.
|
|
1941
|
+
|
|
1942
|
+
If ``sparse=True`` (the default), return only the nonzero coefficients.
|
|
1943
|
+
Otherwise, return the same value as ``self.list()``.
|
|
1944
|
+
|
|
1945
|
+
.. NOTE::
|
|
1946
|
+
|
|
1947
|
+
This should be overridden in subclasses.
|
|
1948
|
+
|
|
1949
|
+
EXAMPLES::
|
|
1950
|
+
|
|
1951
|
+
sage: R.<t> = QQ[]
|
|
1952
|
+
sage: sigma = R.hom([t+1])
|
|
1953
|
+
sage: S.<x> = R['x',sigma]
|
|
1954
|
+
sage: a = 1 + x^4 + (t+1)*x^2 + t^2
|
|
1955
|
+
sage: a.coefficients()
|
|
1956
|
+
[t^2 + 1, t + 1, 1]
|
|
1957
|
+
sage: a.coefficients(sparse=False)
|
|
1958
|
+
[t^2 + 1, 0, t + 1, 0, 1]
|
|
1959
|
+
"""
|
|
1960
|
+
raise NotImplementedError
|
|
1961
|
+
|
|
1962
|
+
def number_of_terms(self):
|
|
1963
|
+
r"""
|
|
1964
|
+
Return the number of nonzero coefficients of ``self``.
|
|
1965
|
+
|
|
1966
|
+
This is also known as the weight, hamming weight or sparsity.
|
|
1967
|
+
|
|
1968
|
+
EXAMPLES::
|
|
1969
|
+
|
|
1970
|
+
sage: R.<t> = QQ[]
|
|
1971
|
+
sage: sigma = R.hom([t+1])
|
|
1972
|
+
sage: S.<x> = R['x',sigma]
|
|
1973
|
+
sage: a = 1 + x^4 + (t+1)*x^2 + t^2
|
|
1974
|
+
sage: a.number_of_terms()
|
|
1975
|
+
3
|
|
1976
|
+
|
|
1977
|
+
This is also an alias for ``hamming_weight``::
|
|
1978
|
+
|
|
1979
|
+
sage: a.hamming_weight()
|
|
1980
|
+
3
|
|
1981
|
+
"""
|
|
1982
|
+
return len(self.coefficients())
|
|
1983
|
+
|
|
1984
|
+
# alias hamming_weight for number_of_terms:
|
|
1985
|
+
hamming_weight = number_of_terms
|
|
1986
|
+
|
|
1987
|
+
def __copy__(self):
|
|
1988
|
+
r"""
|
|
1989
|
+
Return a "copy" of ``self``.
|
|
1990
|
+
|
|
1991
|
+
In Sage, since Ore polynomials are immutable, this just returns
|
|
1992
|
+
``self`` again.
|
|
1993
|
+
|
|
1994
|
+
EXAMPLES::
|
|
1995
|
+
|
|
1996
|
+
sage: R.<t> = QQ[]
|
|
1997
|
+
sage: sigma = R.hom([t+1])
|
|
1998
|
+
sage: S.<x> = R['x',sigma]
|
|
1999
|
+
sage: a = 1 + x^4 + (t+1)*x^2 + t^2
|
|
2000
|
+
sage: b = copy(a)
|
|
2001
|
+
sage: b is a
|
|
2002
|
+
True
|
|
2003
|
+
"""
|
|
2004
|
+
return self
|
|
2005
|
+
|
|
2006
|
+
cpdef bint is_zero(self) noexcept:
|
|
2007
|
+
r"""
|
|
2008
|
+
Return ``True`` if ``self`` is the zero polynomial.
|
|
2009
|
+
|
|
2010
|
+
EXAMPLES::
|
|
2011
|
+
|
|
2012
|
+
sage: R.<t> = ZZ[]
|
|
2013
|
+
sage: sigma = R.hom([t+1])
|
|
2014
|
+
sage: S.<x> = R['x',sigma]
|
|
2015
|
+
sage: a = x + 1
|
|
2016
|
+
sage: a.is_zero()
|
|
2017
|
+
False
|
|
2018
|
+
sage: b = S.zero()
|
|
2019
|
+
sage: b.is_zero()
|
|
2020
|
+
True
|
|
2021
|
+
"""
|
|
2022
|
+
return self.degree() == -1
|
|
2023
|
+
|
|
2024
|
+
cpdef bint is_one(self) noexcept:
|
|
2025
|
+
r"""
|
|
2026
|
+
Test whether this polynomial is `1`.
|
|
2027
|
+
|
|
2028
|
+
EXAMPLES::
|
|
2029
|
+
|
|
2030
|
+
sage: R.<t> = QQ[]
|
|
2031
|
+
sage: sigma = R.hom([t+1])
|
|
2032
|
+
sage: S.<x> = R['x',sigma]
|
|
2033
|
+
sage: R(1).is_one()
|
|
2034
|
+
True
|
|
2035
|
+
sage: (x + 3).is_one()
|
|
2036
|
+
False
|
|
2037
|
+
"""
|
|
2038
|
+
return self.degree() == 0 and self[0].is_one()
|
|
2039
|
+
|
|
2040
|
+
@coerce_binop
|
|
2041
|
+
def right_mod(self, other):
|
|
2042
|
+
r"""
|
|
2043
|
+
Return the remainder of right division of ``self`` by ``other``.
|
|
2044
|
+
|
|
2045
|
+
EXAMPLES::
|
|
2046
|
+
|
|
2047
|
+
sage: R.<t> = QQ[]
|
|
2048
|
+
sage: sigma = R.hom([t+1])
|
|
2049
|
+
sage: S.<x> = R['x',sigma]
|
|
2050
|
+
sage: a = 1 + t*x^2
|
|
2051
|
+
sage: b = x + 1
|
|
2052
|
+
sage: a % b
|
|
2053
|
+
t + 1
|
|
2054
|
+
sage: (x^3 + x - 1).right_mod(x^2 - 1)
|
|
2055
|
+
2*x - 1
|
|
2056
|
+
"""
|
|
2057
|
+
return self % other
|
|
2058
|
+
|
|
2059
|
+
@coerce_binop
|
|
2060
|
+
def left_mod(self, other):
|
|
2061
|
+
r"""
|
|
2062
|
+
Return the remainder of left division of ``self`` by ``other``.
|
|
2063
|
+
|
|
2064
|
+
EXAMPLES::
|
|
2065
|
+
|
|
2066
|
+
sage: # needs sage.rings.finite_rings
|
|
2067
|
+
sage: k.<t> = GF(5^3)
|
|
2068
|
+
sage: Frob = k.frobenius_endomorphism()
|
|
2069
|
+
sage: S.<x> = k['x',Frob]
|
|
2070
|
+
sage: a = 1 + t*x^2
|
|
2071
|
+
sage: b = x + 1
|
|
2072
|
+
sage: a.left_mod(b)
|
|
2073
|
+
2*t^2 + 4*t
|
|
2074
|
+
"""
|
|
2075
|
+
_, r = self.left_quo_rem(other)
|
|
2076
|
+
return r
|
|
2077
|
+
|
|
2078
|
+
def is_constant(self):
|
|
2079
|
+
r"""
|
|
2080
|
+
Return whether ``self`` is a constant polynomial.
|
|
2081
|
+
|
|
2082
|
+
EXAMPLES::
|
|
2083
|
+
|
|
2084
|
+
sage: R.<t> = QQ[]
|
|
2085
|
+
sage: sigma = R.hom([t+1])
|
|
2086
|
+
sage: S.<x> = R['x',sigma]
|
|
2087
|
+
sage: R(2).is_constant()
|
|
2088
|
+
True
|
|
2089
|
+
sage: (x + 1).is_constant()
|
|
2090
|
+
False
|
|
2091
|
+
"""
|
|
2092
|
+
return self.degree() <= 0
|
|
2093
|
+
|
|
2094
|
+
def exponents(self):
|
|
2095
|
+
r"""
|
|
2096
|
+
Return the exponents of the monomials appearing in ``self``.
|
|
2097
|
+
|
|
2098
|
+
EXAMPLES::
|
|
2099
|
+
|
|
2100
|
+
sage: R.<t> = QQ[]
|
|
2101
|
+
sage: sigma = R.hom([t+1])
|
|
2102
|
+
sage: S.<x> = R['x',sigma]
|
|
2103
|
+
sage: a = 1 + x^4 + (t+1)*x^2 + t^2
|
|
2104
|
+
sage: a.exponents()
|
|
2105
|
+
[0, 2, 4]
|
|
2106
|
+
"""
|
|
2107
|
+
return [i for i in range(self.degree() + 1) if bool(self[i])]
|
|
2108
|
+
|
|
2109
|
+
def prec(self):
|
|
2110
|
+
r"""
|
|
2111
|
+
Return the precision of ``self``.
|
|
2112
|
+
|
|
2113
|
+
This is always infinity, since polynomials are of infinite precision by
|
|
2114
|
+
definition (there is no big-oh).
|
|
2115
|
+
|
|
2116
|
+
EXAMPLES::
|
|
2117
|
+
|
|
2118
|
+
sage: R.<t> = QQ[]
|
|
2119
|
+
sage: sigma = R.hom([t+1])
|
|
2120
|
+
sage: S.<x> = R['x',sigma]
|
|
2121
|
+
sage: x.prec()
|
|
2122
|
+
+Infinity
|
|
2123
|
+
"""
|
|
2124
|
+
return infinity
|
|
2125
|
+
|
|
2126
|
+
def padded_list(self, n=None):
|
|
2127
|
+
r"""
|
|
2128
|
+
Return list of coefficients of ``self`` up to (but not including)
|
|
2129
|
+
degree `n`.
|
|
2130
|
+
|
|
2131
|
+
Includes `0`s in the list on the right so that the list always has length
|
|
2132
|
+
exactly `n`.
|
|
2133
|
+
|
|
2134
|
+
INPUT:
|
|
2135
|
+
|
|
2136
|
+
- ``n`` -- (default: ``None``) if given, an integer that
|
|
2137
|
+
is at least `0`
|
|
2138
|
+
|
|
2139
|
+
EXAMPLES::
|
|
2140
|
+
|
|
2141
|
+
sage: R.<t> = QQ[]
|
|
2142
|
+
sage: sigma = R.hom([t+1])
|
|
2143
|
+
sage: S.<x> = R['x',sigma]
|
|
2144
|
+
sage: a = 1 + t*x^3 + t^2*x^5
|
|
2145
|
+
sage: a.padded_list()
|
|
2146
|
+
[1, 0, 0, t, 0, t^2]
|
|
2147
|
+
sage: a.padded_list(10)
|
|
2148
|
+
[1, 0, 0, t, 0, t^2, 0, 0, 0, 0]
|
|
2149
|
+
sage: len(a.padded_list(10))
|
|
2150
|
+
10
|
|
2151
|
+
sage: a.padded_list(3)
|
|
2152
|
+
[1, 0, 0]
|
|
2153
|
+
sage: a.padded_list(0)
|
|
2154
|
+
[]
|
|
2155
|
+
sage: a.padded_list(-1)
|
|
2156
|
+
Traceback (most recent call last):
|
|
2157
|
+
...
|
|
2158
|
+
ValueError: n must be at least 0
|
|
2159
|
+
"""
|
|
2160
|
+
v = self.list()
|
|
2161
|
+
if n is None:
|
|
2162
|
+
return v
|
|
2163
|
+
if n < 0:
|
|
2164
|
+
raise ValueError("n must be at least 0")
|
|
2165
|
+
if len(v) < n:
|
|
2166
|
+
z = self._parent.base_ring().zero()
|
|
2167
|
+
return v + [z] * (n - len(v))
|
|
2168
|
+
return v[:int(n)]
|
|
2169
|
+
|
|
2170
|
+
def variable_name(self):
|
|
2171
|
+
r"""
|
|
2172
|
+
Return the string name of the variable used in ``self``.
|
|
2173
|
+
|
|
2174
|
+
EXAMPLES::
|
|
2175
|
+
|
|
2176
|
+
sage: R.<t> = QQ[]
|
|
2177
|
+
sage: sigma = R.hom([t+1])
|
|
2178
|
+
sage: S.<x> = R['x',sigma]
|
|
2179
|
+
sage: a = x + t
|
|
2180
|
+
sage: a.variable_name()
|
|
2181
|
+
'x'
|
|
2182
|
+
"""
|
|
2183
|
+
return self.parent().variable_name()
|
|
2184
|
+
|
|
2185
|
+
|
|
2186
|
+
cdef void lmul_gen(list A, Morphism m, d) noexcept:
|
|
2187
|
+
r"""
|
|
2188
|
+
If ``A`` is the list of coefficients of an Ore polynomial ``P``,
|
|
2189
|
+
replace it by the list of coefficients of ``X*P`` (where ``X``
|
|
2190
|
+
is the variable in the Ore polynomial ring).
|
|
2191
|
+
|
|
2192
|
+
This is a helper function.
|
|
2193
|
+
|
|
2194
|
+
INPUT:
|
|
2195
|
+
|
|
2196
|
+
- ``A`` -- list of coefficients
|
|
2197
|
+
|
|
2198
|
+
- ``m`` -- the twisting morphism of the Ore polynomial ring
|
|
2199
|
+
|
|
2200
|
+
- ``d`` -- the twisting derivation of the Ore polynomial ring
|
|
2201
|
+
"""
|
|
2202
|
+
if m is None:
|
|
2203
|
+
A.append(A[-1])
|
|
2204
|
+
for j in range(len(A) - 2, 0, -1):
|
|
2205
|
+
A[j] = d(A[j]) + A[j - 1]
|
|
2206
|
+
else:
|
|
2207
|
+
A.append(m(A[-1]))
|
|
2208
|
+
for j in range(len(A) - 2, 0, -1):
|
|
2209
|
+
A[j] = d(A[j]) + m(A[j - 1])
|
|
2210
|
+
A[0] = d(A[0])
|
|
2211
|
+
|
|
2212
|
+
|
|
2213
|
+
cdef class OrePolynomial_generic_dense(OrePolynomial):
|
|
2214
|
+
r"""
|
|
2215
|
+
Generic implementation of dense Ore polynomial supporting any valid base
|
|
2216
|
+
ring, twisting morphism and twisting derivation.
|
|
2217
|
+
"""
|
|
2218
|
+
def __init__(self, parent, x=None, int check=1, int construct=0, **kwds):
|
|
2219
|
+
r"""
|
|
2220
|
+
Construct an Ore polynomial over the given parent with the given
|
|
2221
|
+
coefficients.
|
|
2222
|
+
|
|
2223
|
+
INPUT:
|
|
2224
|
+
|
|
2225
|
+
- ``parent`` -- parent of ``self``
|
|
2226
|
+
|
|
2227
|
+
- ``x`` -- list of coefficients from which ``self`` can be constructed
|
|
2228
|
+
|
|
2229
|
+
- ``check`` -- flag variable to normalize the polynomial
|
|
2230
|
+
|
|
2231
|
+
- ``construct`` -- boolean (default: ``False``)
|
|
2232
|
+
|
|
2233
|
+
TESTS::
|
|
2234
|
+
|
|
2235
|
+
sage: R.<t> = QQ[]
|
|
2236
|
+
sage: sigma = R.hom([t+1])
|
|
2237
|
+
sage: S.<x> = R['x',sigma]
|
|
2238
|
+
|
|
2239
|
+
We create an Ore polynomial from a list::
|
|
2240
|
+
|
|
2241
|
+
sage: S([t,1])
|
|
2242
|
+
x + t
|
|
2243
|
+
|
|
2244
|
+
from another Ore polynomial::
|
|
2245
|
+
|
|
2246
|
+
sage: S(x^2 + t)
|
|
2247
|
+
x^2 + t
|
|
2248
|
+
|
|
2249
|
+
from a constant::
|
|
2250
|
+
|
|
2251
|
+
sage: x = S(t^2 + 1); x
|
|
2252
|
+
t^2 + 1
|
|
2253
|
+
sage: x.parent() is S
|
|
2254
|
+
True
|
|
2255
|
+
"""
|
|
2256
|
+
OrePolynomial.__init__(self, parent)
|
|
2257
|
+
if x is None:
|
|
2258
|
+
self._coeffs = []
|
|
2259
|
+
return
|
|
2260
|
+
|
|
2261
|
+
R = parent.base_ring()
|
|
2262
|
+
if isinstance(x, list):
|
|
2263
|
+
if check:
|
|
2264
|
+
self._coeffs = [R(t) for t in x]
|
|
2265
|
+
self._normalize()
|
|
2266
|
+
else:
|
|
2267
|
+
self._coeffs = x
|
|
2268
|
+
return
|
|
2269
|
+
|
|
2270
|
+
if isinstance(x, OrePolynomial):
|
|
2271
|
+
if (<Element>x)._parent is self._parent:
|
|
2272
|
+
x = list(x.list())
|
|
2273
|
+
elif R.has_coerce_map_from((<Element>x)._parent):
|
|
2274
|
+
try:
|
|
2275
|
+
if x.is_zero():
|
|
2276
|
+
self._coeffs = []
|
|
2277
|
+
return
|
|
2278
|
+
except (AttributeError, TypeError):
|
|
2279
|
+
pass
|
|
2280
|
+
x = [x]
|
|
2281
|
+
else:
|
|
2282
|
+
self._coeffs = [R(a, **kwds) for a in x.list()]
|
|
2283
|
+
if check:
|
|
2284
|
+
self._normalize()
|
|
2285
|
+
return
|
|
2286
|
+
|
|
2287
|
+
elif isinstance(x, int) and x == 0:
|
|
2288
|
+
self._coeffs = []
|
|
2289
|
+
return
|
|
2290
|
+
|
|
2291
|
+
elif isinstance(x, dict):
|
|
2292
|
+
x = _dict_to_list(x, R.zero())
|
|
2293
|
+
|
|
2294
|
+
elif not isinstance(x, list):
|
|
2295
|
+
x = [x]
|
|
2296
|
+
if check:
|
|
2297
|
+
self._coeffs = [R(z, **kwds) for z in x]
|
|
2298
|
+
self._normalize()
|
|
2299
|
+
else:
|
|
2300
|
+
self._coeffs = x
|
|
2301
|
+
|
|
2302
|
+
def __reduce__(self):
|
|
2303
|
+
r"""
|
|
2304
|
+
Return the generic dense Ore polynomial corresponding to the
|
|
2305
|
+
current parameters provided ``self``.
|
|
2306
|
+
|
|
2307
|
+
EXAMPLES::
|
|
2308
|
+
|
|
2309
|
+
sage: R.<t> = QQ[]
|
|
2310
|
+
sage: sigma = R.hom([t+1])
|
|
2311
|
+
sage: S.<x> = R['x',sigma]
|
|
2312
|
+
sage: loads(dumps(x)) == x
|
|
2313
|
+
True
|
|
2314
|
+
sage: loads(dumps(x))
|
|
2315
|
+
x
|
|
2316
|
+
"""
|
|
2317
|
+
return (self._parent, (self._coeffs,))
|
|
2318
|
+
|
|
2319
|
+
cdef long _hash_c(self) noexcept:
|
|
2320
|
+
r"""
|
|
2321
|
+
This hash incorporates the name of the variable.
|
|
2322
|
+
|
|
2323
|
+
.. NOTE::
|
|
2324
|
+
|
|
2325
|
+
This is an internal method. Use :meth:`__hash__` instead.
|
|
2326
|
+
"""
|
|
2327
|
+
# todo - come up with a way to create hashes of zero that
|
|
2328
|
+
# that do not incorrectly indicate that the element is 0.
|
|
2329
|
+
cdef long result = 0
|
|
2330
|
+
cdef long result_mon
|
|
2331
|
+
cdef long c_hash
|
|
2332
|
+
cdef long var_name_hash = 0
|
|
2333
|
+
cdef int i
|
|
2334
|
+
for i in range(len(self._coeffs)):
|
|
2335
|
+
if i == 1:
|
|
2336
|
+
var_name_hash = hash(self._parent._names[0])
|
|
2337
|
+
c_hash = hash(self._coeffs[i])
|
|
2338
|
+
if c_hash != 0:
|
|
2339
|
+
if i == 0:
|
|
2340
|
+
result += c_hash
|
|
2341
|
+
else:
|
|
2342
|
+
result_mon = c_hash
|
|
2343
|
+
result_mon = (1000003 * result_mon) ^ var_name_hash
|
|
2344
|
+
result_mon = (1000003 * result_mon) ^ i
|
|
2345
|
+
result += result_mon
|
|
2346
|
+
if result == -1:
|
|
2347
|
+
return -2
|
|
2348
|
+
return result
|
|
2349
|
+
|
|
2350
|
+
cdef OrePolynomial _new_c(self, list coeffs, Parent P, char check=0):
|
|
2351
|
+
r"""
|
|
2352
|
+
Fast creation of a new Ore polynomial given a list of coefficients.
|
|
2353
|
+
|
|
2354
|
+
.. WARNING::
|
|
2355
|
+
|
|
2356
|
+
The list ``coeffs`` is stored internally in the newly created Ore
|
|
2357
|
+
polynomial, so this must not be modified after calling this method.
|
|
2358
|
+
|
|
2359
|
+
TESTS::
|
|
2360
|
+
|
|
2361
|
+
sage: R.<t> = ZZ[]
|
|
2362
|
+
sage: sigma = R.hom([t+1])
|
|
2363
|
+
sage: S.<x> = R['x',sigma]
|
|
2364
|
+
sage: a = t*x^3 + x^4 + (t+1)*x^2
|
|
2365
|
+
sage: a.truncate(4) #indirect doctest
|
|
2366
|
+
t*x^3 + (t + 1)*x^2
|
|
2367
|
+
"""
|
|
2368
|
+
cdef type t = type(self)
|
|
2369
|
+
cdef OrePolynomial_generic_dense f = t.__new__(t)
|
|
2370
|
+
f._parent = P
|
|
2371
|
+
f._coeffs = coeffs
|
|
2372
|
+
if check:
|
|
2373
|
+
f._normalize()
|
|
2374
|
+
return f
|
|
2375
|
+
|
|
2376
|
+
cdef void _normalize(self) noexcept:
|
|
2377
|
+
r"""
|
|
2378
|
+
Remove higher order `0`-coefficients from the representation of ``self``.
|
|
2379
|
+
|
|
2380
|
+
TESTS::
|
|
2381
|
+
|
|
2382
|
+
sage: R.<t> = QQ[]
|
|
2383
|
+
sage: sigma = R.hom([t+1])
|
|
2384
|
+
sage: S.<x> = R['x',sigma]; S #indirect doctest
|
|
2385
|
+
Ore Polynomial Ring in x over Univariate Polynomial Ring in t over Rational Field twisted by t |--> t + 1
|
|
2386
|
+
"""
|
|
2387
|
+
cdef list x = self._coeffs
|
|
2388
|
+
cdef Py_ssize_t n = len(x) - 1
|
|
2389
|
+
while n >= 0 and not x[n]:
|
|
2390
|
+
del x[n]
|
|
2391
|
+
n -= 1
|
|
2392
|
+
|
|
2393
|
+
cpdef _richcmp_(left, right, int op):
|
|
2394
|
+
r"""
|
|
2395
|
+
Compare the two Ore polynomials ``self`` and ``other``.
|
|
2396
|
+
|
|
2397
|
+
We order polynomials first by degree, then in dictionary order
|
|
2398
|
+
starting with the coefficient of largest degree.
|
|
2399
|
+
|
|
2400
|
+
EXAMPLES::
|
|
2401
|
+
|
|
2402
|
+
sage: R.<t> = QQ[]
|
|
2403
|
+
sage: sigma = R.hom([t+1])
|
|
2404
|
+
sage: S.<x> = R['x',sigma]
|
|
2405
|
+
sage: a = 1 + x^4 + (t+1)*x^2 + t^2
|
|
2406
|
+
sage: b = (2*t^2)*x + t + 1
|
|
2407
|
+
sage: a > b
|
|
2408
|
+
True
|
|
2409
|
+
sage: a < b
|
|
2410
|
+
False
|
|
2411
|
+
"""
|
|
2412
|
+
cdef x = (<OrePolynomial_generic_dense>left)._coeffs
|
|
2413
|
+
cdef y = (<OrePolynomial_generic_dense>right)._coeffs
|
|
2414
|
+
return PyObject_RichCompare(x, y, op)
|
|
2415
|
+
|
|
2416
|
+
def __iter__(self):
|
|
2417
|
+
r"""
|
|
2418
|
+
Iterate over the list of coefficients of ``self``.
|
|
2419
|
+
|
|
2420
|
+
EXAMPLES::
|
|
2421
|
+
|
|
2422
|
+
sage: R.<t> = QQ[]
|
|
2423
|
+
sage: sigma = R.hom([t+1])
|
|
2424
|
+
sage: S.<x> = R['x',sigma]
|
|
2425
|
+
sage: P = S([1, 2, 3])
|
|
2426
|
+
sage: [y for y in iter(P)]
|
|
2427
|
+
[1, 2, 3]
|
|
2428
|
+
"""
|
|
2429
|
+
return iter((<OrePolynomial_generic_dense>self)._coeffs)
|
|
2430
|
+
|
|
2431
|
+
def __getitem__(self, n):
|
|
2432
|
+
r"""
|
|
2433
|
+
Return the `n`-th coefficient of ``self``.
|
|
2434
|
+
|
|
2435
|
+
INPUT:
|
|
2436
|
+
|
|
2437
|
+
- ``n`` -- integer
|
|
2438
|
+
|
|
2439
|
+
OUTPUT: the ``n``-th coefficient of ``self``
|
|
2440
|
+
|
|
2441
|
+
EXAMPLES::
|
|
2442
|
+
|
|
2443
|
+
sage: R.<t> = QQ[]
|
|
2444
|
+
sage: sigma = R.hom([t+1])
|
|
2445
|
+
sage: S.<x> = R['x',sigma]
|
|
2446
|
+
sage: a = t*x^2 + (t + 3/7)*x + t^2
|
|
2447
|
+
sage: a[1]
|
|
2448
|
+
t + 3/7
|
|
2449
|
+
sage: a[3]
|
|
2450
|
+
0
|
|
2451
|
+
"""
|
|
2452
|
+
try:
|
|
2453
|
+
return self._coeffs[n]
|
|
2454
|
+
except IndexError:
|
|
2455
|
+
return self.base_ring().zero()
|
|
2456
|
+
|
|
2457
|
+
cpdef list list(self, bint copy=True):
|
|
2458
|
+
r"""
|
|
2459
|
+
Return a list of the coefficients of ``self``.
|
|
2460
|
+
|
|
2461
|
+
EXAMPLES::
|
|
2462
|
+
|
|
2463
|
+
sage: R.<t> = QQ[]
|
|
2464
|
+
sage: sigma = R.hom([t+1])
|
|
2465
|
+
sage: S.<x> = R['x',sigma]
|
|
2466
|
+
sage: a = 1 + x^4 + (t+1)*x^2 + t^2
|
|
2467
|
+
sage: l = a.list(); l
|
|
2468
|
+
[t^2 + 1, 0, t + 1, 0, 1]
|
|
2469
|
+
|
|
2470
|
+
Note that `l` is a list, it is mutable, and each call to the list
|
|
2471
|
+
method returns a new list::
|
|
2472
|
+
|
|
2473
|
+
sage: type(l)
|
|
2474
|
+
<... 'list'>
|
|
2475
|
+
sage: l[0] = 5
|
|
2476
|
+
sage: a.list()
|
|
2477
|
+
[t^2 + 1, 0, t + 1, 0, 1]
|
|
2478
|
+
"""
|
|
2479
|
+
if copy:
|
|
2480
|
+
# This creates a shallow copy
|
|
2481
|
+
return list((<OrePolynomial_generic_dense>self)._coeffs)
|
|
2482
|
+
else:
|
|
2483
|
+
return (<OrePolynomial_generic_dense>self)._coeffs
|
|
2484
|
+
|
|
2485
|
+
cpdef dict monomial_coefficients(self):
|
|
2486
|
+
r"""
|
|
2487
|
+
Return a dictionary representation of ``self``.
|
|
2488
|
+
|
|
2489
|
+
EXAMPLES::
|
|
2490
|
+
|
|
2491
|
+
sage: R.<t> = ZZ[]
|
|
2492
|
+
sage: sigma = R.hom([t+1])
|
|
2493
|
+
sage: S.<x> = R['x',sigma]
|
|
2494
|
+
sage: a = x^2012 + t*x^1006 + t^3 + 2*t
|
|
2495
|
+
sage: a.monomial_coefficients()
|
|
2496
|
+
{0: t^3 + 2*t, 1006: t, 2012: 1}
|
|
2497
|
+
|
|
2498
|
+
``dict`` is an alias::
|
|
2499
|
+
|
|
2500
|
+
sage: a.dict()
|
|
2501
|
+
{0: t^3 + 2*t, 1006: t, 2012: 1}
|
|
2502
|
+
"""
|
|
2503
|
+
cdef dict X = {}
|
|
2504
|
+
cdef list Y = (<OrePolynomial_generic_dense>self)._coeffs
|
|
2505
|
+
cdef int i
|
|
2506
|
+
for i in range(len(Y)):
|
|
2507
|
+
c = Y[i]
|
|
2508
|
+
if c:
|
|
2509
|
+
X[i] = c
|
|
2510
|
+
return X
|
|
2511
|
+
|
|
2512
|
+
dict = monomial_coefficients
|
|
2513
|
+
|
|
2514
|
+
cpdef Integer degree(self):
|
|
2515
|
+
r"""
|
|
2516
|
+
Return the degree of ``self``.
|
|
2517
|
+
|
|
2518
|
+
By convention, the zero Ore polynomial has degree `-1`.
|
|
2519
|
+
|
|
2520
|
+
EXAMPLES::
|
|
2521
|
+
|
|
2522
|
+
sage: R.<t> = ZZ[]
|
|
2523
|
+
sage: sigma = R.hom([t+1])
|
|
2524
|
+
sage: S.<x> = R['x',sigma]
|
|
2525
|
+
sage: a = x^2 + t*x^3 + t^2*x + 1
|
|
2526
|
+
sage: a.degree()
|
|
2527
|
+
3
|
|
2528
|
+
|
|
2529
|
+
By convention, the degree of `0` is `-1`::
|
|
2530
|
+
|
|
2531
|
+
sage: S(0).degree()
|
|
2532
|
+
-1
|
|
2533
|
+
|
|
2534
|
+
TESTS:
|
|
2535
|
+
|
|
2536
|
+
We check that the degree is an ``Integer`` object (see #35519)::
|
|
2537
|
+
|
|
2538
|
+
sage: R.<t> = ZZ[]
|
|
2539
|
+
sage: sigma = R.hom([t+1])
|
|
2540
|
+
sage: S.<x> = R['x',sigma]
|
|
2541
|
+
sage: a = x^2 + t*x^3 + t^2*x + 1
|
|
2542
|
+
sage: isinstance(a.degree(), Integer)
|
|
2543
|
+
True
|
|
2544
|
+
|
|
2545
|
+
::
|
|
2546
|
+
|
|
2547
|
+
sage: R.<t> = OrePolynomialRing(GF(5)['T'], GF(5)['T'].frobenius_endomorphism())
|
|
2548
|
+
sage: isinstance((t + 1).degree(), Integer)
|
|
2549
|
+
True
|
|
2550
|
+
"""
|
|
2551
|
+
return Integer(len(self._coeffs) - 1)
|
|
2552
|
+
|
|
2553
|
+
cpdef _add_(self, right):
|
|
2554
|
+
r"""
|
|
2555
|
+
Add two polynomials.
|
|
2556
|
+
|
|
2557
|
+
EXAMPLES::
|
|
2558
|
+
|
|
2559
|
+
sage: R.<t> = QQ[]
|
|
2560
|
+
sage: sigma = R.hom([t+1])
|
|
2561
|
+
sage: S.<x> = R['x',sigma]
|
|
2562
|
+
sage: a = S.random_element(monic=True)
|
|
2563
|
+
sage: b = -S.random_element(monic=True)
|
|
2564
|
+
sage: c = a + b
|
|
2565
|
+
sage: c - b == a
|
|
2566
|
+
True
|
|
2567
|
+
sage: c - b == a
|
|
2568
|
+
True
|
|
2569
|
+
sage: a + a == 2*a
|
|
2570
|
+
True
|
|
2571
|
+
"""
|
|
2572
|
+
cdef Py_ssize_t i
|
|
2573
|
+
cdef list x = (<OrePolynomial_generic_dense>self)._coeffs
|
|
2574
|
+
cdef list y = (<OrePolynomial_generic_dense>right)._coeffs
|
|
2575
|
+
cdef Py_ssize_t dx = len(x), dy = len(y)
|
|
2576
|
+
if dx > dy:
|
|
2577
|
+
r = self._new_c([x[i] + y[i] for i in range(dy)] + x[dy:], self._parent, 0)
|
|
2578
|
+
elif dx < dy:
|
|
2579
|
+
r = self._new_c([x[i] + y[i] for i in range(dx)] + y[dx:], self._parent, 0)
|
|
2580
|
+
else:
|
|
2581
|
+
r = self._new_c([x[i] + y[i] for i in range(dx)], self._parent, 1)
|
|
2582
|
+
return r
|
|
2583
|
+
|
|
2584
|
+
cpdef _sub_(self, right):
|
|
2585
|
+
r"""
|
|
2586
|
+
Subtract polynomial ``right`` from ``self``.
|
|
2587
|
+
|
|
2588
|
+
EXAMPLES::
|
|
2589
|
+
|
|
2590
|
+
sage: R.<t> = QQ[]
|
|
2591
|
+
sage: sigma = R.hom([t+1])
|
|
2592
|
+
sage: S.<x> = R['x',sigma]
|
|
2593
|
+
sage: a = S.random_element(monic=True)
|
|
2594
|
+
sage: b = S.random_element(monic=True)
|
|
2595
|
+
sage: c = a - b
|
|
2596
|
+
sage: c - a == -b
|
|
2597
|
+
True
|
|
2598
|
+
sage: c + b == a
|
|
2599
|
+
True
|
|
2600
|
+
sage: c - c == 0
|
|
2601
|
+
True
|
|
2602
|
+
"""
|
|
2603
|
+
cdef Py_ssize_t i
|
|
2604
|
+
cdef list x = (<OrePolynomial_generic_dense>self)._coeffs
|
|
2605
|
+
cdef list y = (<OrePolynomial_generic_dense>right)._coeffs
|
|
2606
|
+
cdef Py_ssize_t dx = len(x), dy = len(y)
|
|
2607
|
+
cdef RingElement c
|
|
2608
|
+
if dx > dy:
|
|
2609
|
+
r = self._new_c([x[i] - y[i] for i in range(dy)] + x[dy:], self._parent, 0)
|
|
2610
|
+
elif dx < dy:
|
|
2611
|
+
r = self._new_c([x[i] - y[i] for i in range(dx)] + [-c for c in y[dx:]], self._parent, 0)
|
|
2612
|
+
else:
|
|
2613
|
+
r = self._new_c([x[i] - y[i] for i in range(dx)], self._parent, 1)
|
|
2614
|
+
return r
|
|
2615
|
+
|
|
2616
|
+
cpdef _neg_(self):
|
|
2617
|
+
r"""
|
|
2618
|
+
Return the negative of ``self``.
|
|
2619
|
+
|
|
2620
|
+
EXAMPLES::
|
|
2621
|
+
|
|
2622
|
+
sage: R.<t> = QQ[]
|
|
2623
|
+
sage: sigma = R.hom([t+1])
|
|
2624
|
+
sage: S.<x> = R['x',sigma]
|
|
2625
|
+
sage: a = t*x^2 + x - 3
|
|
2626
|
+
sage: -a
|
|
2627
|
+
-t*x^2 - x + 3
|
|
2628
|
+
"""
|
|
2629
|
+
c = self._new_c([-x for x in (<OrePolynomial_generic_dense>self)._coeffs],
|
|
2630
|
+
self._parent, 0)
|
|
2631
|
+
return c
|
|
2632
|
+
|
|
2633
|
+
def valuation(self):
|
|
2634
|
+
r"""
|
|
2635
|
+
Return the minimal degree of a nonzero monomial of ``self``.
|
|
2636
|
+
|
|
2637
|
+
By convention, the zero Ore polynomial has valuation `+\infty`.
|
|
2638
|
+
|
|
2639
|
+
EXAMPLES::
|
|
2640
|
+
|
|
2641
|
+
sage: R.<t> = ZZ[]
|
|
2642
|
+
sage: sigma = R.hom([t+1])
|
|
2643
|
+
sage: S.<x> = R['x',sigma]
|
|
2644
|
+
sage: a = x^2 + t*x^3 + t^2*x
|
|
2645
|
+
sage: a.valuation()
|
|
2646
|
+
1
|
|
2647
|
+
|
|
2648
|
+
By convention, the valuation of `0` is `+\infty`::
|
|
2649
|
+
|
|
2650
|
+
sage: S(0).valuation()
|
|
2651
|
+
+Infinity
|
|
2652
|
+
"""
|
|
2653
|
+
cdef list x = self._coeffs
|
|
2654
|
+
if not x:
|
|
2655
|
+
return infinity
|
|
2656
|
+
cdef Py_ssize_t v = 0
|
|
2657
|
+
while x[v].is_zero() and v < len(x):
|
|
2658
|
+
v += 1
|
|
2659
|
+
return v
|
|
2660
|
+
|
|
2661
|
+
def truncate(self, n):
|
|
2662
|
+
r"""
|
|
2663
|
+
Return the polynomial resulting from discarding all monomials of degree
|
|
2664
|
+
at least `n`.
|
|
2665
|
+
|
|
2666
|
+
EXAMPLES::
|
|
2667
|
+
|
|
2668
|
+
sage: R.<t> = ZZ[]
|
|
2669
|
+
sage: sigma = R.hom([t+1])
|
|
2670
|
+
sage: S.<x> = R['x',sigma]
|
|
2671
|
+
sage: a = t*x^3 + x^4 + (t+1)*x^2
|
|
2672
|
+
sage: a.truncate(4)
|
|
2673
|
+
t*x^3 + (t + 1)*x^2
|
|
2674
|
+
sage: a.truncate(3)
|
|
2675
|
+
(t + 1)*x^2
|
|
2676
|
+
"""
|
|
2677
|
+
return self._new_c(self._coeffs[:n], self._parent, 1)
|
|
2678
|
+
|
|
2679
|
+
cdef list _mul_list(self, list A):
|
|
2680
|
+
r"""
|
|
2681
|
+
Return the list of coefficients of the product of this
|
|
2682
|
+
Ore polynomial by that whose coefficients are given by ``A``.
|
|
2683
|
+
|
|
2684
|
+
This is a helper function.
|
|
2685
|
+
"""
|
|
2686
|
+
cdef list BA = [self.base_ring().zero()] * (len(self._coeffs) + len(A) - 1)
|
|
2687
|
+
cdef Morphism m = self._parent._morphism
|
|
2688
|
+
cdef d = self._parent._derivation
|
|
2689
|
+
cdef coeff
|
|
2690
|
+
cdef Py_ssize_t i, j
|
|
2691
|
+
for i in range(len(self._coeffs)):
|
|
2692
|
+
if i:
|
|
2693
|
+
lmul_gen(A, m, d)
|
|
2694
|
+
coeff = self._coeffs[i]
|
|
2695
|
+
if coeff:
|
|
2696
|
+
for j in range(len(A)):
|
|
2697
|
+
BA[j] += coeff * A[j]
|
|
2698
|
+
return BA
|
|
2699
|
+
|
|
2700
|
+
cpdef _lmul_(self, Element s):
|
|
2701
|
+
r"""
|
|
2702
|
+
Return the product ``self * right``.
|
|
2703
|
+
|
|
2704
|
+
INPUT:
|
|
2705
|
+
|
|
2706
|
+
- ``right`` -- an element of the base ring
|
|
2707
|
+
|
|
2708
|
+
EXAMPLES::
|
|
2709
|
+
|
|
2710
|
+
sage: R.<t> = QQ[]
|
|
2711
|
+
sage: der = R.derivation()
|
|
2712
|
+
sage: A.<d> = R['d', der]
|
|
2713
|
+
sage: d*t # indirect doctest
|
|
2714
|
+
t*d + 1
|
|
2715
|
+
"""
|
|
2716
|
+
cdef coeffs = self._mul_list([s])
|
|
2717
|
+
return self._new_c(coeffs, self._parent, 1)
|
|
2718
|
+
|
|
2719
|
+
cpdef _rmul_(self, Element s):
|
|
2720
|
+
r"""
|
|
2721
|
+
Return the product ``left * self``.
|
|
2722
|
+
|
|
2723
|
+
INPUT:
|
|
2724
|
+
|
|
2725
|
+
- ``left`` -- an element of the base ring
|
|
2726
|
+
|
|
2727
|
+
EXAMPLES::
|
|
2728
|
+
|
|
2729
|
+
sage: R.<t> = QQ[]
|
|
2730
|
+
sage: der = R.derivation()
|
|
2731
|
+
sage: A.<d> = R['d', der]
|
|
2732
|
+
sage: t*(d + 1) # indirect doctest
|
|
2733
|
+
t*d + t
|
|
2734
|
+
|
|
2735
|
+
TESTS:
|
|
2736
|
+
|
|
2737
|
+
We check that :issue:`32210` is fixed::
|
|
2738
|
+
|
|
2739
|
+
sage: A.<t> = GF(5)[]
|
|
2740
|
+
sage: S.<X> = A['X', A.derivation()]
|
|
2741
|
+
sage: f = 0*X
|
|
2742
|
+
sage: f.degree()
|
|
2743
|
+
-1
|
|
2744
|
+
"""
|
|
2745
|
+
return self._new_c([s * c for c in self._coeffs], self._parent, 1)
|
|
2746
|
+
|
|
2747
|
+
cpdef _mul_(self, other):
|
|
2748
|
+
r"""
|
|
2749
|
+
Return the product ``self * right``.
|
|
2750
|
+
|
|
2751
|
+
INPUT:
|
|
2752
|
+
|
|
2753
|
+
- ``right`` -- an Ore polynomial in the same ring as ``self``
|
|
2754
|
+
|
|
2755
|
+
EXAMPLES::
|
|
2756
|
+
|
|
2757
|
+
sage: R.<t> = QQ[]
|
|
2758
|
+
sage: der = R.derivation()
|
|
2759
|
+
sage: A.<d> = R['d', der]
|
|
2760
|
+
sage: P = d^2 + t
|
|
2761
|
+
sage: Q = d^2 + (t + 1)*d
|
|
2762
|
+
sage: P * Q
|
|
2763
|
+
d^4 + (t + 1)*d^3 + (t + 2)*d^2 + (t^2 + t)*d
|
|
2764
|
+
sage: P * Q == Q * P
|
|
2765
|
+
False
|
|
2766
|
+
|
|
2767
|
+
TESTS:
|
|
2768
|
+
|
|
2769
|
+
We check associativity and distributivity::
|
|
2770
|
+
|
|
2771
|
+
sage: U = A.random_element(degree=10)
|
|
2772
|
+
sage: V = A.random_element(degree=10)
|
|
2773
|
+
sage: W = A.random_element(degree=10)
|
|
2774
|
+
sage: U * (V * W) == (U * V) * W
|
|
2775
|
+
True
|
|
2776
|
+
sage: U * (V + W) == U*V + U*W
|
|
2777
|
+
True
|
|
2778
|
+
sage: (U + V) * W == U*W + V*W
|
|
2779
|
+
True
|
|
2780
|
+
"""
|
|
2781
|
+
cdef coeffs = list((<OrePolynomial_generic_dense>other)._coeffs)
|
|
2782
|
+
if coeffs:
|
|
2783
|
+
coeffs = self._mul_list(coeffs)
|
|
2784
|
+
return self._new_c(coeffs, self._parent, 1)
|
|
2785
|
+
|
|
2786
|
+
cdef _left_quo_rem(self, OrePolynomial other):
|
|
2787
|
+
r"""
|
|
2788
|
+
Return the quotient and remainder of the left Euclidean
|
|
2789
|
+
division of ``self`` by ``other`` (C implementation).
|
|
2790
|
+
"""
|
|
2791
|
+
sig_check()
|
|
2792
|
+
cdef list A = list(self._coeffs)
|
|
2793
|
+
cdef Py_ssize_t degB = other.degree()
|
|
2794
|
+
cdef Morphism m = self._parent.twisting_morphism(-degB)
|
|
2795
|
+
cdef RingElement s, inv = other.leading_coefficient()
|
|
2796
|
+
cdef Py_ssize_t nb = len(A) - degB
|
|
2797
|
+
cdef list L
|
|
2798
|
+
cdef list quo = []
|
|
2799
|
+
if not inv.is_unit():
|
|
2800
|
+
raise ValueError("the leading coefficient of the divisor in not a unit")
|
|
2801
|
+
inv = inv.inverse_of_unit()
|
|
2802
|
+
for i in range(nb - 1, -1, -1):
|
|
2803
|
+
s = A[i + degB]
|
|
2804
|
+
if s:
|
|
2805
|
+
s = s * inv
|
|
2806
|
+
if m is not None:
|
|
2807
|
+
s = m(s)
|
|
2808
|
+
L = (<OrePolynomial_generic_dense>other)._mul_list([s])
|
|
2809
|
+
for j in range(len(L) - 1):
|
|
2810
|
+
A[i + j] -= L[j]
|
|
2811
|
+
quo.append(s)
|
|
2812
|
+
quo.reverse()
|
|
2813
|
+
return self._new_c(quo, self._parent), self._new_c(A[:degB], self._parent, 1)
|
|
2814
|
+
|
|
2815
|
+
cdef _right_quo_rem(self, OrePolynomial other):
|
|
2816
|
+
r"""
|
|
2817
|
+
Return the quotient and remainder of the right Euclidean
|
|
2818
|
+
division of ``self`` by ``other`` (C implementation).
|
|
2819
|
+
"""
|
|
2820
|
+
sig_check()
|
|
2821
|
+
cdef list A = list(self._coeffs)
|
|
2822
|
+
cdef Py_ssize_t i, j
|
|
2823
|
+
cdef Py_ssize_t degB = other.degree()
|
|
2824
|
+
cdef Py_ssize_t nb = len(A) - degB
|
|
2825
|
+
cdef Morphism m = self._parent._morphism
|
|
2826
|
+
cdef d = self._parent._derivation
|
|
2827
|
+
cdef RingElement s, inv = other.leading_coefficient()
|
|
2828
|
+
cdef list XnB = (<OrePolynomial_generic_dense>other)._coeffs
|
|
2829
|
+
cdef list XnBs = []
|
|
2830
|
+
cdef list quo = []
|
|
2831
|
+
if not inv.is_unit():
|
|
2832
|
+
raise ValueError("the leading coefficient of the divisor in not a unit")
|
|
2833
|
+
inv = inv.inverse_of_unit()
|
|
2834
|
+
for i in range(nb):
|
|
2835
|
+
if i:
|
|
2836
|
+
XnB = list(XnB)
|
|
2837
|
+
lmul_gen(XnB, m, d)
|
|
2838
|
+
XnBs.append(XnB)
|
|
2839
|
+
for i in range(nb - 1, -1, -1):
|
|
2840
|
+
s = A[i + degB]
|
|
2841
|
+
if s:
|
|
2842
|
+
if m:
|
|
2843
|
+
s *= self._parent.twisting_morphism(i)(inv)
|
|
2844
|
+
else:
|
|
2845
|
+
s *= inv
|
|
2846
|
+
XnB = XnBs[i]
|
|
2847
|
+
for j in range(len(XnB) - 1):
|
|
2848
|
+
A[j] -= s * XnB[j]
|
|
2849
|
+
quo.append(s)
|
|
2850
|
+
quo.reverse()
|
|
2851
|
+
return self._new_c(quo, self._parent), self._new_c(A[:degB], self._parent, 1)
|
|
2852
|
+
|
|
2853
|
+
cpdef list coefficients(self, sparse=True):
|
|
2854
|
+
r"""
|
|
2855
|
+
Return the coefficients of the monomials appearing in ``self``.
|
|
2856
|
+
|
|
2857
|
+
If ``sparse=True`` (the default), return only the nonzero coefficients.
|
|
2858
|
+
Otherwise, return the same value as ``self.list()``.
|
|
2859
|
+
|
|
2860
|
+
EXAMPLES::
|
|
2861
|
+
|
|
2862
|
+
sage: R.<t> = QQ[]
|
|
2863
|
+
sage: sigma = R.hom([t+1])
|
|
2864
|
+
sage: S.<x> = R['x',sigma]
|
|
2865
|
+
sage: a = 1 + x^4 + (t+1)*x^2 + t^2
|
|
2866
|
+
sage: a.coefficients()
|
|
2867
|
+
[t^2 + 1, t + 1, 1]
|
|
2868
|
+
sage: a.coefficients(sparse=False)
|
|
2869
|
+
[t^2 + 1, 0, t + 1, 0, 1]
|
|
2870
|
+
"""
|
|
2871
|
+
if sparse:
|
|
2872
|
+
return [c for c in self._coeffs if not c.is_zero()]
|
|
2873
|
+
else:
|
|
2874
|
+
return self._coeffs
|
|
2875
|
+
|
|
2876
|
+
def hilbert_shift(self, s, var=None):
|
|
2877
|
+
r"""
|
|
2878
|
+
Return this Ore polynomial with variable shifted by `s`.
|
|
2879
|
+
|
|
2880
|
+
If this Ore polynomial is `P(x)`, this returns `P(x+s)`.
|
|
2881
|
+
|
|
2882
|
+
INPUT:
|
|
2883
|
+
|
|
2884
|
+
- ``s`` -- an element in the base ring
|
|
2885
|
+
|
|
2886
|
+
- ``var`` -- string; the variable name
|
|
2887
|
+
|
|
2888
|
+
EXAMPLES::
|
|
2889
|
+
|
|
2890
|
+
sage: R.<t> = GF(7)[]
|
|
2891
|
+
sage: der = R.derivation()
|
|
2892
|
+
sage: A.<d> = R['d', der]
|
|
2893
|
+
|
|
2894
|
+
sage: L = d^3 + t*d^2
|
|
2895
|
+
sage: L.hilbert_shift(t)
|
|
2896
|
+
d^3 + 4*t*d^2 + (5*t^2 + 3)*d + 2*t^3 + 4*t
|
|
2897
|
+
sage: (d+t)^3 + t*(d+t)^2
|
|
2898
|
+
d^3 + 4*t*d^2 + (5*t^2 + 3)*d + 2*t^3 + 4*t
|
|
2899
|
+
|
|
2900
|
+
One can specify another variable name::
|
|
2901
|
+
|
|
2902
|
+
sage: L.hilbert_shift(t, var='x')
|
|
2903
|
+
x^3 + 4*t*x^2 + (5*t^2 + 3)*x + 2*t^3 + 4*t
|
|
2904
|
+
|
|
2905
|
+
When the twisting morphism is not trivial, the output lies
|
|
2906
|
+
in a different Ore polynomial ring::
|
|
2907
|
+
|
|
2908
|
+
sage: # needs sage.rings.finite_rings
|
|
2909
|
+
sage: k.<a> = GF(5^3)
|
|
2910
|
+
sage: Frob = k.frobenius_endomorphism()
|
|
2911
|
+
sage: S.<x> = k['x', Frob]
|
|
2912
|
+
sage: P = x^2 + a*x + a^2
|
|
2913
|
+
sage: Q = P.hilbert_shift(a); Q
|
|
2914
|
+
x^2 + (2*a^2 + a + 4)*x + a^2 + 3*a + 4
|
|
2915
|
+
sage: Q.parent()
|
|
2916
|
+
Ore Polynomial Ring in x over
|
|
2917
|
+
Finite Field in a of size 5^3 twisted by a |--> a^5 and a*([a |--> a^5] - id)
|
|
2918
|
+
sage: Q.parent() is S
|
|
2919
|
+
False
|
|
2920
|
+
|
|
2921
|
+
This behavior ensures that the Hilbert shift by a fixed element
|
|
2922
|
+
defines a homomorphism of rings::
|
|
2923
|
+
|
|
2924
|
+
sage: # needs sage.rings.finite_rings
|
|
2925
|
+
sage: U = S.random_element(degree=5)
|
|
2926
|
+
sage: V = S.random_element(degree=5)
|
|
2927
|
+
sage: s = k.random_element()
|
|
2928
|
+
sage: (U+V).hilbert_shift(s) == U.hilbert_shift(s) + V.hilbert_shift(s)
|
|
2929
|
+
True
|
|
2930
|
+
sage: (U*V).hilbert_shift(s) == U.hilbert_shift(s) * V.hilbert_shift(s)
|
|
2931
|
+
True
|
|
2932
|
+
|
|
2933
|
+
We check that shifting by an element and then by its opposite
|
|
2934
|
+
gives back the initial Ore polynomial::
|
|
2935
|
+
|
|
2936
|
+
sage: # needs sage.rings.finite_rings
|
|
2937
|
+
sage: P = S.random_element(degree=10)
|
|
2938
|
+
sage: s = k.random_element()
|
|
2939
|
+
sage: P.hilbert_shift(s).hilbert_shift(-s) == P
|
|
2940
|
+
True
|
|
2941
|
+
"""
|
|
2942
|
+
from sage.rings.polynomial.ore_polynomial_ring import OrePolynomialRing
|
|
2943
|
+
parent = self._parent
|
|
2944
|
+
k = parent.base_ring()
|
|
2945
|
+
morphism = parent._morphism
|
|
2946
|
+
derivation = parent._derivation
|
|
2947
|
+
if morphism is not None:
|
|
2948
|
+
if derivation is None:
|
|
2949
|
+
derivation = k.derivation(s, twist=morphism)
|
|
2950
|
+
else:
|
|
2951
|
+
derivation += k.derivation(s, twist=morphism)
|
|
2952
|
+
if var is None:
|
|
2953
|
+
var = parent.variable_name()
|
|
2954
|
+
if derivation is None:
|
|
2955
|
+
S = OrePolynomialRing(k, morphism, var, polcast=False)
|
|
2956
|
+
else:
|
|
2957
|
+
S = OrePolynomialRing(k, derivation, var, polcast=False)
|
|
2958
|
+
if not self:
|
|
2959
|
+
return S.zero()
|
|
2960
|
+
X = S.gen() + s
|
|
2961
|
+
Xi = S.one()
|
|
2962
|
+
ans = S(self[0])
|
|
2963
|
+
for i in range(1, self.degree() + 1):
|
|
2964
|
+
Xi = X * Xi
|
|
2965
|
+
ans += self[i] * Xi
|
|
2966
|
+
return ans
|
|
2967
|
+
|
|
2968
|
+
|
|
2969
|
+
cdef class ConstantOrePolynomialSection(Map):
|
|
2970
|
+
r"""
|
|
2971
|
+
Representation of the canonical homomorphism from the constants of an Ore
|
|
2972
|
+
polynomial ring to the base ring.
|
|
2973
|
+
|
|
2974
|
+
This class is necessary for automatic coercion from zero-degree Ore
|
|
2975
|
+
polynomial ring into the base ring.
|
|
2976
|
+
|
|
2977
|
+
EXAMPLES::
|
|
2978
|
+
|
|
2979
|
+
sage: from sage.rings.polynomial.ore_polynomial_element import ConstantOrePolynomialSection
|
|
2980
|
+
sage: R.<t> = QQ[]
|
|
2981
|
+
sage: sigma = R.hom([t+1])
|
|
2982
|
+
sage: S.<x> = R['x',sigma]
|
|
2983
|
+
sage: m = ConstantOrePolynomialSection(S, R); m
|
|
2984
|
+
Generic map:
|
|
2985
|
+
From: Ore Polynomial Ring in x over Univariate Polynomial Ring in t
|
|
2986
|
+
over Rational Field twisted by t |--> t + 1
|
|
2987
|
+
To: Univariate Polynomial Ring in t over Rational Field
|
|
2988
|
+
"""
|
|
2989
|
+
cpdef Element _call_(self, x):
|
|
2990
|
+
r"""
|
|
2991
|
+
Return the corresponding element of the base ring if ``self`` is a
|
|
2992
|
+
constant Ore polynomial. Otherwise, it fails.
|
|
2993
|
+
|
|
2994
|
+
TESTS::
|
|
2995
|
+
|
|
2996
|
+
sage: from sage.rings.polynomial.ore_polynomial_element import ConstantOrePolynomialSection
|
|
2997
|
+
sage: R.<t> = QQ[]
|
|
2998
|
+
sage: sigma = R.hom([t+1])
|
|
2999
|
+
sage: S.<x> = R['x',sigma]
|
|
3000
|
+
sage: m = ConstantOrePolynomialSection(S, R); m
|
|
3001
|
+
Generic map:
|
|
3002
|
+
From: Ore Polynomial Ring in x over Univariate Polynomial Ring in t over Rational Field twisted by t |--> t + 1
|
|
3003
|
+
To: Univariate Polynomial Ring in t over Rational Field
|
|
3004
|
+
sage: m(S([0,1])-S([0,1]))
|
|
3005
|
+
0
|
|
3006
|
+
sage: m(S([3,1])-S([0,1]))
|
|
3007
|
+
3
|
|
3008
|
+
sage: m(S([0,1])-S([0,t]))
|
|
3009
|
+
Traceback (most recent call last):
|
|
3010
|
+
...
|
|
3011
|
+
TypeError: (-t + 1)*x is not a constant polynomial
|
|
3012
|
+
"""
|
|
3013
|
+
if x.degree() <= 0:
|
|
3014
|
+
try:
|
|
3015
|
+
return <Element>(x.constant_coefficient())
|
|
3016
|
+
except AttributeError:
|
|
3017
|
+
return <Element>((<OrePolynomial>x).constant_coefficient())
|
|
3018
|
+
else:
|
|
3019
|
+
raise TypeError(f"{x} is not a constant polynomial")
|
|
3020
|
+
|
|
3021
|
+
|
|
3022
|
+
cdef class OrePolynomialBaseringInjection(Morphism):
|
|
3023
|
+
r"""
|
|
3024
|
+
Representation of the canonical homomorphism from a ring `R` into an Ore
|
|
3025
|
+
polynomial ring over `R`.
|
|
3026
|
+
|
|
3027
|
+
This class is necessary for automatic coercion from the base ring to the Ore
|
|
3028
|
+
polynomial ring.
|
|
3029
|
+
|
|
3030
|
+
.. SEEALSO::
|
|
3031
|
+
|
|
3032
|
+
:class:`~sage.rings.polynomial.polynomial_element.PolynomialBaseringInjection`
|
|
3033
|
+
|
|
3034
|
+
EXAMPLES::
|
|
3035
|
+
|
|
3036
|
+
sage: R.<t> = QQ[]
|
|
3037
|
+
sage: sigma = R.hom([t+1])
|
|
3038
|
+
sage: S.<x> = R['x',sigma]
|
|
3039
|
+
sage: S.coerce_map_from(S.base_ring()) #indirect doctest
|
|
3040
|
+
Ore Polynomial base injection morphism:
|
|
3041
|
+
From: Univariate Polynomial Ring in t over Rational Field
|
|
3042
|
+
To: Ore Polynomial Ring in x over Univariate Polynomial Ring in t
|
|
3043
|
+
over Rational Field twisted by t |--> t + 1
|
|
3044
|
+
"""
|
|
3045
|
+
def __init__(self, domain, codomain):
|
|
3046
|
+
r"""
|
|
3047
|
+
Construct a Skew Polynomial Basering Injection.
|
|
3048
|
+
|
|
3049
|
+
INPUT:
|
|
3050
|
+
|
|
3051
|
+
- ``domain`` -- a ring `R`; this will be the domain of the injection
|
|
3052
|
+
|
|
3053
|
+
- ``codomain`` -- an Ore polynomial ring over ``domain``; this will be
|
|
3054
|
+
the codomain
|
|
3055
|
+
|
|
3056
|
+
TESTS::
|
|
3057
|
+
|
|
3058
|
+
sage: # needs sage.rings.finite_rings
|
|
3059
|
+
sage: from sage.rings.polynomial.ore_polynomial_element import OrePolynomialBaseringInjection
|
|
3060
|
+
sage: k.<t> = GF(5^3)
|
|
3061
|
+
sage: Frob = k.frobenius_endomorphism()
|
|
3062
|
+
sage: S.<x> = k['x',Frob]
|
|
3063
|
+
sage: OrePolynomialBaseringInjection(k, k['x', Frob])
|
|
3064
|
+
Ore Polynomial base injection morphism:
|
|
3065
|
+
From: Finite Field in t of size 5^3
|
|
3066
|
+
To: Ore Polynomial Ring in x over Finite Field in t of size 5^3 twisted by t |--> t^5
|
|
3067
|
+
sage: R.<t> = QQ[]
|
|
3068
|
+
sage: OrePolynomialBaseringInjection(QQ, k['x', Frob])
|
|
3069
|
+
Traceback (most recent call last):
|
|
3070
|
+
...
|
|
3071
|
+
AssertionError: the domain of the injection must be the base ring of the Ore polynomial ring
|
|
3072
|
+
"""
|
|
3073
|
+
assert codomain.base_ring() is domain, \
|
|
3074
|
+
"the domain of the injection must be the base ring of the Ore polynomial ring"
|
|
3075
|
+
Morphism.__init__(self, Hom(domain, codomain))
|
|
3076
|
+
self._an_element = codomain.gen()
|
|
3077
|
+
self._repr_type_str = "Ore Polynomial base injection"
|
|
3078
|
+
self._new_constant_poly_ = self._an_element._new_constant_poly
|
|
3079
|
+
|
|
3080
|
+
def an_element(self):
|
|
3081
|
+
r"""
|
|
3082
|
+
Return an element of the codomain of the ring homomorphism.
|
|
3083
|
+
|
|
3084
|
+
EXAMPLES::
|
|
3085
|
+
|
|
3086
|
+
sage: # needs sage.rings.finite_rings
|
|
3087
|
+
sage: from sage.rings.polynomial.ore_polynomial_element import OrePolynomialBaseringInjection
|
|
3088
|
+
sage: k.<t> = GF(5^3)
|
|
3089
|
+
sage: Frob = k.frobenius_endomorphism()
|
|
3090
|
+
sage: S.<x> = k['x',Frob]
|
|
3091
|
+
sage: m = OrePolynomialBaseringInjection(k, k['x', Frob])
|
|
3092
|
+
sage: m.an_element()
|
|
3093
|
+
x
|
|
3094
|
+
"""
|
|
3095
|
+
return self._an_element
|
|
3096
|
+
|
|
3097
|
+
cpdef Element _call_(self, e):
|
|
3098
|
+
r"""
|
|
3099
|
+
Return the corresponding Ore polynomial to the element from the
|
|
3100
|
+
base ring according to ``self``.
|
|
3101
|
+
|
|
3102
|
+
INPUT:
|
|
3103
|
+
|
|
3104
|
+
- ``e`` -- element belonging to the base ring according to ``self``
|
|
3105
|
+
|
|
3106
|
+
OUTPUT: the Ore polynomial corresponding to `e` according to ``self``
|
|
3107
|
+
|
|
3108
|
+
TESTS::
|
|
3109
|
+
|
|
3110
|
+
sage: # needs sage.rings.finite_rings
|
|
3111
|
+
sage: from sage.rings.polynomial.ore_polynomial_element import OrePolynomialBaseringInjection
|
|
3112
|
+
sage: k.<t> = GF(5^3)
|
|
3113
|
+
sage: Frob = k.frobenius_endomorphism()
|
|
3114
|
+
sage: S.<x> = k['x',Frob]
|
|
3115
|
+
sage: m = OrePolynomialBaseringInjection(k, k['x', Frob])
|
|
3116
|
+
sage: m(4)
|
|
3117
|
+
4
|
|
3118
|
+
sage: parent(m(4))
|
|
3119
|
+
Ore Polynomial Ring in x over Finite Field in t of size 5^3 twisted by t |--> t^5
|
|
3120
|
+
"""
|
|
3121
|
+
try:
|
|
3122
|
+
return self._codomain._element_constructor_(e)
|
|
3123
|
+
except AttributeError:
|
|
3124
|
+
return self._codomain(e)
|
|
3125
|
+
|
|
3126
|
+
def section(self):
|
|
3127
|
+
r"""
|
|
3128
|
+
Return the canonical homomorphism from the constants of an Ore
|
|
3129
|
+
polynomial ring to the base ring according to ``self``.
|
|
3130
|
+
|
|
3131
|
+
TESTS::
|
|
3132
|
+
|
|
3133
|
+
sage: # needs sage.rings.finite_rings
|
|
3134
|
+
sage: from sage.rings.polynomial.ore_polynomial_element import OrePolynomialBaseringInjection
|
|
3135
|
+
sage: k.<t> = GF(5^3)
|
|
3136
|
+
sage: Frob = k.frobenius_endomorphism()
|
|
3137
|
+
sage: S.<x> = k['x',Frob]
|
|
3138
|
+
sage: m = OrePolynomialBaseringInjection(k, k['x', Frob])
|
|
3139
|
+
sage: m.section()
|
|
3140
|
+
Generic map:
|
|
3141
|
+
From: Ore Polynomial Ring in x over Finite Field in t of size 5^3
|
|
3142
|
+
twisted by t |--> t^5
|
|
3143
|
+
To: Finite Field in t of size 5^3
|
|
3144
|
+
"""
|
|
3145
|
+
return ConstantOrePolynomialSection(self._codomain, self.domain())
|