passagemath-symbolics 10.8.1a1__cp314-cp314t-musllinux_1_2_aarch64.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (181) hide show
  1. passagemath_symbolics/__init__.py +3 -0
  2. passagemath_symbolics-10.8.1a1.dist-info/METADATA +186 -0
  3. passagemath_symbolics-10.8.1a1.dist-info/RECORD +181 -0
  4. passagemath_symbolics-10.8.1a1.dist-info/WHEEL +5 -0
  5. passagemath_symbolics-10.8.1a1.dist-info/top_level.txt +3 -0
  6. sage/all__sagemath_symbolics.py +17 -0
  7. sage/calculus/all.py +14 -0
  8. sage/calculus/calculus.py +2838 -0
  9. sage/calculus/desolvers.py +1864 -0
  10. sage/calculus/predefined.py +51 -0
  11. sage/calculus/tests.py +225 -0
  12. sage/calculus/var.cpython-314t-aarch64-linux-musl.so +0 -0
  13. sage/calculus/var.pyx +401 -0
  14. sage/dynamics/all__sagemath_symbolics.py +6 -0
  15. sage/dynamics/complex_dynamics/all.py +5 -0
  16. sage/dynamics/complex_dynamics/mandel_julia.py +765 -0
  17. sage/dynamics/complex_dynamics/mandel_julia_helper.cpython-314t-aarch64-linux-musl.so +0 -0
  18. sage/dynamics/complex_dynamics/mandel_julia_helper.pyx +1034 -0
  19. sage/ext/all__sagemath_symbolics.py +1 -0
  20. sage/ext_data/kenzo/CP2.txt +45 -0
  21. sage/ext_data/kenzo/CP3.txt +349 -0
  22. sage/ext_data/kenzo/CP4.txt +4774 -0
  23. sage/ext_data/kenzo/README.txt +49 -0
  24. sage/ext_data/kenzo/S4.txt +20 -0
  25. sage/ext_data/magma/latex/latex.m +1021 -0
  26. sage/ext_data/magma/latex/latex.spec +1 -0
  27. sage/ext_data/magma/sage/basic.m +356 -0
  28. sage/ext_data/magma/sage/sage.spec +1 -0
  29. sage/ext_data/magma/spec +9 -0
  30. sage/geometry/all__sagemath_symbolics.py +8 -0
  31. sage/geometry/hyperbolic_space/all.py +5 -0
  32. sage/geometry/hyperbolic_space/hyperbolic_coercion.py +755 -0
  33. sage/geometry/hyperbolic_space/hyperbolic_constants.py +5 -0
  34. sage/geometry/hyperbolic_space/hyperbolic_geodesic.py +2419 -0
  35. sage/geometry/hyperbolic_space/hyperbolic_interface.py +206 -0
  36. sage/geometry/hyperbolic_space/hyperbolic_isometry.py +1083 -0
  37. sage/geometry/hyperbolic_space/hyperbolic_model.py +1502 -0
  38. sage/geometry/hyperbolic_space/hyperbolic_point.py +621 -0
  39. sage/geometry/riemannian_manifolds/all.py +7 -0
  40. sage/geometry/riemannian_manifolds/parametrized_surface3d.py +1632 -0
  41. sage/geometry/riemannian_manifolds/surface3d_generators.py +461 -0
  42. sage/interfaces/all__sagemath_symbolics.py +1 -0
  43. sage/interfaces/magma.py +2991 -0
  44. sage/interfaces/magma_free.py +90 -0
  45. sage/interfaces/maple.py +1402 -0
  46. sage/interfaces/mathematica.py +1345 -0
  47. sage/interfaces/mathics.py +1312 -0
  48. sage/interfaces/sympy.py +1398 -0
  49. sage/interfaces/sympy_wrapper.py +197 -0
  50. sage/interfaces/tides.py +938 -0
  51. sage/libs/all__sagemath_symbolics.py +6 -0
  52. sage/manifolds/all.py +7 -0
  53. sage/manifolds/calculus_method.py +553 -0
  54. sage/manifolds/catalog.py +437 -0
  55. sage/manifolds/chart.py +4010 -0
  56. sage/manifolds/chart_func.py +3416 -0
  57. sage/manifolds/continuous_map.py +2183 -0
  58. sage/manifolds/continuous_map_image.py +155 -0
  59. sage/manifolds/differentiable/affine_connection.py +2475 -0
  60. sage/manifolds/differentiable/all.py +1 -0
  61. sage/manifolds/differentiable/automorphismfield.py +1383 -0
  62. sage/manifolds/differentiable/automorphismfield_group.py +604 -0
  63. sage/manifolds/differentiable/bundle_connection.py +1445 -0
  64. sage/manifolds/differentiable/characteristic_cohomology_class.py +1840 -0
  65. sage/manifolds/differentiable/chart.py +1241 -0
  66. sage/manifolds/differentiable/curve.py +1028 -0
  67. sage/manifolds/differentiable/de_rham_cohomology.py +541 -0
  68. sage/manifolds/differentiable/degenerate.py +559 -0
  69. sage/manifolds/differentiable/degenerate_submanifold.py +1668 -0
  70. sage/manifolds/differentiable/diff_form.py +1660 -0
  71. sage/manifolds/differentiable/diff_form_module.py +1062 -0
  72. sage/manifolds/differentiable/diff_map.py +1315 -0
  73. sage/manifolds/differentiable/differentiable_submanifold.py +291 -0
  74. sage/manifolds/differentiable/examples/all.py +1 -0
  75. sage/manifolds/differentiable/examples/euclidean.py +2517 -0
  76. sage/manifolds/differentiable/examples/real_line.py +897 -0
  77. sage/manifolds/differentiable/examples/sphere.py +1186 -0
  78. sage/manifolds/differentiable/examples/symplectic_space.py +187 -0
  79. sage/manifolds/differentiable/examples/symplectic_space_test.py +40 -0
  80. sage/manifolds/differentiable/integrated_curve.py +4035 -0
  81. sage/manifolds/differentiable/levi_civita_connection.py +841 -0
  82. sage/manifolds/differentiable/manifold.py +4254 -0
  83. sage/manifolds/differentiable/manifold_homset.py +1826 -0
  84. sage/manifolds/differentiable/metric.py +3032 -0
  85. sage/manifolds/differentiable/mixed_form.py +1507 -0
  86. sage/manifolds/differentiable/mixed_form_algebra.py +559 -0
  87. sage/manifolds/differentiable/multivector_module.py +800 -0
  88. sage/manifolds/differentiable/multivectorfield.py +1522 -0
  89. sage/manifolds/differentiable/poisson_tensor.py +268 -0
  90. sage/manifolds/differentiable/pseudo_riemannian.py +755 -0
  91. sage/manifolds/differentiable/pseudo_riemannian_submanifold.py +1839 -0
  92. sage/manifolds/differentiable/scalarfield.py +1343 -0
  93. sage/manifolds/differentiable/scalarfield_algebra.py +472 -0
  94. sage/manifolds/differentiable/symplectic_form.py +912 -0
  95. sage/manifolds/differentiable/symplectic_form_test.py +220 -0
  96. sage/manifolds/differentiable/tangent_space.py +412 -0
  97. sage/manifolds/differentiable/tangent_vector.py +616 -0
  98. sage/manifolds/differentiable/tensorfield.py +4665 -0
  99. sage/manifolds/differentiable/tensorfield_module.py +963 -0
  100. sage/manifolds/differentiable/tensorfield_paral.py +2450 -0
  101. sage/manifolds/differentiable/tensorfield_paral_test.py +16 -0
  102. sage/manifolds/differentiable/vector_bundle.py +1725 -0
  103. sage/manifolds/differentiable/vectorfield.py +1717 -0
  104. sage/manifolds/differentiable/vectorfield_module.py +2445 -0
  105. sage/manifolds/differentiable/vectorframe.py +1832 -0
  106. sage/manifolds/family.py +270 -0
  107. sage/manifolds/local_frame.py +1490 -0
  108. sage/manifolds/manifold.py +3090 -0
  109. sage/manifolds/manifold_homset.py +452 -0
  110. sage/manifolds/operators.py +359 -0
  111. sage/manifolds/point.py +994 -0
  112. sage/manifolds/scalarfield.py +3718 -0
  113. sage/manifolds/scalarfield_algebra.py +629 -0
  114. sage/manifolds/section.py +3111 -0
  115. sage/manifolds/section_module.py +831 -0
  116. sage/manifolds/structure.py +229 -0
  117. sage/manifolds/subset.py +2721 -0
  118. sage/manifolds/subsets/all.py +1 -0
  119. sage/manifolds/subsets/closure.py +131 -0
  120. sage/manifolds/subsets/pullback.py +883 -0
  121. sage/manifolds/topological_submanifold.py +891 -0
  122. sage/manifolds/trivialization.py +733 -0
  123. sage/manifolds/utilities.py +1348 -0
  124. sage/manifolds/vector_bundle.py +1347 -0
  125. sage/manifolds/vector_bundle_fiber.py +332 -0
  126. sage/manifolds/vector_bundle_fiber_element.py +111 -0
  127. sage/matrix/all__sagemath_symbolics.py +1 -0
  128. sage/matrix/matrix_symbolic_dense.cpython-314t-aarch64-linux-musl.so +0 -0
  129. sage/matrix/matrix_symbolic_dense.pxd +6 -0
  130. sage/matrix/matrix_symbolic_dense.pyx +1030 -0
  131. sage/matrix/matrix_symbolic_sparse.cpython-314t-aarch64-linux-musl.so +0 -0
  132. sage/matrix/matrix_symbolic_sparse.pxd +6 -0
  133. sage/matrix/matrix_symbolic_sparse.pyx +1038 -0
  134. sage/modules/all__sagemath_symbolics.py +1 -0
  135. sage/modules/vector_callable_symbolic_dense.py +105 -0
  136. sage/modules/vector_symbolic_dense.py +116 -0
  137. sage/modules/vector_symbolic_sparse.py +118 -0
  138. sage/rings/all__sagemath_symbolics.py +4 -0
  139. sage/rings/asymptotic/all.py +6 -0
  140. sage/rings/asymptotic/asymptotic_expansion_generators.py +1485 -0
  141. sage/rings/asymptotic/asymptotic_ring.py +4858 -0
  142. sage/rings/asymptotic/asymptotics_multivariate_generating_functions.py +4106 -0
  143. sage/rings/asymptotic/growth_group.py +5373 -0
  144. sage/rings/asymptotic/growth_group_cartesian.py +1400 -0
  145. sage/rings/asymptotic/term_monoid.py +5205 -0
  146. sage/rings/function_field/all__sagemath_symbolics.py +2 -0
  147. sage/rings/polynomial/all__sagemath_symbolics.py +1 -0
  148. sage/symbolic/all.py +15 -0
  149. sage/symbolic/assumptions.py +987 -0
  150. sage/symbolic/benchmark.py +93 -0
  151. sage/symbolic/callable.py +456 -0
  152. sage/symbolic/callable.pyi +66 -0
  153. sage/symbolic/comparison_impl.pyi +38 -0
  154. sage/symbolic/complexity_measures.py +35 -0
  155. sage/symbolic/constants.py +1286 -0
  156. sage/symbolic/constants_c_impl.pyi +10 -0
  157. sage/symbolic/expression_conversion_algebraic.py +310 -0
  158. sage/symbolic/expression_conversion_sympy.py +317 -0
  159. sage/symbolic/expression_conversions.py +1727 -0
  160. sage/symbolic/function_factory.py +355 -0
  161. sage/symbolic/function_factory.pyi +41 -0
  162. sage/symbolic/getitem_impl.pyi +24 -0
  163. sage/symbolic/integration/all.py +1 -0
  164. sage/symbolic/integration/external.py +271 -0
  165. sage/symbolic/integration/integral.py +1075 -0
  166. sage/symbolic/maxima_wrapper.py +162 -0
  167. sage/symbolic/operators.py +267 -0
  168. sage/symbolic/operators.pyi +61 -0
  169. sage/symbolic/pynac_constant_impl.pyi +13 -0
  170. sage/symbolic/pynac_function_impl.pyi +8 -0
  171. sage/symbolic/random_tests.py +461 -0
  172. sage/symbolic/relation.py +2062 -0
  173. sage/symbolic/ring.cpython-314t-aarch64-linux-musl.so +0 -0
  174. sage/symbolic/ring.pxd +5 -0
  175. sage/symbolic/ring.pyi +110 -0
  176. sage/symbolic/ring.pyx +1393 -0
  177. sage/symbolic/series_impl.pyi +10 -0
  178. sage/symbolic/subring.py +1025 -0
  179. sage/symbolic/symengine.py +19 -0
  180. sage/symbolic/tests.py +40 -0
  181. sage/symbolic/units.py +1468 -0
@@ -0,0 +1,1400 @@
1
+ # sage_setup: distribution = sagemath-symbolics
2
+ # sage.doctest: needs sage.graphs
3
+ r"""
4
+ Cartesian Products of Growth Groups
5
+
6
+ See :doc:`growth_group` for a description.
7
+
8
+ AUTHORS:
9
+
10
+ - Benjamin Hackl (2015)
11
+ - Daniel Krenn (2015)
12
+ - Clemens Heuberger (2016)
13
+
14
+ ACKNOWLEDGEMENT:
15
+
16
+ - Benjamin Hackl, Clemens Heuberger and Daniel Krenn are supported by the
17
+ Austrian Science Fund (FWF): P 24644-N26.
18
+
19
+ - Benjamin Hackl is supported by the Google Summer of Code 2015.
20
+
21
+
22
+ TESTS::
23
+
24
+ sage: from sage.rings.asymptotic.growth_group import GrowthGroup
25
+ sage: A = GrowthGroup('(QQ_+)^x * x^ZZ'); A
26
+ Growth Group QQ^x * x^ZZ
27
+ sage: A.construction()
28
+ (The cartesian_product functorial construction,
29
+ (Growth Group QQ^x, Growth Group x^ZZ))
30
+ sage: A.construction()[1][0].construction()
31
+ (ExponentialGrowthGroup[x], Rational Field)
32
+ sage: A.construction()[1][1].construction()
33
+ (MonomialGrowthGroup[x], Integer Ring)
34
+ sage: B = GrowthGroup('x^ZZ * y^ZZ'); B
35
+ Growth Group x^ZZ * y^ZZ
36
+ sage: B.construction()
37
+ (The cartesian_product functorial construction,
38
+ (Growth Group x^ZZ, Growth Group y^ZZ))
39
+ sage: C = GrowthGroup('x^ZZ * log(x)^ZZ * y^ZZ'); C
40
+ Growth Group x^ZZ * log(x)^ZZ * y^ZZ
41
+ sage: C.construction()
42
+ (The cartesian_product functorial construction,
43
+ (Growth Group x^ZZ * log(x)^ZZ, Growth Group y^ZZ))
44
+ sage: C.construction()[1][0].construction()
45
+ (The cartesian_product functorial construction,
46
+ (Growth Group x^ZZ, Growth Group log(x)^ZZ))
47
+ sage: C.construction()[1][1].construction()
48
+ (MonomialGrowthGroup[y], Integer Ring)
49
+
50
+ ::
51
+
52
+ sage: cm = sage.structure.element.get_coercion_model()
53
+ sage: D = GrowthGroup('(QQ_+)^x * x^QQ')
54
+ sage: cm.common_parent(A, D)
55
+ Growth Group QQ^x * x^QQ
56
+ sage: E = GrowthGroup('(ZZ_+)^x * x^QQ')
57
+ sage: cm.record_exceptions() # not tested, see #19411
58
+ sage: cm.common_parent(A, E)
59
+ Growth Group QQ^x * x^QQ
60
+ sage: for t in cm.exception_stack(): # not tested, see #19411
61
+ ....: print(t)
62
+
63
+ ::
64
+
65
+ sage: assume(SR.an_element() > 0)
66
+ sage: F = GrowthGroup('(SR_+)^n * n^ZZ * UU^n'); F
67
+ Growth Group SR^n * n^ZZ * UU^n
68
+ sage: G = GrowthGroup('QQ^n * n^QQ'); G
69
+ Growth Group QQ^n * n^QQ * Signs^n
70
+ sage: cm.common_parent(F, G)
71
+ Growth Group SR^n * n^QQ * UU^n
72
+ sage: forget()
73
+
74
+ ::
75
+
76
+ sage: A.an_element()
77
+ (1/2)^x*x
78
+ sage: tuple(E.an_element())
79
+ (1, x^(1/2))
80
+
81
+ Classes and Methods
82
+ ===================
83
+ """
84
+
85
+ # ***************************************************************************
86
+ # Copyright (C) 2014--2015 Benjamin Hackl <benjamin.hackl@aau.at>
87
+ # 2014--2015 Daniel Krenn <dev@danielkrenn.at>
88
+ #
89
+ # This program is free software: you can redistribute it and/or modify
90
+ # it under the terms of the GNU General Public License as published by
91
+ # the Free Software Foundation, either version 2 of the License, or
92
+ # (at your option) any later version.
93
+ # https://www.gnu.org/licenses/
94
+ # ***************************************************************************
95
+
96
+ from sage.structure.factory import UniqueFactory
97
+
98
+
99
+ class CartesianProductFactory(UniqueFactory):
100
+ r"""
101
+ Create various types of Cartesian products depending on its input.
102
+
103
+ INPUT:
104
+
105
+ - ``growth_groups`` -- tuple (or other iterable) of growth groups
106
+
107
+ - ``order`` -- (default: ``None``) if specified, then this order
108
+ is taken for comparing two Cartesian product elements. If ``order`` is
109
+ ``None`` this is determined automatically.
110
+
111
+ .. NOTE::
112
+
113
+ The Cartesian product of growth groups is again a growth
114
+ group. In particular, the resulting structure is partially
115
+ ordered.
116
+
117
+ The order on the product is determined as follows:
118
+
119
+ - Cartesian factors with respect to the same variable are
120
+ ordered lexicographically. This causes
121
+ ``GrowthGroup('x^ZZ * log(x)^ZZ')`` and
122
+ ``GrowthGroup('log(x)^ZZ * x^ZZ')`` to produce two
123
+ different growth groups.
124
+
125
+ - Factors over different variables are equipped with the
126
+ product order (i.e. the comparison is component-wise).
127
+
128
+ Also, note that the sets of variables of the Cartesian
129
+ factors have to be either equal or disjoint.
130
+
131
+ EXAMPLES::
132
+
133
+ sage: from sage.rings.asymptotic.growth_group import GrowthGroup
134
+ sage: A = GrowthGroup('x^ZZ'); A
135
+ Growth Group x^ZZ
136
+ sage: B = GrowthGroup('log(x)^ZZ'); B
137
+ Growth Group log(x)^ZZ
138
+ sage: C = cartesian_product([A, B]); C # indirect doctest
139
+ Growth Group x^ZZ * log(x)^ZZ
140
+ sage: C._le_ == C.le_lex
141
+ True
142
+ sage: D = GrowthGroup('y^ZZ'); D
143
+ Growth Group y^ZZ
144
+ sage: E = cartesian_product([A, D]); E # indirect doctest
145
+ Growth Group x^ZZ * y^ZZ
146
+ sage: E._le_ == E.le_product
147
+ True
148
+ sage: F = cartesian_product([C, D]); F # indirect doctest
149
+ Growth Group x^ZZ * log(x)^ZZ * y^ZZ
150
+ sage: F._le_ == F.le_product
151
+ True
152
+ sage: cartesian_product([A, E]); G # indirect doctest
153
+ Traceback (most recent call last):
154
+ ...
155
+ ValueError: The growth groups (Growth Group x^ZZ, Growth Group x^ZZ * y^ZZ)
156
+ need to have pairwise disjoint or equal variables.
157
+ sage: cartesian_product([A, B, D]) # indirect doctest
158
+ Growth Group x^ZZ * log(x)^ZZ * y^ZZ
159
+
160
+ TESTS::
161
+
162
+ sage: from sage.rings.asymptotic.growth_group_cartesian import CartesianProductFactory
163
+ sage: CartesianProductFactory('factory')([A, B], category=Groups() & Posets())
164
+ Growth Group x^ZZ * log(x)^ZZ
165
+ sage: CartesianProductFactory('factory')([], category=Sets())
166
+ Traceback (most recent call last):
167
+ ...
168
+ TypeError: Cannot create Cartesian product without factors.
169
+
170
+ sage: from sage.rings.asymptotic.growth_group import GrowthGroup
171
+ sage: G1 = GrowthGroup('x^QQ')
172
+ sage: G2 = GrowthGroup('log(x)^ZZ')
173
+ sage: G = cartesian_product([G1, G2])
174
+ sage: cartesian_product([G1, G2], category=G.category()) is G
175
+ True
176
+ """
177
+ def create_key_and_extra_args(self, growth_groups, category, **kwds):
178
+ r"""
179
+ Given the arguments and keywords, create a key that uniquely
180
+ determines this object.
181
+
182
+ TESTS::
183
+
184
+ sage: from sage.rings.asymptotic.growth_group_cartesian import CartesianProductFactory
185
+ sage: from sage.rings.asymptotic.growth_group import GrowthGroup
186
+ sage: A = GrowthGroup('x^ZZ')
187
+ sage: CartesianProductFactory('factory').create_key_and_extra_args(
188
+ ....: [A], category=Sets(), order='blub')
189
+ (((Growth Group x^ZZ,), Category of posets), {'order': 'blub'})
190
+ """
191
+
192
+ # CartesianProductPosets automatically add Posets() to their categories
193
+ from sage.categories.category import Category
194
+ from sage.categories.posets import Posets
195
+ if not isinstance(category, tuple):
196
+ category = (category,)
197
+ category = Category.join(category + (Posets(),))
198
+
199
+ return (tuple(growth_groups), category), kwds
200
+
201
+ def create_object(self, version, args, **kwds):
202
+ r"""
203
+ Create an object from the given arguments.
204
+
205
+ TESTS::
206
+
207
+ sage: from sage.rings.asymptotic.growth_group import GrowthGroup
208
+ sage: cartesian_product([GrowthGroup('x^ZZ')]) # indirect doctest
209
+ Growth Group x^ZZ
210
+ """
211
+ growth_groups, category = args
212
+ if not growth_groups:
213
+ raise TypeError('Cannot create Cartesian product without factors.')
214
+ order = kwds.pop('order', None)
215
+ if order is not None:
216
+ return GenericProduct(growth_groups, category, order=order, **kwds)
217
+
218
+ vg = tuple((g.variable_names(), g) for g in growth_groups)
219
+
220
+ # check if all groups have a variable
221
+ if not all(v for v, _ in vg):
222
+ raise NotImplementedError('Growth groups %s have no variable.' %
223
+ tuple(g for g in growth_groups
224
+ if not g.variable_names()))
225
+
226
+ # sort by variables
227
+ from itertools import groupby, product
228
+ vgs = tuple((v, tuple(gs)) for v, gs in
229
+ groupby(sorted(vg, key=lambda k: k[0]), key=lambda k: k[0]))
230
+
231
+ # check whether variables are pairwise disjoint
232
+ for u, w in product(iter(v for v, _ in vgs), repeat=2):
233
+ if u != w and not set(u).isdisjoint(set(w)):
234
+ raise ValueError('The growth groups %s need to have pairwise '
235
+ 'disjoint or equal variables.' % (growth_groups,))
236
+
237
+ # build Cartesian products
238
+ u_groups = list()
239
+ for _, gs in vgs:
240
+ gs = tuple(g for _, g in gs)
241
+ if len(gs) > 1:
242
+ u_groups.append(UnivariateProduct(gs, category, **kwds))
243
+ else:
244
+ u_groups.append(gs[0])
245
+
246
+ if len(u_groups) > 1:
247
+ m_group = MultivariateProduct(tuple(u_groups), category, **kwds)
248
+ else:
249
+ m_group = u_groups[0]
250
+ return m_group
251
+
252
+
253
+ CartesianProductGrowthGroups = CartesianProductFactory('CartesianProductGrowthGroups')
254
+
255
+
256
+ from sage.combinat.posets.cartesian_product import CartesianProductPoset
257
+ from .growth_group import GenericGrowthGroup
258
+
259
+
260
+ class GenericProduct(CartesianProductPoset, GenericGrowthGroup):
261
+ r"""
262
+ A Cartesian product of growth groups.
263
+
264
+ EXAMPLES::
265
+
266
+ sage: from sage.rings.asymptotic.growth_group import GrowthGroup
267
+ sage: P = GrowthGroup('x^QQ')
268
+ sage: L = GrowthGroup('log(x)^ZZ')
269
+ sage: C = cartesian_product([P, L], order='lex'); C # indirect doctest
270
+ Growth Group x^QQ * log(x)^ZZ
271
+ sage: C.an_element()
272
+ x^(1/2)*log(x)
273
+
274
+ ::
275
+
276
+ sage: Px = GrowthGroup('x^QQ')
277
+ sage: Lx = GrowthGroup('log(x)^ZZ')
278
+ sage: Cx = cartesian_product([Px, Lx], order='lex') # indirect doctest
279
+ sage: Py = GrowthGroup('y^QQ')
280
+ sage: C = cartesian_product([Cx, Py], order='product'); C # indirect doctest
281
+ Growth Group x^QQ * log(x)^ZZ * y^QQ
282
+ sage: C.an_element()
283
+ x^(1/2)*log(x)*y^(1/2)
284
+
285
+ .. SEEALSO::
286
+
287
+ :class:`~sage.sets.cartesian_product.CartesianProduct`,
288
+ :class:`~sage.combinat.posets.cartesian_product.CartesianProductPoset`.
289
+ """
290
+
291
+ __classcall__ = CartesianProductPoset.__classcall__
292
+
293
+ def __init__(self, sets, category, **kwds):
294
+ r"""
295
+ See :class:`GenericProduct` for details.
296
+
297
+ TESTS::
298
+
299
+ sage: from sage.rings.asymptotic.growth_group import GrowthGroup
300
+ sage: GrowthGroup('x^ZZ * y^ZZ') # indirect doctest
301
+ Growth Group x^ZZ * y^ZZ
302
+
303
+ Check :issue:`26452`::
304
+
305
+ sage: from sage.rings.asymptotic.growth_group import MonomialGrowthGroup
306
+ sage: R = QQ.extension(x^2+1, 'i')
307
+ sage: P = MonomialGrowthGroup(R, 'w')
308
+ sage: L = MonomialGrowthGroup(ZZ, 'log(w)')
309
+ sage: cartesian_product([P, L])
310
+ Growth Group w^(Number Field in i with defining polynomial x^2 + 1) * log(w)^ZZ
311
+ """
312
+ order = kwds.pop('order')
313
+ CartesianProductPoset.__init__(self, sets, category, order, **kwds)
314
+
315
+ vars = sum(iter(factor.variable_names()
316
+ for factor in self.cartesian_factors()),
317
+ tuple())
318
+ from itertools import groupby
319
+ from .growth_group import Variable
320
+ Vars = Variable(tuple(v for v, _ in groupby(vars)), repr=self._repr_short_())
321
+
322
+ GenericGrowthGroup.__init__(self, sets[0], Vars, self.category(), **kwds)
323
+
324
+ __hash__ = CartesianProductPoset.__hash__
325
+
326
+ def some_elements(self):
327
+ r"""
328
+ Return some elements of this Cartesian product of growth groups.
329
+
330
+ See :class:`TestSuite` for a typical use case.
331
+
332
+ OUTPUT: an iterator
333
+
334
+ EXAMPLES::
335
+
336
+ sage: from itertools import islice
337
+ sage: from sage.rings.asymptotic.growth_group import GrowthGroup
338
+ sage: G = GrowthGroup('(QQ_+)^y * x^QQ * log(x)^ZZ')
339
+ sage: tuple(islice(G.some_elements(), 10r))
340
+ (x^(1/2)*(1/2)^y,
341
+ x^(-1/2)*log(x)*2^y,
342
+ x^2*log(x)^(-1),
343
+ x^(-2)*log(x)^2*42^y,
344
+ log(x)^(-2)*(2/3)^y,
345
+ x*log(x)^3*(3/2)^y,
346
+ x^(-1)*log(x)^(-3)*(4/5)^y,
347
+ x^42*log(x)^4*(5/4)^y,
348
+ x^(2/3)*log(x)^(-4)*(6/7)^y,
349
+ x^(-2/3)*log(x)^5*(7/6)^y)
350
+ """
351
+ return iter(
352
+ self(c) for c in
353
+ zip(*tuple(F.some_elements() for F in self.cartesian_factors())))
354
+
355
+ def _create_element_in_extension_(self, element):
356
+ r"""
357
+ Create an element in an extension of this Cartesian product of
358
+ growth groups which is chosen according to the input ``element``.
359
+
360
+ INPUT:
361
+
362
+ - ``element`` -- tuple
363
+
364
+ OUTPUT: an element
365
+
366
+ EXAMPLES::
367
+
368
+ sage: from sage.rings.asymptotic.growth_group import GrowthGroup
369
+ sage: G = GrowthGroup('z^ZZ * log(z)^ZZ')
370
+ sage: z = G('z')[0]
371
+ sage: lz = G('log(z)')[1]
372
+ sage: G._create_element_in_extension_((z^3, lz)).parent()
373
+ Growth Group z^ZZ * log(z)^ZZ
374
+ sage: G._create_element_in_extension_((z^(1/2), lz)).parent()
375
+ Growth Group z^QQ * log(z)^ZZ
376
+
377
+ ::
378
+
379
+ sage: G._create_element_in_extension_((3, 3, 3))
380
+ Traceback (most recent call last):
381
+ ...
382
+ ValueError: Cannot create (3, 3, 3) as a Cartesian product like
383
+ Growth Group z^ZZ * log(z)^ZZ.
384
+ """
385
+ factors = self.cartesian_factors()
386
+ if len(element) != len(factors):
387
+ raise ValueError('Cannot create %s as a Cartesian product like %s.' %
388
+ (element, self))
389
+
390
+ if all(n.parent() is f for n, f in zip(element, factors)):
391
+ parent = self
392
+ else:
393
+ parent = self._underlying_class()(tuple(n.parent() for n in element),
394
+ category=self.category())
395
+ return parent(element)
396
+
397
+ def _element_constructor_(self, data):
398
+ r"""
399
+ Convert the given object to an element of this Cartesian product.
400
+
401
+ EXAMPLES::
402
+
403
+ sage: from sage.rings.asymptotic.growth_group import GrowthGroup
404
+ sage: G = GrowthGroup('x^ZZ * y^ZZ')
405
+ sage: G_log = GrowthGroup('x^ZZ * log(x)^ZZ * y^ZZ')
406
+
407
+ Conversion from the symbolic ring works::
408
+
409
+ sage: x,y = var('x y')
410
+ sage: G(x^-3*y^2)
411
+ x^(-3)*y^2
412
+ sage: G(x^4), G(y^2)
413
+ (x^4, y^2)
414
+ sage: G(1)
415
+ 1
416
+
417
+ Even more complex expressions can be parsed::
418
+
419
+ sage: G_log(x^42*log(x)^-42*y^42)
420
+ x^42*log(x)^(-42)*y^42
421
+
422
+ TESTS::
423
+
424
+ sage: G = GrowthGroup('x^ZZ * y^ZZ')
425
+ sage: G('x'), G('y')
426
+ (x, y)
427
+
428
+ ::
429
+
430
+ sage: G_log(log(x))
431
+ log(x)
432
+
433
+ ::
434
+
435
+ sage: G(G.cartesian_factors()[0].gen())
436
+ x
437
+
438
+ ::
439
+
440
+ sage: GrowthGroup('QQ^x * x^QQ')(['x^(1/2)'])
441
+ x^(1/2)
442
+ sage: l = GrowthGroup('x^ZZ * log(x)^ZZ')(['x', 'log(x)']); l
443
+ x*log(x)
444
+ sage: type(l)
445
+ <class 'sage.rings.asymptotic.growth_group_cartesian.UnivariateProduct_with_category.element_class'>
446
+ sage: GrowthGroup('(QQ_+)^x * x^QQ')(['2^log(x)'])
447
+ Traceback (most recent call last):
448
+ ...
449
+ ValueError: ['2^log(x)'] is not in Growth Group QQ^x * x^QQ.
450
+ > *previous* ValueError: 2^log(x) is not in any of the factors of
451
+ Growth Group QQ^x * x^QQ
452
+ >> *previous* ValueError: 2^log(x) is not in Growth Group QQ^x.
453
+ >> *and* ValueError: 2^log(x) is not in Growth Group x^QQ.
454
+ sage: GrowthGroup('(QQ_+)^x * x^QQ')(['2^log(x)', 'x^55'])
455
+ Traceback (most recent call last):
456
+ ...
457
+ ValueError: ['2^log(x)', 'x^55'] is not in Growth Group QQ^x * x^QQ.
458
+ > *previous* ValueError: 2^log(x) is not in any of the factors of
459
+ Growth Group QQ^x * x^QQ
460
+ >> *previous* ValueError: 2^log(x) is not in Growth Group QQ^x.
461
+ >> *and* ValueError: 2^log(x) is not in Growth Group x^QQ.
462
+
463
+ ::
464
+
465
+ sage: n = GrowthGroup('n^ZZ * log(n)^ZZ')('n')
466
+ sage: G = GrowthGroup('(QQ_+)^n * n^ZZ * log(n)^ZZ')
467
+ sage: G(n).value
468
+ (1, n, 1)
469
+ """
470
+ from sage.sets.cartesian_product import CartesianProduct
471
+ from sage.symbolic.ring import SR
472
+
473
+ def convert_factors(data, raw_data):
474
+ try:
475
+ return self._convert_factors_(data)
476
+ except ValueError as e:
477
+ from .misc import combine_exceptions
478
+ raise combine_exceptions(
479
+ ValueError('%s is not in %s.' % (raw_data, self)), e)
480
+
481
+ if data == 1:
482
+ return self.one()
483
+
484
+ elif data is None:
485
+ raise ValueError('%s cannot be converted.' % (data,))
486
+
487
+ elif type(data) is self.element_class and data.parent() == self:
488
+ return data
489
+
490
+ elif isinstance(data, str):
491
+ from .misc import split_str_by_op
492
+ return convert_factors(split_str_by_op(data, '*'), data)
493
+
494
+ elif hasattr(data, 'parent'):
495
+ P = data.parent()
496
+
497
+ if P is self:
498
+ return data
499
+
500
+ elif P is SR:
501
+ from sage.symbolic.operators import mul_vararg
502
+ if data.operator() == mul_vararg:
503
+ return convert_factors(data.operands(), data)
504
+
505
+ # room for other parents (e.g. polynomial ring et al.)
506
+
507
+ try:
508
+ return super()._element_constructor_(data)
509
+ except (TypeError, ValueError):
510
+ pass
511
+ if isinstance(data, (tuple, list, CartesianProduct.Element)):
512
+ return convert_factors(tuple(data), data)
513
+
514
+ return convert_factors((data,), data)
515
+
516
+ _repr_ = GenericGrowthGroup._repr_
517
+
518
+ def _repr_short_(self):
519
+ r"""
520
+ A short (shorter than :meth:`._repr_`) representation string
521
+ for this Cartesian product of growth groups.
522
+
523
+ OUTPUT: string
524
+
525
+ EXAMPLES::
526
+
527
+ sage: from sage.rings.asymptotic.growth_group import GrowthGroup
528
+ sage: P = GrowthGroup('x^QQ')
529
+ sage: L = GrowthGroup('log(x)^ZZ')
530
+ sage: cartesian_product([P, L], order='lex')._repr_short_()
531
+ 'x^QQ * log(x)^ZZ'
532
+ """
533
+ return ' * '.join(S._repr_short_() for S in self.cartesian_factors())
534
+
535
+ def _convert_factors_(self, factors):
536
+ r"""
537
+ Helper method. Try to convert some ``factors`` to an
538
+ element of one of the Cartesian factors and return the product of
539
+ all these factors.
540
+
541
+ INPUT:
542
+
543
+ - ``factors`` -- tuple or other iterable
544
+
545
+ OUTPUT: an element of this Cartesian product
546
+
547
+ EXAMPLES::
548
+
549
+ sage: from sage.rings.asymptotic.growth_group import GrowthGroup
550
+ sage: G = GrowthGroup('x^ZZ * log(x)^QQ * y^QQ')
551
+ sage: e1 = G._convert_factors_([x^2])
552
+ sage: (e1, e1.parent())
553
+ (x^2, Growth Group x^ZZ * log(x)^QQ * y^QQ)
554
+
555
+ ::
556
+
557
+ sage: G = GrowthGroup('(QQ_+)^n * n^ZZ * UU^n')
558
+ sage: n = SR.var('n')
559
+ sage: G((-2)^n)
560
+ 2^n*(-1)^n
561
+ """
562
+ from sage.misc.misc_c import prod
563
+ from .growth_group import PartialConversionValueError
564
+ from .misc import combine_exceptions
565
+
566
+ def get_factors(data):
567
+ result = []
568
+ errors = []
569
+ for factor in self.cartesian_factors():
570
+ try:
571
+ try:
572
+ result.append((factor, factor(data)))
573
+ break
574
+ except PartialConversionValueError as e:
575
+ try:
576
+ element, todo = e.element.split()
577
+ except NotImplementedError as nie:
578
+ raise combine_exceptions(
579
+ ValueError('cannot split {}: no splitting '
580
+ 'implemented'.format(e.element)),
581
+ nie)
582
+ except ValueError as ve:
583
+ raise combine_exceptions(
584
+ ValueError('cannot split {} after failed '
585
+ 'conversion into element of '
586
+ '{}'.format(e.element, factor)),
587
+ ve)
588
+ assert todo is not None
589
+ result.append((factor, element))
590
+ data = todo
591
+ except (ValueError, TypeError) as error:
592
+ errors.append(error)
593
+ if not result:
594
+ raise combine_exceptions(
595
+ ValueError('%s is not in any of the factors of %s' % (data, self)),
596
+ *errors)
597
+ return result
598
+
599
+ return prod(self.cartesian_injection(*fs)
600
+ for f in factors for fs in get_factors(f))
601
+
602
+ def cartesian_injection(self, factor, element):
603
+ r"""
604
+ Inject the given element into this Cartesian product at the given factor.
605
+
606
+ INPUT:
607
+
608
+ - ``factor`` -- a growth group (a factor of this Cartesian product)
609
+
610
+ - ``element`` -- an element of ``factor``
611
+
612
+ OUTPUT: an element of this Cartesian product
613
+
614
+ TESTS::
615
+
616
+ sage: from sage.rings.asymptotic.growth_group import GrowthGroup
617
+ sage: G = GrowthGroup('x^ZZ * y^QQ')
618
+ sage: G.cartesian_injection(G.cartesian_factors()[1], 'y^7')
619
+ y^7
620
+ """
621
+ return self(tuple((f.one() if f != factor else element)
622
+ for f in self.cartesian_factors()))
623
+
624
+ def _coerce_map_from_(self, S):
625
+ r"""
626
+ Return whether ``S`` coerces into this growth group.
627
+
628
+ INPUT:
629
+
630
+ - ``S`` -- a parent
631
+
632
+ OUTPUT: boolean
633
+
634
+ TESTS::
635
+
636
+ sage: from sage.rings.asymptotic.growth_group import GrowthGroup
637
+ sage: A = GrowthGroup('QQ^x * x^QQ')
638
+ sage: B = GrowthGroup('QQ^x * x^ZZ')
639
+ sage: A.has_coerce_map_from(B) # indirect doctest
640
+ True
641
+ sage: B.has_coerce_map_from(A) # indirect doctest
642
+ False
643
+ """
644
+ if CartesianProductPoset.has_coerce_map_from(self, S):
645
+ return True
646
+
647
+ elif isinstance(S, GenericProduct):
648
+ factors = S.cartesian_factors()
649
+ else:
650
+ factors = (S,)
651
+
652
+ if all(any(g.has_coerce_map_from(f) for g in self.cartesian_factors())
653
+ for f in factors):
654
+ return True
655
+
656
+ def _pushout_(self, other):
657
+ r"""
658
+ Construct the pushout of this and the other growth group. This is called by
659
+ :func:`sage.categories.pushout.pushout`.
660
+
661
+ TESTS::
662
+
663
+ sage: from sage.rings.asymptotic.growth_group import GrowthGroup
664
+ sage: from sage.categories.pushout import pushout
665
+ sage: cm = sage.structure.element.get_coercion_model()
666
+ sage: A = GrowthGroup('(QQ_+)^x * x^ZZ')
667
+ sage: B = GrowthGroup('x^ZZ * log(x)^ZZ')
668
+ sage: A._pushout_(B)
669
+ Growth Group QQ^x * x^ZZ * log(x)^ZZ
670
+ sage: pushout(A, B)
671
+ Growth Group QQ^x * x^ZZ * log(x)^ZZ
672
+ sage: cm.discover_coercion(A, B)
673
+ ((map internal to coercion system -- copy before use)
674
+ Coercion map:
675
+ From: Growth Group QQ^x * x^ZZ
676
+ To: Growth Group QQ^x * x^ZZ * log(x)^ZZ,
677
+ (map internal to coercion system -- copy before use)
678
+ Coercion map:
679
+ From: Growth Group x^ZZ * log(x)^ZZ
680
+ To: Growth Group QQ^x * x^ZZ * log(x)^ZZ)
681
+ sage: cm.common_parent(A, B)
682
+ Growth Group QQ^x * x^ZZ * log(x)^ZZ
683
+
684
+ ::
685
+
686
+ sage: C = GrowthGroup('(QQ_+)^x * x^QQ * y^ZZ')
687
+ sage: D = GrowthGroup('x^ZZ * log(x)^QQ * (QQ_+)^z')
688
+ sage: C._pushout_(D)
689
+ Growth Group QQ^x * x^QQ * log(x)^QQ * y^ZZ * QQ^z
690
+ sage: cm.common_parent(C, D)
691
+ Growth Group QQ^x * x^QQ * log(x)^QQ * y^ZZ * QQ^z
692
+ sage: A._pushout_(D)
693
+ Growth Group QQ^x * x^ZZ * log(x)^QQ * QQ^z
694
+ sage: cm.common_parent(A, D)
695
+ Growth Group QQ^x * x^ZZ * log(x)^QQ * QQ^z
696
+ sage: cm.common_parent(B, D)
697
+ Growth Group x^ZZ * log(x)^QQ * QQ^z
698
+ sage: cm.common_parent(A, C)
699
+ Growth Group QQ^x * x^QQ * y^ZZ
700
+ sage: E = GrowthGroup('log(x)^ZZ * y^ZZ')
701
+ sage: cm.common_parent(A, E)
702
+ Traceback (most recent call last):
703
+ ...
704
+ TypeError: no common canonical parent for objects with parents:
705
+ 'Growth Group QQ^x * x^ZZ' and 'Growth Group log(x)^ZZ * y^ZZ'
706
+
707
+ ::
708
+
709
+ sage: F = GrowthGroup('z^QQ')
710
+ sage: pushout(C, F)
711
+ Growth Group QQ^x * x^QQ * y^ZZ * z^QQ
712
+
713
+ ::
714
+
715
+ sage: pushout(GrowthGroup('(QQ_+)^x * x^ZZ'), GrowthGroup('(ZZ_+)^x * x^QQ'))
716
+ Growth Group QQ^x * x^QQ
717
+ sage: cm.common_parent(GrowthGroup('(QQ_+)^x * x^ZZ'), GrowthGroup('(ZZ_+)^x * x^QQ'))
718
+ Growth Group QQ^x * x^QQ
719
+
720
+ ::
721
+
722
+ sage: pushout(GrowthGroup('(QQ_+)^n * n^QQ'), GrowthGroup('(SR_+)^n'))
723
+ Growth Group SR^n * n^QQ
724
+
725
+ ::
726
+
727
+ sage: cm.common_parent(GrowthGroup('n^ZZ * log(n)^ZZ * UU^n'),
728
+ ....: GrowthGroup('n^QQ * UU^n'))
729
+ Growth Group n^QQ * log(n)^ZZ * UU^n
730
+ """
731
+ from .growth_group import GenericGrowthGroup, AbstractGrowthGroupFunctor
732
+ from .misc import bidirectional_merge_sorted
733
+ from sage.structure.element import get_coercion_model
734
+
735
+ Sfactors = self.cartesian_factors()
736
+ if isinstance(other, GenericProduct):
737
+ Ofactors = other.cartesian_factors()
738
+ elif isinstance(other, GenericGrowthGroup):
739
+ Ofactors = (other,)
740
+ elif (other.construction() is not None and
741
+ isinstance(other.construction()[0], AbstractGrowthGroupFunctor)):
742
+ Ofactors = (other,)
743
+ else:
744
+ return
745
+
746
+ def pushout_univariate_factors(self, other, var, Sfactors, Ofactors):
747
+ try:
748
+ return bidirectional_merge_sorted(
749
+ Sfactors, Ofactors,
750
+ lambda f: (f._underlying_class(), f._var_.var_repr))
751
+ except RuntimeError:
752
+ pass
753
+
754
+ cm = get_coercion_model()
755
+ try:
756
+ Z = cm.common_parent(*Sfactors+Ofactors)
757
+ return (Z,), (Z,)
758
+ except TypeError:
759
+ pass
760
+
761
+ def subfactors(F):
762
+ for f in F:
763
+ if isinstance(f, GenericProduct):
764
+ yield from subfactors(f.cartesian_factors())
765
+ else:
766
+ yield f
767
+
768
+ try:
769
+ return bidirectional_merge_sorted(
770
+ tuple(subfactors(Sfactors)), tuple(subfactors(Ofactors)),
771
+ lambda f: (f._underlying_class(), f._var_.var_repr))
772
+ except RuntimeError:
773
+ pass
774
+
775
+ from sage.structure.coerce_exceptions import CoercionException
776
+ raise CoercionException(
777
+ 'Cannot construct the pushout of %s and %s: The factors '
778
+ 'with variables %s are not overlapping, '
779
+ 'no common parent was found, and '
780
+ 'splitting the factors was unsuccessful.' % (self, other, var))
781
+
782
+ # A wrapper around an iterator that stores additional intermediate data.
783
+ # This deviates slightly from the iterator protocol:
784
+ # At the end of the iteration the data is reset to None instead
785
+ # of raising a StopIteration.
786
+ class it:
787
+ def __init__(self, it):
788
+ self.it = it
789
+ self.var = None
790
+ self.factors = None
791
+
792
+ def next_custom(self):
793
+ try:
794
+ self.var, factors = next(self.it)
795
+ self.factors = tuple(factors)
796
+ except StopIteration:
797
+ self.var = None
798
+ self.factors = tuple()
799
+
800
+ from itertools import groupby
801
+ S = it(groupby(Sfactors, key=lambda k: k.variable_names()))
802
+ O = it(groupby(Ofactors, key=lambda k: k.variable_names()))
803
+
804
+ newS = []
805
+ newO = []
806
+
807
+ S.next_custom()
808
+ O.next_custom()
809
+ while S.var is not None or O.var is not None:
810
+ if S.var is not None and O.var is not None and S.var < O.var:
811
+ newS.extend(S.factors)
812
+ newO.extend(S.factors)
813
+ S.next_custom()
814
+ elif S.var is not None and O.var is not None and S.var > O.var:
815
+ newS.extend(O.factors)
816
+ newO.extend(O.factors)
817
+ O.next_custom()
818
+ else:
819
+ SL, OL = pushout_univariate_factors(self, other, S.var,
820
+ S.factors, O.factors)
821
+ newS.extend(SL)
822
+ newO.extend(OL)
823
+ S.next_custom()
824
+ O.next_custom()
825
+
826
+ assert (len(newS) == len(newO))
827
+
828
+ if (len(Sfactors) == len(newS) and
829
+ len(Ofactors) == len(newO)):
830
+ # We had already all factors in each of self and
831
+ # other, thus splitting it in subproblems (one for
832
+ # each factor) is the strategy to use. If a pushout is
833
+ # possible :func:`sage.categories.pushout.pushout`
834
+ # will manage this by itself.
835
+ return
836
+
837
+ from sage.categories.pushout import pushout
838
+ from sage.categories.cartesian_product import cartesian_product
839
+ return pushout(cartesian_product(newS), cartesian_product(newO))
840
+
841
+ def gens_monomial(self) -> tuple:
842
+ r"""
843
+ Return a tuple containing monomial generators of this growth group.
844
+
845
+ OUTPUT: a tuple containing elements of this growth group
846
+
847
+ .. NOTE::
848
+
849
+ This method calls the ``gens_monomial()`` method on the
850
+ individual factors of this Cartesian product and
851
+ concatenates the respective outputs.
852
+
853
+ EXAMPLES::
854
+
855
+ sage: from sage.rings.asymptotic.growth_group import GrowthGroup
856
+ sage: G = GrowthGroup('x^ZZ * log(x)^ZZ * y^QQ * log(z)^ZZ')
857
+ sage: G.gens_monomial()
858
+ (x, y)
859
+
860
+ TESTS::
861
+
862
+ sage: all(g.parent() == G for g in G.gens_monomial())
863
+ True
864
+ """
865
+ return sum(iter(
866
+ tuple(self.cartesian_injection(factor, g) for g in factor.gens_monomial())
867
+ for factor in self.cartesian_factors()),
868
+ tuple())
869
+
870
+ def variable_names(self):
871
+ r"""
872
+ Return the names of the variables.
873
+
874
+ OUTPUT: a tuple of strings
875
+
876
+ EXAMPLES::
877
+
878
+ sage: from sage.rings.asymptotic.growth_group import GrowthGroup
879
+ sage: GrowthGroup('x^ZZ * log(x)^ZZ * y^QQ * log(z)^ZZ').variable_names()
880
+ ('x', 'y', 'z')
881
+ """
882
+ vars = sum(iter(factor.variable_names()
883
+ for factor in self.cartesian_factors()),
884
+ tuple())
885
+ from itertools import groupby
886
+ return tuple(v for v, _ in groupby(vars))
887
+
888
+ class Element(CartesianProductPoset.Element):
889
+
890
+ from .growth_group import _is_lt_one_
891
+ is_lt_one = _is_lt_one_
892
+
893
+ def _repr_(self, latex=False):
894
+ r"""
895
+ A representation string for this Cartesian product element.
896
+
897
+ INPUT:
898
+
899
+ - ``latex`` -- boolean (default: ``False``); if set, then
900
+ LaTeX-output is returned
901
+
902
+ OUTPUT: string
903
+
904
+ EXAMPLES::
905
+
906
+ sage: from sage.rings.asymptotic.growth_group import GrowthGroup
907
+ sage: P = GrowthGroup('x^QQ')
908
+ sage: L = GrowthGroup('log(x)^ZZ')
909
+ sage: cartesian_product([P, L], order='lex').an_element()._repr_()
910
+ 'x^(1/2)*log(x)'
911
+ """
912
+ if latex:
913
+ from sage.misc.latex import latex as latex_repr
914
+ f = latex_repr
915
+ else:
916
+ f = repr
917
+
918
+ mul = ' ' if latex else '*'
919
+ s = mul.join(f(v) for v in self.value if not v.is_one())
920
+ if s == '':
921
+ return '1'
922
+ return s
923
+
924
+ def _latex_(self):
925
+ r"""
926
+ A representation string for this Cartesian product element.
927
+
928
+ OUTPUT: string
929
+
930
+ TESTS::
931
+
932
+ sage: from sage.rings.asymptotic.growth_group import GrowthGroup
933
+ sage: P = GrowthGroup('x^QQ')
934
+ sage: L = GrowthGroup('log(x)^ZZ')
935
+ sage: latex(cartesian_product([P, L], order='lex').an_element()) # indirect doctest
936
+ x^{\frac{1}{2}} \log\left(x\right)
937
+ sage: latex(GrowthGroup('(QQ_+)^n * n^QQ').an_element()) # indirect doctest
938
+ \left(\frac{1}{2}\right)^{n} n^{\frac{1}{2}}
939
+ """
940
+ return self._repr_(latex=True)
941
+
942
+ def __pow__(self, exponent):
943
+ r"""
944
+ Calculate the power of this growth element to the given
945
+ ``exponent``.
946
+
947
+ INPUT:
948
+
949
+ - ``exponent`` -- a number
950
+
951
+ OUTPUT: a growth element
952
+
953
+ EXAMPLES::
954
+
955
+ sage: from sage.rings.asymptotic.growth_group import GrowthGroup
956
+ sage: G = GrowthGroup('x^ZZ * y^QQ * z^ZZ')
957
+ sage: x, y, z = G.gens_monomial()
958
+ sage: (x^5 * y * z^5)^(1/5) # indirect doctest
959
+ x*y^(1/5)*z
960
+
961
+ ::
962
+
963
+ sage: G = GrowthGroup('x^QQ * log(x)^QQ'); x = G('x')
964
+ sage: (x^(21/5) * log(x)^7)^(1/42) # indirect doctest
965
+ x^(1/10)*log(x)^(1/6)
966
+ """
967
+ return self.parent()._create_element_in_extension_(
968
+ tuple(x ** exponent for x in self.cartesian_factors()))
969
+
970
+ def factors(self):
971
+ r"""
972
+ Return the atomic factors of this growth element. An atomic factor
973
+ cannot be split further and is not the identity (`1`).
974
+
975
+ OUTPUT: a tuple of growth elements
976
+
977
+ EXAMPLES::
978
+
979
+ sage: from sage.rings.asymptotic.growth_group import GrowthGroup
980
+ sage: G = GrowthGroup('x^ZZ * log(x)^ZZ * y^ZZ')
981
+ sage: x, y = G.gens_monomial()
982
+ sage: x.factors()
983
+ (x,)
984
+ sage: f = (x * y).factors(); f
985
+ (x, y)
986
+ sage: tuple(factor.parent() for factor in f)
987
+ (Growth Group x^ZZ, Growth Group y^ZZ)
988
+ sage: f = (x * log(x)).factors(); f
989
+ (x, log(x))
990
+ sage: tuple(factor.parent() for factor in f)
991
+ (Growth Group x^ZZ, Growth Group log(x)^ZZ)
992
+
993
+ ::
994
+
995
+ sage: G = GrowthGroup('x^ZZ * log(x)^ZZ * log(log(x))^ZZ * y^QQ')
996
+ sage: x, y = G.gens_monomial()
997
+ sage: f = (x * log(x) * y).factors(); f
998
+ (x, log(x), y)
999
+ sage: tuple(factor.parent() for factor in f)
1000
+ (Growth Group x^ZZ, Growth Group log(x)^ZZ, Growth Group y^QQ)
1001
+
1002
+ ::
1003
+
1004
+ sage: G.one().factors()
1005
+ ()
1006
+ """
1007
+ return sum(iter(f.factors()
1008
+ for f in self.cartesian_factors()
1009
+ if not f.is_one()),
1010
+ tuple())
1011
+
1012
+ from .growth_group import _log_factor_, _log_
1013
+ log = _log_
1014
+ log_factor = _log_factor_
1015
+
1016
+ def _log_factor_(self, base=None, locals=None):
1017
+ r"""
1018
+ Helper method for calculating the logarithm of the factorization
1019
+ of this element.
1020
+
1021
+ INPUT:
1022
+
1023
+ - ``base`` -- the base of the logarithm; if ``None``
1024
+ (default value) is used, the natural logarithm is taken
1025
+
1026
+ - ``locals`` -- dictionary which may contain the following keys and
1027
+ values:
1028
+
1029
+ - ``'log'`` -- value: a function; if not used, then the usual
1030
+ :class:`log <sage.functions.log.Function_log>` is taken
1031
+
1032
+ OUTPUT:
1033
+
1034
+ A tuple of pairs, where the first entry is either a growth
1035
+ element or something out of which we can construct a growth element
1036
+ and the second a multiplicative coefficient.
1037
+
1038
+ TESTS::
1039
+
1040
+ sage: from sage.rings.asymptotic.growth_group import GrowthGroup
1041
+ sage: G = GrowthGroup('QQ^x * x^ZZ * log(x)^ZZ * y^ZZ * log(y)^ZZ')
1042
+ sage: x, y = G.gens_monomial()
1043
+ sage: (x * y).log_factor() # indirect doctest
1044
+ ((log(x), 1), (log(y), 1))
1045
+ """
1046
+ if self.is_one():
1047
+ return tuple()
1048
+
1049
+ def try_create_growth(g):
1050
+ try:
1051
+ return self.parent()(g)
1052
+ except (TypeError, ValueError):
1053
+ return g
1054
+
1055
+ try:
1056
+ return sum(iter(tuple((try_create_growth(g), c)
1057
+ for g, c in
1058
+ factor._log_factor_(base=base,
1059
+ locals=locals))
1060
+ for factor in self.cartesian_factors()
1061
+ if factor != factor.parent().one()),
1062
+ tuple())
1063
+ except (ArithmeticError, TypeError, ValueError) as e:
1064
+ from .misc import combine_exceptions
1065
+ raise combine_exceptions(
1066
+ ArithmeticError('Cannot build log(%s) in %s.' %
1067
+ (self, self.parent())), e)
1068
+
1069
+ from .growth_group import _rpow_
1070
+ rpow = _rpow_
1071
+
1072
+ def _rpow_element_(self, base):
1073
+ r"""
1074
+ Return an element which is the power of ``base`` to this element.
1075
+
1076
+ INPUT:
1077
+
1078
+ - ``base`` -- an element
1079
+
1080
+ OUTPUT: a growth element
1081
+
1082
+ .. NOTE::
1083
+
1084
+ The parent of the result can be different from the parent
1085
+ of this element.
1086
+
1087
+ A :exc:`ValueError` is raised if the calculation is not possible
1088
+ within this method. (Then the calling method should take care
1089
+ of the calculation.)
1090
+
1091
+ TESTS::
1092
+
1093
+ sage: from sage.rings.asymptotic.growth_group import GrowthGroup
1094
+ sage: G = GrowthGroup('QQ^x * x^ZZ * log(x)^ZZ')
1095
+ sage: lx = log(G('x'))
1096
+ sage: rp = lx._rpow_element_('e'); rp
1097
+ x
1098
+ sage: rp.parent()
1099
+ Growth Group x^ZZ
1100
+ """
1101
+ factors = self.factors()
1102
+ if len(factors) != 1:
1103
+ raise ValueError # calling method has to deal with it...
1104
+ from .growth_group import MonomialGrowthGroup
1105
+ factor = factors[0]
1106
+ if not isinstance(factor.parent(), MonomialGrowthGroup):
1107
+ raise ValueError # calling method has to deal with it...
1108
+ return factor._rpow_element_(base)
1109
+
1110
+ def exp(self):
1111
+ r"""
1112
+ The exponential of this element.
1113
+
1114
+ OUTPUT: a growth element
1115
+
1116
+ EXAMPLES::
1117
+
1118
+ sage: from sage.rings.asymptotic.growth_group import GrowthGroup
1119
+ sage: G = GrowthGroup('x^ZZ * log(x)^ZZ * log(log(x))^ZZ')
1120
+ sage: x = G('x')
1121
+ sage: exp(log(x))
1122
+ x
1123
+ sage: exp(log(log(x)))
1124
+ log(x)
1125
+
1126
+ ::
1127
+
1128
+ sage: exp(x)
1129
+ Traceback (most recent call last):
1130
+ ...
1131
+ ArithmeticError: Cannot construct e^x in
1132
+ Growth Group x^ZZ * log(x)^ZZ * log(log(x))^ZZ
1133
+ > *previous* TypeError: unsupported operand parent(s) for *:
1134
+ 'Growth Group x^ZZ * log(x)^ZZ * log(log(x))^ZZ' and
1135
+ 'Growth Group (e^x)^ZZ'
1136
+
1137
+ TESTS::
1138
+
1139
+ sage: E = GrowthGroup("(e^y)^QQ * y^QQ * log(y)^QQ")
1140
+ sage: y = E('y')
1141
+ sage: log(exp(y))
1142
+ y
1143
+ sage: exp(log(y))
1144
+ y
1145
+ """
1146
+ return self.rpow('e')
1147
+
1148
+ def __invert__(self):
1149
+ r"""
1150
+ Return the multiplicative inverse of this Cartesian product.
1151
+
1152
+ OUTPUT: a growth element
1153
+
1154
+ .. NOTE::
1155
+
1156
+ The result may live in a larger parent than we started with.
1157
+
1158
+ TESTS::
1159
+
1160
+ sage: from sage.rings.asymptotic.growth_group import GrowthGroup
1161
+ sage: G = GrowthGroup('(ZZ_+)^x * x^ZZ')
1162
+ sage: g = G('2^x * x^3')
1163
+ sage: (~g).parent()
1164
+ Growth Group QQ^x * x^ZZ
1165
+ """
1166
+ return self.parent()._create_element_in_extension_(
1167
+ tuple(~x for x in self.cartesian_factors()))
1168
+
1169
+ def _substitute_(self, rules):
1170
+ r"""
1171
+ Substitute the given ``rules`` in this
1172
+ Cartesian product growth element.
1173
+
1174
+ INPUT:
1175
+
1176
+ - ``rules`` -- dictionary; the neutral element of the group is
1177
+ replaced by the value to key ``'_one_'``
1178
+
1179
+ OUTPUT: an object
1180
+
1181
+ TESTS::
1182
+
1183
+ sage: from sage.rings.asymptotic.growth_group import GrowthGroup
1184
+ sage: G = GrowthGroup('x^QQ * log(x)^QQ')
1185
+ sage: G(x^3 * log(x)^5)._substitute_({'x': SR.var('z')})
1186
+ z^3*log(z)^5
1187
+ sage: _.parent()
1188
+ Symbolic Ring
1189
+ sage: G(x^3 * log(x)^5)._substitute_({'x': 2.2}) # rel tol 1e-6
1190
+ 3.24458458945
1191
+ sage: _.parent()
1192
+ Real Field with 53 bits of precision
1193
+ sage: G(1 / x)._substitute_({'x': 0})
1194
+ Traceback (most recent call last):
1195
+ ...
1196
+ ZeroDivisionError: Cannot substitute in x^(-1) in
1197
+ Growth Group x^QQ * log(x)^QQ.
1198
+ > *previous* ZeroDivisionError: Cannot substitute in x^(-1) in
1199
+ Growth Group x^QQ.
1200
+ >> *previous* ZeroDivisionError: rational division by zero
1201
+ sage: G(1)._substitute_({'_one_': 'one'})
1202
+ 'one'
1203
+ """
1204
+ if self.is_one():
1205
+ return rules['_one_']
1206
+ from sage.symbolic.operators import mul_vararg
1207
+ try:
1208
+ return mul_vararg(
1209
+ *tuple(x._substitute_(rules)
1210
+ for x in self.cartesian_factors()))
1211
+ except (ArithmeticError, TypeError, ValueError) as e:
1212
+ from .misc import substitute_raise_exception
1213
+ substitute_raise_exception(self, e)
1214
+
1215
+ def _singularity_analysis_(self, var, zeta, precision):
1216
+ r"""
1217
+ Perform singularity analysis on this growth element.
1218
+
1219
+ INPUT:
1220
+
1221
+ - ``var`` -- string denoting the variable
1222
+
1223
+ - ``zeta`` -- a number
1224
+
1225
+ - ``precision`` -- integer
1226
+
1227
+ OUTPUT:
1228
+
1229
+ An asymptotic expansion for `[z^n] f` where `n` is ``var``
1230
+ and `f` has this growth element as a singular expansion
1231
+ in `T=\frac{1}{1-\frac{z}{\zeta}}\to \infty` where this
1232
+ element is a growth element in `T`.
1233
+
1234
+ EXAMPLES::
1235
+
1236
+ sage: from sage.rings.asymptotic.growth_group import GrowthGroup
1237
+ sage: G = GrowthGroup('exp(x)^QQ * x^QQ * log(x)^QQ')
1238
+ sage: G(x^(1/2))._singularity_analysis_('n', 2, precision=2)
1239
+ 1/sqrt(pi)*(1/2)^n*n^(-1/2) - 1/8/sqrt(pi)*(1/2)^n*n^(-3/2)
1240
+ + O((1/2)^n*n^(-5/2))
1241
+ sage: G(log(x))._singularity_analysis_('n', 1, precision=5)
1242
+ n^(-1) + O(n^(-3))
1243
+ sage: G(x*log(x))._singularity_analysis_('n', 1, precision=5)
1244
+ log(n) + euler_gamma + 1/2*n^(-1) + O(n^(-2))
1245
+
1246
+ TESTS::
1247
+
1248
+ sage: G('exp(x)*log(x)')._singularity_analysis_('n', 1, precision=5)
1249
+ Traceback (most recent call last):
1250
+ ...
1251
+ NotImplementedError: singularity analysis of exp(x)*log(x)
1252
+ not implemented
1253
+ sage: G('exp(x)*x*log(x)')._singularity_analysis_('n', 1, precision=5)
1254
+ Traceback (most recent call last):
1255
+ ...
1256
+ NotImplementedError: singularity analysis of exp(x)*x*log(x)
1257
+ not yet implemented since it has more than two factors
1258
+ sage: G(1)._singularity_analysis_('n', 2, precision=3)
1259
+ Traceback (most recent call last):
1260
+ ...
1261
+ NotImplementedOZero: got O(0)
1262
+ The error term O(0) means 0 for sufficiently large n.
1263
+ sage: G('exp(x)')._singularity_analysis_('n', 2, precision=3)
1264
+ Traceback (most recent call last):
1265
+ ...
1266
+ NotImplementedError: singularity analysis of exp(x)
1267
+ not implemented
1268
+ """
1269
+ factors = self.factors()
1270
+ if len(factors) == 0:
1271
+ from .asymptotic_expansion_generators import asymptotic_expansions
1272
+ from .misc import NotImplementedOZero
1273
+ raise NotImplementedOZero(var=var, exact_part=0)
1274
+ elif len(factors) == 1:
1275
+ return factors[0]._singularity_analysis_(
1276
+ var=var, zeta=zeta, precision=precision)
1277
+ elif len(factors) == 2:
1278
+ from .growth_group import MonomialGrowthGroup
1279
+ from sage.rings.integer_ring import ZZ
1280
+
1281
+ a, b = factors
1282
+ if all(isinstance(f.parent(), MonomialGrowthGroup)
1283
+ for f in factors) \
1284
+ and a.parent().gens_monomial() \
1285
+ and b.parent().gens_logarithmic() \
1286
+ and a.parent().variable_name() == \
1287
+ b.parent().variable_name():
1288
+ if b.exponent not in ZZ:
1289
+ raise NotImplementedError(
1290
+ 'singularity analysis of {} not implemented '
1291
+ 'since exponent {} of {} is not an integer'.format(
1292
+ self, b.exponent, b.parent().gen()))
1293
+
1294
+ from sage.rings.asymptotic.asymptotic_expansion_generators import \
1295
+ asymptotic_expansions
1296
+ return asymptotic_expansions.SingularityAnalysis(
1297
+ var=var, zeta=zeta, alpha=a.exponent,
1298
+ beta=ZZ(b.exponent), delta=0,
1299
+ precision=precision, normalized=False)
1300
+ else:
1301
+ raise NotImplementedError(
1302
+ 'singularity analysis of {} not implemented'.format(self))
1303
+ else:
1304
+ raise NotImplementedError(
1305
+ 'singularity analysis of {} not yet implemented '
1306
+ 'since it has more than two factors'.format(self))
1307
+
1308
+ def variable_names(self):
1309
+ r"""
1310
+ Return the names of the variables of this growth element.
1311
+
1312
+ OUTPUT: a tuple of strings
1313
+
1314
+ EXAMPLES::
1315
+
1316
+ sage: from sage.rings.asymptotic.growth_group import GrowthGroup
1317
+ sage: G = GrowthGroup('QQ^m * m^QQ * log(n)^ZZ')
1318
+ sage: G('2^m * m^4 * log(n)').variable_names()
1319
+ ('m', 'n')
1320
+ sage: G('2^m * m^4').variable_names()
1321
+ ('m',)
1322
+ sage: G('log(n)').variable_names()
1323
+ ('n',)
1324
+ sage: G('m^3').variable_names()
1325
+ ('m',)
1326
+ sage: G('m^0').variable_names()
1327
+ ()
1328
+ """
1329
+ vars = sum(iter(factor.variable_names()
1330
+ for factor in self.factors()),
1331
+ tuple())
1332
+ from itertools import groupby
1333
+ return tuple(v for v, _ in groupby(vars))
1334
+
1335
+ CartesianProduct = CartesianProductGrowthGroups
1336
+
1337
+
1338
+ class UnivariateProduct(GenericProduct):
1339
+ r"""
1340
+ A Cartesian product of growth groups with the same variables.
1341
+
1342
+ .. NOTE::
1343
+
1344
+ A univariate product of growth groups is ordered
1345
+ lexicographically. This is motivated by the assumption
1346
+ that univariate growth groups can be ordered in a chain
1347
+ with respect to the growth they model (e.g.
1348
+ ``x^ZZ * log(x)^ZZ``: polynomial growth dominates
1349
+ logarithmic growth).
1350
+
1351
+ .. SEEALSO::
1352
+
1353
+ :class:`MultivariateProduct`,
1354
+ :class:`GenericProduct`.
1355
+ """
1356
+
1357
+ def __init__(self, sets, category, **kwargs):
1358
+ r"""
1359
+ See :class:`UnivariateProduct` for details.
1360
+
1361
+ TESTS::
1362
+
1363
+ sage: from sage.rings.asymptotic.growth_group import GrowthGroup
1364
+ sage: type(GrowthGroup('x^ZZ * log(x)^ZZ')) # indirect doctest
1365
+ <class 'sage.rings.asymptotic.growth_group_cartesian.UnivariateProduct_with_category'>
1366
+ """
1367
+ super().__init__(sets, category, order='lex', **kwargs)
1368
+
1369
+ CartesianProduct = CartesianProductGrowthGroups
1370
+
1371
+
1372
+ class MultivariateProduct(GenericProduct):
1373
+ r"""
1374
+ A Cartesian product of growth groups with pairwise disjoint
1375
+ (or equal) variable sets.
1376
+
1377
+ .. NOTE::
1378
+
1379
+ A multivariate product of growth groups is ordered by
1380
+ means of the product order, i.e. component-wise. This is
1381
+ motivated by the assumption that different variables are
1382
+ considered to be independent (e.g. ``x^ZZ * y^ZZ``).
1383
+
1384
+ .. SEEALSO::
1385
+
1386
+ :class:`UnivariateProduct`,
1387
+ :class:`GenericProduct`.
1388
+ """
1389
+ def __init__(self, sets, category, **kwargs):
1390
+ r"""
1391
+
1392
+ TESTS::
1393
+
1394
+ sage: from sage.rings.asymptotic.growth_group import GrowthGroup
1395
+ sage: type(GrowthGroup('x^ZZ * y^ZZ')) # indirect doctest
1396
+ <class 'sage.rings.asymptotic.growth_group_cartesian.MultivariateProduct_with_category'>
1397
+ """
1398
+ super().__init__(sets, category, order='product', **kwargs)
1399
+
1400
+ CartesianProduct = CartesianProductGrowthGroups