passagemath-symbolics 10.6.37__cp314-cp314t-macosx_13_0_arm64.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 (172) hide show
  1. passagemath_symbolics/.dylibs/libgmp.10.dylib +0 -0
  2. passagemath_symbolics/__init__.py +3 -0
  3. passagemath_symbolics-10.6.37.dist-info/METADATA +187 -0
  4. passagemath_symbolics-10.6.37.dist-info/RECORD +172 -0
  5. passagemath_symbolics-10.6.37.dist-info/WHEEL +6 -0
  6. passagemath_symbolics-10.6.37.dist-info/top_level.txt +3 -0
  7. sage/all__sagemath_symbolics.py +17 -0
  8. sage/calculus/all.py +14 -0
  9. sage/calculus/calculus.py +2826 -0
  10. sage/calculus/desolvers.py +1866 -0
  11. sage/calculus/predefined.py +51 -0
  12. sage/calculus/tests.py +225 -0
  13. sage/calculus/var.cpython-314t-darwin.so +0 -0
  14. sage/calculus/var.pyx +401 -0
  15. sage/dynamics/all__sagemath_symbolics.py +6 -0
  16. sage/dynamics/complex_dynamics/all.py +5 -0
  17. sage/dynamics/complex_dynamics/mandel_julia.py +765 -0
  18. sage/dynamics/complex_dynamics/mandel_julia_helper.cpython-314t-darwin.so +0 -0
  19. sage/dynamics/complex_dynamics/mandel_julia_helper.pyx +1035 -0
  20. sage/ext/all__sagemath_symbolics.py +1 -0
  21. sage/ext_data/kenzo/CP2.txt +45 -0
  22. sage/ext_data/kenzo/CP3.txt +349 -0
  23. sage/ext_data/kenzo/CP4.txt +4774 -0
  24. sage/ext_data/kenzo/README.txt +49 -0
  25. sage/ext_data/kenzo/S4.txt +20 -0
  26. sage/ext_data/magma/latex/latex.m +1021 -0
  27. sage/ext_data/magma/latex/latex.spec +1 -0
  28. sage/ext_data/magma/sage/basic.m +356 -0
  29. sage/ext_data/magma/sage/sage.spec +1 -0
  30. sage/ext_data/magma/spec +9 -0
  31. sage/geometry/all__sagemath_symbolics.py +8 -0
  32. sage/geometry/hyperbolic_space/all.py +5 -0
  33. sage/geometry/hyperbolic_space/hyperbolic_coercion.py +743 -0
  34. sage/geometry/hyperbolic_space/hyperbolic_constants.py +5 -0
  35. sage/geometry/hyperbolic_space/hyperbolic_geodesic.py +2409 -0
  36. sage/geometry/hyperbolic_space/hyperbolic_interface.py +206 -0
  37. sage/geometry/hyperbolic_space/hyperbolic_isometry.py +1082 -0
  38. sage/geometry/hyperbolic_space/hyperbolic_model.py +1502 -0
  39. sage/geometry/hyperbolic_space/hyperbolic_point.py +621 -0
  40. sage/geometry/riemannian_manifolds/all.py +7 -0
  41. sage/geometry/riemannian_manifolds/parametrized_surface3d.py +1632 -0
  42. sage/geometry/riemannian_manifolds/surface3d_generators.py +461 -0
  43. sage/interfaces/all__sagemath_symbolics.py +1 -0
  44. sage/interfaces/magma.py +3017 -0
  45. sage/interfaces/magma_free.py +92 -0
  46. sage/interfaces/maple.py +1397 -0
  47. sage/interfaces/mathematica.py +1345 -0
  48. sage/interfaces/mathics.py +1312 -0
  49. sage/interfaces/sympy.py +1398 -0
  50. sage/interfaces/sympy_wrapper.py +197 -0
  51. sage/interfaces/tides.py +938 -0
  52. sage/libs/all__sagemath_symbolics.py +6 -0
  53. sage/manifolds/all.py +7 -0
  54. sage/manifolds/calculus_method.py +555 -0
  55. sage/manifolds/catalog.py +437 -0
  56. sage/manifolds/chart.py +4019 -0
  57. sage/manifolds/chart_func.py +3419 -0
  58. sage/manifolds/continuous_map.py +2183 -0
  59. sage/manifolds/continuous_map_image.py +155 -0
  60. sage/manifolds/differentiable/affine_connection.py +2475 -0
  61. sage/manifolds/differentiable/all.py +1 -0
  62. sage/manifolds/differentiable/automorphismfield.py +1383 -0
  63. sage/manifolds/differentiable/automorphismfield_group.py +604 -0
  64. sage/manifolds/differentiable/bundle_connection.py +1445 -0
  65. sage/manifolds/differentiable/characteristic_cohomology_class.py +1840 -0
  66. sage/manifolds/differentiable/chart.py +1241 -0
  67. sage/manifolds/differentiable/curve.py +1028 -0
  68. sage/manifolds/differentiable/de_rham_cohomology.py +541 -0
  69. sage/manifolds/differentiable/degenerate.py +559 -0
  70. sage/manifolds/differentiable/degenerate_submanifold.py +1671 -0
  71. sage/manifolds/differentiable/diff_form.py +1658 -0
  72. sage/manifolds/differentiable/diff_form_module.py +1062 -0
  73. sage/manifolds/differentiable/diff_map.py +1315 -0
  74. sage/manifolds/differentiable/differentiable_submanifold.py +291 -0
  75. sage/manifolds/differentiable/examples/all.py +1 -0
  76. sage/manifolds/differentiable/examples/euclidean.py +2517 -0
  77. sage/manifolds/differentiable/examples/real_line.py +897 -0
  78. sage/manifolds/differentiable/examples/sphere.py +1186 -0
  79. sage/manifolds/differentiable/examples/symplectic_space.py +187 -0
  80. sage/manifolds/differentiable/examples/symplectic_space_test.py +40 -0
  81. sage/manifolds/differentiable/integrated_curve.py +4035 -0
  82. sage/manifolds/differentiable/levi_civita_connection.py +841 -0
  83. sage/manifolds/differentiable/manifold.py +4254 -0
  84. sage/manifolds/differentiable/manifold_homset.py +1826 -0
  85. sage/manifolds/differentiable/metric.py +3032 -0
  86. sage/manifolds/differentiable/mixed_form.py +1507 -0
  87. sage/manifolds/differentiable/mixed_form_algebra.py +559 -0
  88. sage/manifolds/differentiable/multivector_module.py +800 -0
  89. sage/manifolds/differentiable/multivectorfield.py +1520 -0
  90. sage/manifolds/differentiable/poisson_tensor.py +268 -0
  91. sage/manifolds/differentiable/pseudo_riemannian.py +755 -0
  92. sage/manifolds/differentiable/pseudo_riemannian_submanifold.py +1839 -0
  93. sage/manifolds/differentiable/scalarfield.py +1343 -0
  94. sage/manifolds/differentiable/scalarfield_algebra.py +472 -0
  95. sage/manifolds/differentiable/symplectic_form.py +910 -0
  96. sage/manifolds/differentiable/symplectic_form_test.py +220 -0
  97. sage/manifolds/differentiable/tangent_space.py +412 -0
  98. sage/manifolds/differentiable/tangent_vector.py +616 -0
  99. sage/manifolds/differentiable/tensorfield.py +4665 -0
  100. sage/manifolds/differentiable/tensorfield_module.py +963 -0
  101. sage/manifolds/differentiable/tensorfield_paral.py +2450 -0
  102. sage/manifolds/differentiable/tensorfield_paral_test.py +16 -0
  103. sage/manifolds/differentiable/vector_bundle.py +1728 -0
  104. sage/manifolds/differentiable/vectorfield.py +1717 -0
  105. sage/manifolds/differentiable/vectorfield_module.py +2445 -0
  106. sage/manifolds/differentiable/vectorframe.py +1832 -0
  107. sage/manifolds/family.py +270 -0
  108. sage/manifolds/local_frame.py +1490 -0
  109. sage/manifolds/manifold.py +3090 -0
  110. sage/manifolds/manifold_homset.py +452 -0
  111. sage/manifolds/operators.py +359 -0
  112. sage/manifolds/point.py +994 -0
  113. sage/manifolds/scalarfield.py +3718 -0
  114. sage/manifolds/scalarfield_algebra.py +629 -0
  115. sage/manifolds/section.py +3111 -0
  116. sage/manifolds/section_module.py +831 -0
  117. sage/manifolds/structure.py +229 -0
  118. sage/manifolds/subset.py +2764 -0
  119. sage/manifolds/subsets/all.py +1 -0
  120. sage/manifolds/subsets/closure.py +131 -0
  121. sage/manifolds/subsets/pullback.py +885 -0
  122. sage/manifolds/topological_submanifold.py +891 -0
  123. sage/manifolds/trivialization.py +733 -0
  124. sage/manifolds/utilities.py +1348 -0
  125. sage/manifolds/vector_bundle.py +1342 -0
  126. sage/manifolds/vector_bundle_fiber.py +332 -0
  127. sage/manifolds/vector_bundle_fiber_element.py +111 -0
  128. sage/matrix/all__sagemath_symbolics.py +1 -0
  129. sage/matrix/matrix_symbolic_dense.cpython-314t-darwin.so +0 -0
  130. sage/matrix/matrix_symbolic_dense.pxd +6 -0
  131. sage/matrix/matrix_symbolic_dense.pyx +1022 -0
  132. sage/matrix/matrix_symbolic_sparse.cpython-314t-darwin.so +0 -0
  133. sage/matrix/matrix_symbolic_sparse.pxd +6 -0
  134. sage/matrix/matrix_symbolic_sparse.pyx +1029 -0
  135. sage/modules/all__sagemath_symbolics.py +1 -0
  136. sage/modules/vector_callable_symbolic_dense.py +105 -0
  137. sage/modules/vector_symbolic_dense.py +116 -0
  138. sage/modules/vector_symbolic_sparse.py +118 -0
  139. sage/rings/all__sagemath_symbolics.py +4 -0
  140. sage/rings/asymptotic/all.py +6 -0
  141. sage/rings/asymptotic/asymptotic_expansion_generators.py +1485 -0
  142. sage/rings/asymptotic/asymptotic_ring.py +4858 -0
  143. sage/rings/asymptotic/asymptotics_multivariate_generating_functions.py +4153 -0
  144. sage/rings/asymptotic/growth_group.py +5373 -0
  145. sage/rings/asymptotic/growth_group_cartesian.py +1400 -0
  146. sage/rings/asymptotic/term_monoid.py +5237 -0
  147. sage/rings/function_field/all__sagemath_symbolics.py +2 -0
  148. sage/rings/polynomial/all__sagemath_symbolics.py +1 -0
  149. sage/symbolic/all.py +15 -0
  150. sage/symbolic/assumptions.py +985 -0
  151. sage/symbolic/benchmark.py +93 -0
  152. sage/symbolic/callable.py +459 -0
  153. sage/symbolic/complexity_measures.py +35 -0
  154. sage/symbolic/constants.py +1287 -0
  155. sage/symbolic/expression_conversion_algebraic.py +310 -0
  156. sage/symbolic/expression_conversion_sympy.py +317 -0
  157. sage/symbolic/expression_conversions.py +1713 -0
  158. sage/symbolic/function_factory.py +355 -0
  159. sage/symbolic/integration/all.py +1 -0
  160. sage/symbolic/integration/external.py +270 -0
  161. sage/symbolic/integration/integral.py +1115 -0
  162. sage/symbolic/maxima_wrapper.py +162 -0
  163. sage/symbolic/operators.py +267 -0
  164. sage/symbolic/random_tests.py +462 -0
  165. sage/symbolic/relation.py +1907 -0
  166. sage/symbolic/ring.cpython-314t-darwin.so +0 -0
  167. sage/symbolic/ring.pxd +5 -0
  168. sage/symbolic/ring.pyx +1396 -0
  169. sage/symbolic/subring.py +1025 -0
  170. sage/symbolic/symengine.py +19 -0
  171. sage/symbolic/tests.py +40 -0
  172. sage/symbolic/units.py +1470 -0
@@ -0,0 +1,743 @@
1
+ # sage_setup: distribution = sagemath-symbolics
2
+ """
3
+ Coercion Maps Between Hyperbolic Plane Models
4
+
5
+ This module implements the coercion maps between different hyperbolic
6
+ plane models.
7
+
8
+ AUTHORS:
9
+
10
+ - Travis Scrimshaw (2014): initial version
11
+ """
12
+
13
+ #***********************************************************************
14
+ # Copyright (C) 2014 Travis Scrimshaw <tscrim at ucdavis.edu>
15
+ #
16
+ # Distributed under the terms of the GNU General Public License (GPL)
17
+ # as published by the Free Software Foundation; either version 2 of
18
+ # the License, or (at your option) any later version.
19
+ # http://www.gnu.org/licenses/
20
+ #***********************************************************************
21
+
22
+ from sage.categories.morphism import Morphism
23
+ from sage.symbolic.constants import I
24
+ from sage.matrix.constructor import matrix
25
+ from sage.modules.free_module_element import vector
26
+ from sage.rings.integer import Integer
27
+ from sage.rings.infinity import infinity
28
+ from sage.functions.other import real, imag
29
+ from sage.misc.functional import sqrt
30
+ from sage.misc.lazy_import import lazy_import
31
+ lazy_import('sage.misc.call', 'attrcall')
32
+
33
+
34
+ class HyperbolicModelCoercion(Morphism):
35
+ """
36
+ Abstract base class for morphisms between the hyperbolic models.
37
+ """
38
+ def _repr_type(self):
39
+ """
40
+ Return the type of morphism.
41
+
42
+ EXAMPLES::
43
+
44
+ sage: UHP = HyperbolicPlane().UHP()
45
+ sage: PD = HyperbolicPlane().PD()
46
+ sage: phi = UHP.coerce_map_from(PD)
47
+ sage: phi._repr_type()
48
+ 'Coercion Isometry'
49
+ """
50
+ return "Coercion Isometry"
51
+
52
+ def _call_(self, x):
53
+ """
54
+ Return the image of ``x`` under ``self``.
55
+
56
+ EXAMPLES::
57
+
58
+ sage: UHP = HyperbolicPlane().UHP()
59
+ sage: PD = HyperbolicPlane().PD()
60
+ sage: HM = HyperbolicPlane().HM()
61
+ sage: phi = UHP.coerce_map_from(PD)
62
+ sage: phi(PD.get_point(0.5+0.5*I))
63
+ Point in UHP 2.00000000000000 + 1.00000000000000*I
64
+ sage: psi = HM.coerce_map_from(UHP)
65
+ sage: psi(UHP.get_point(I))
66
+ Point in HM (0, 0, 1)
67
+
68
+ It is an error to try to convert a boundary point to a model
69
+ that doesn't support boundary points::
70
+
71
+ sage: psi(UHP.get_point(infinity))
72
+ Traceback (most recent call last):
73
+ ...
74
+ NotImplementedError: boundary points are not implemented for the Hyperboloid Model
75
+
76
+ It is an error to try to convert a boundary point to a model
77
+ that doesn't support boundary points::
78
+
79
+ sage: psi(UHP(infinity))
80
+ Traceback (most recent call last):
81
+ ...
82
+ NotImplementedError: boundary points are not implemented for the Hyperboloid Model
83
+ """
84
+ C = self.codomain()
85
+ if not C.is_bounded() and self.domain().is_bounded() and x.is_boundary():
86
+ msg = "boundary points are not implemented for the {}"
87
+ raise NotImplementedError(msg.format(C.name()))
88
+
89
+ y = self.image_coordinates(x.coordinates())
90
+ if self.domain().is_bounded():
91
+ bdry = x.is_boundary()
92
+ else:
93
+ bdry = C.boundary_point_in_model(y)
94
+
95
+ return C.element_class(C, y, bdry, check=False, **x.graphics_options())
96
+
97
+ def convert_geodesic(self, x):
98
+ """
99
+ Convert the geodesic ``x`` of the domain into a geodesic of
100
+ the codomain.
101
+
102
+ EXAMPLES::
103
+
104
+ sage: UHP = HyperbolicPlane().UHP()
105
+ sage: PD = HyperbolicPlane().PD()
106
+ sage: phi = UHP.coerce_map_from(PD)
107
+ sage: phi.convert_geodesic(PD.get_geodesic(0.5+0.5*I, -I))
108
+ Geodesic in UHP from 2.00000000000000 + 1.00000000000000*I to 0
109
+ """
110
+ return self.codomain().get_geodesic(self(x.start()), self(x.end()),
111
+ **x.graphics_options())
112
+
113
+ def convert_isometry(self, x):
114
+ """
115
+ Convert the hyperbolic isometry ``x`` of the domain into an
116
+ isometry of the codomain.
117
+
118
+ EXAMPLES::
119
+
120
+ sage: UHP = HyperbolicPlane().UHP()
121
+ sage: HM = HyperbolicPlane().HM()
122
+ sage: phi = HM.coerce_map_from(UHP)
123
+ sage: I2 = UHP.get_isometry(identity_matrix(2))
124
+ sage: phi.convert_isometry(I2)
125
+ Isometry in HM
126
+ [1 0 0]
127
+ [0 1 0]
128
+ [0 0 1]
129
+ """
130
+ C = self.codomain()
131
+ return C._Isometry(C, self.image_isometry_matrix(x._matrix), check=False)
132
+
133
+ def __invert__(self):
134
+ """
135
+ Return the inverse coercion of ``self``.
136
+
137
+ EXAMPLES::
138
+
139
+ sage: UHP = HyperbolicPlane().UHP()
140
+ sage: PD = HyperbolicPlane().PD()
141
+ sage: phi = UHP.coerce_map_from(PD)
142
+ sage: ~phi
143
+ Coercion Isometry morphism:
144
+ From: Hyperbolic plane in the Upper Half Plane Model
145
+ To: Hyperbolic plane in the Poincare Disk Model
146
+ """
147
+ return self.domain().coerce_map_from(self.codomain())
148
+
149
+ ############
150
+ # From UHP #
151
+ ############
152
+
153
+
154
+ class CoercionUHPtoPD(HyperbolicModelCoercion):
155
+ """
156
+ Coercion from the UHP to PD model.
157
+ """
158
+ def image_coordinates(self, x):
159
+ """
160
+ Return the image of the coordinates of the hyperbolic point ``x``
161
+ under ``self``.
162
+
163
+ EXAMPLES::
164
+
165
+ sage: UHP = HyperbolicPlane().UHP()
166
+ sage: PD = HyperbolicPlane().PD()
167
+ sage: phi = PD.coerce_map_from(UHP)
168
+ sage: phi.image_coordinates(I)
169
+ 0
170
+ """
171
+ if x == infinity:
172
+ return I
173
+ return (x - I) / (Integer(1) - I*x)
174
+
175
+ def image_isometry_matrix(self, x):
176
+ """
177
+ Return the image of the matrix of the hyperbolic isometry ``x``
178
+ under ``self``.
179
+
180
+ EXAMPLES::
181
+
182
+ sage: UHP = HyperbolicPlane().UHP()
183
+ sage: PD = HyperbolicPlane().PD()
184
+ sage: phi = PD.coerce_map_from(UHP)
185
+ sage: phi.image_isometry_matrix(identity_matrix(2))
186
+ [1 0]
187
+ [0 1]
188
+ """
189
+ if x.det() < 0:
190
+ # x = I * x
191
+ return matrix([[1,-I],[-I,1]]) * x * matrix([[1,I],[I,1]]).conjugate()/Integer(2)
192
+ return matrix([[1,-I],[-I,1]]) * x * matrix([[1,I],[I,1]])/Integer(2)
193
+
194
+
195
+ class CoercionUHPtoKM(HyperbolicModelCoercion):
196
+ """
197
+ Coercion from the UHP to KM model.
198
+ """
199
+ def image_coordinates(self, x):
200
+ """
201
+ Return the image of the coordinates of the hyperbolic point ``x``
202
+ under ``self``.
203
+
204
+ EXAMPLES::
205
+
206
+ sage: UHP = HyperbolicPlane().UHP()
207
+ sage: KM = HyperbolicPlane().KM()
208
+ sage: phi = KM.coerce_map_from(UHP)
209
+ sage: phi.image_coordinates(3 + I)
210
+ (6/11, 9/11)
211
+ """
212
+ if x == infinity:
213
+ return (0, 1)
214
+ return ((2*real(x))/(real(x)**2 + imag(x)**2 + 1),
215
+ (real(x)**2 + imag(x)**2 - 1)/(real(x)**2 + imag(x)**2 + 1))
216
+
217
+ def image_isometry_matrix(self, x):
218
+ """
219
+ Return the image of the matrix of the hyperbolic isometry ``x``
220
+ under ``self``.
221
+
222
+ EXAMPLES::
223
+
224
+ sage: UHP = HyperbolicPlane().UHP()
225
+ sage: KM = HyperbolicPlane().KM()
226
+ sage: phi = KM.coerce_map_from(UHP)
227
+ sage: phi.image_isometry_matrix(identity_matrix(2))
228
+ [1 0 0]
229
+ [0 1 0]
230
+ [0 0 1]
231
+ """
232
+ return SL2R_to_SO21(x)
233
+
234
+
235
+ class CoercionUHPtoHM(HyperbolicModelCoercion):
236
+ """
237
+ Coercion from the UHP to HM model.
238
+ """
239
+ def image_coordinates(self, x):
240
+ """
241
+ Return the image of the coordinates of the hyperbolic point ``x``
242
+ under ``self``.
243
+
244
+ EXAMPLES::
245
+
246
+ sage: UHP = HyperbolicPlane().UHP()
247
+ sage: HM = HyperbolicPlane().HM()
248
+ sage: phi = HM.coerce_map_from(UHP)
249
+ sage: phi.image_coordinates(3 + I)
250
+ (3, 9/2, 11/2)
251
+ """
252
+ return vector((real(x)/imag(x),
253
+ (real(x)**2 + imag(x)**2 - 1)/(2*imag(x)),
254
+ (real(x)**2 + imag(x)**2 + 1)/(2*imag(x))))
255
+
256
+ def image_isometry_matrix(self, x):
257
+ """
258
+ Return the image of the matrix of the hyperbolic isometry ``x``
259
+ under ``self``.
260
+
261
+ EXAMPLES::
262
+
263
+ sage: UHP = HyperbolicPlane().UHP()
264
+ sage: HM = HyperbolicPlane().HM()
265
+ sage: phi = HM.coerce_map_from(UHP)
266
+ sage: phi.image_isometry_matrix(identity_matrix(2))
267
+ [1 0 0]
268
+ [0 1 0]
269
+ [0 0 1]
270
+ """
271
+ return SL2R_to_SO21(x)
272
+
273
+ ###########
274
+ # From PD #
275
+ ###########
276
+
277
+
278
+ class CoercionPDtoUHP(HyperbolicModelCoercion):
279
+ """
280
+ Coercion from the PD to UHP model.
281
+ """
282
+ def image_coordinates(self, x):
283
+ """
284
+ Return the image of the coordinates of the hyperbolic point ``x``
285
+ under ``self``.
286
+
287
+ EXAMPLES::
288
+
289
+ sage: PD = HyperbolicPlane().PD()
290
+ sage: UHP = HyperbolicPlane().UHP()
291
+ sage: phi = UHP.coerce_map_from(PD)
292
+ sage: phi.image_coordinates(0.5+0.5*I)
293
+ 2.00000000000000 + 1.00000000000000*I
294
+ sage: phi.image_coordinates(0)
295
+ I
296
+ sage: phi.image_coordinates(I)
297
+ +Infinity
298
+ sage: phi.image_coordinates(-I)
299
+ 0
300
+ """
301
+ if x == I:
302
+ return infinity
303
+ return (x + I)/(Integer(1) + I*x)
304
+
305
+ def image_isometry_matrix(self, x):
306
+ """
307
+ Return the image of the matrix of the hyperbolic isometry ``x``
308
+ under ``self``.
309
+
310
+ EXAMPLES:
311
+
312
+ We check that orientation-reversing isometries behave as they
313
+ should::
314
+
315
+ sage: PD = HyperbolicPlane().PD()
316
+ sage: UHP = HyperbolicPlane().UHP()
317
+ sage: phi = UHP.coerce_map_from(PD)
318
+ sage: phi.image_isometry_matrix(matrix([[0,I],[I,0]]))
319
+ [-1 0]
320
+ [ 0 -1]
321
+ """
322
+ from sage.geometry.hyperbolic_space.hyperbolic_isometry import HyperbolicIsometryPD
323
+ if not HyperbolicIsometryPD._orientation_preserving(x):
324
+ return matrix([[1,I],[I,1]]) * x * matrix([[1,-I],[-I,1]]).conjugate() / Integer(2)
325
+ return matrix([[1,I],[I,1]]) * x * matrix([[1,-I],[-I,1]]) / Integer(2)
326
+
327
+
328
+ class CoercionPDtoKM(HyperbolicModelCoercion):
329
+ """
330
+ Coercion from the PD to KM model.
331
+ """
332
+ def image_coordinates(self, x):
333
+ """
334
+ Return the image of the coordinates of the hyperbolic point ``x``
335
+ under ``self``.
336
+
337
+ EXAMPLES::
338
+
339
+ sage: PD = HyperbolicPlane().PD()
340
+ sage: KM = HyperbolicPlane().KM()
341
+ sage: phi = KM.coerce_map_from(PD)
342
+ sage: phi.image_coordinates(0.5+0.5*I)
343
+ (0.666666666666667, 0.666666666666667)
344
+ """
345
+ return (2*real(x)/(Integer(1) + real(x)**2 + imag(x)**2),
346
+ 2*imag(x)/(Integer(1) + real(x)**2 + imag(x)**2))
347
+
348
+ def image_isometry_matrix(self, x):
349
+ """
350
+ Return the image of the matrix of the hyperbolic isometry ``x``
351
+ under ``self``.
352
+
353
+ EXAMPLES::
354
+
355
+ sage: PD = HyperbolicPlane().PD()
356
+ sage: KM = HyperbolicPlane().KM()
357
+ sage: phi = KM.coerce_map_from(PD)
358
+ sage: phi.image_isometry_matrix(matrix([[0,I],[I,0]]))
359
+ [-1 0 0]
360
+ [ 0 1 0]
361
+ [ 0 0 -1]
362
+ """
363
+ return SL2R_to_SO21(matrix(2, [1, I, I, 1]) * x *
364
+ matrix(2, [1, -I, -I, 1]) / Integer(2))
365
+
366
+
367
+ class CoercionPDtoHM(HyperbolicModelCoercion):
368
+ """
369
+ Coercion from the PD to HM model.
370
+ """
371
+ def image_coordinates(self, x):
372
+ """
373
+ Return the image of the coordinates of the hyperbolic point ``x``
374
+ under ``self``.
375
+
376
+ EXAMPLES::
377
+
378
+ sage: PD = HyperbolicPlane().PD()
379
+ sage: HM = HyperbolicPlane().HM()
380
+ sage: phi = HM.coerce_map_from(PD)
381
+ sage: phi.image_coordinates(0.5+0.5*I)
382
+ (2.00000000000000, 2.00000000000000, 3.00000000000000)
383
+ """
384
+ return vector((2*real(x)/(1 - real(x)**2 - imag(x)**2),
385
+ 2*imag(x)/(1 - real(x)**2 - imag(x)**2),
386
+ (real(x)**2 + imag(x)**2 + 1) /
387
+ (1 - real(x)**2 - imag(x)**2)))
388
+
389
+ def image_isometry_matrix(self, x):
390
+ """
391
+ Return the image of the matrix of the hyperbolic isometry ``x``
392
+ under ``self``.
393
+
394
+ EXAMPLES::
395
+
396
+ sage: PD = HyperbolicPlane().PD()
397
+ sage: HM = HyperbolicPlane().HM()
398
+ sage: phi = HM.coerce_map_from(PD)
399
+ sage: phi.image_isometry_matrix(matrix([[0,I],[I,0]]))
400
+ [-1 0 0]
401
+ [ 0 1 0]
402
+ [ 0 0 -1]
403
+ """
404
+ return SL2R_to_SO21(matrix(2, [1, I, I, 1]) * x *
405
+ matrix(2, [1, -I, -I, 1]) / Integer(2))
406
+
407
+ ###########
408
+ # From KM #
409
+ ###########
410
+
411
+
412
+ class CoercionKMtoUHP(HyperbolicModelCoercion):
413
+ """
414
+ Coercion from the KM to UHP model.
415
+ """
416
+ def image_coordinates(self, x):
417
+ """
418
+ Return the image of the coordinates of the hyperbolic point ``x``
419
+ under ``self``.
420
+
421
+ EXAMPLES::
422
+
423
+ sage: KM = HyperbolicPlane().KM()
424
+ sage: UHP = HyperbolicPlane().UHP()
425
+ sage: phi = UHP.coerce_map_from(KM)
426
+ sage: phi.image_coordinates((0, 0))
427
+ I
428
+ sage: phi.image_coordinates((0, 1))
429
+ +Infinity
430
+ """
431
+ if tuple(x) == (0, 1):
432
+ return infinity
433
+ return (-x[0]/(x[1] - 1)
434
+ + I*(-(sqrt(-x[0]**2 - x[1]**2 + 1) - x[0]**2 - x[1]**2 + 1)
435
+ / ((x[1] - 1)*sqrt(-x[0]**2 - x[1]**2 + 1) + x[1] - 1)))
436
+
437
+ def image_isometry_matrix(self, x):
438
+ """
439
+ Return the image of the matrix of the hyperbolic isometry ``x``
440
+ under ``self``.
441
+
442
+ EXAMPLES::
443
+
444
+ sage: KM = HyperbolicPlane().KM()
445
+ sage: UHP = HyperbolicPlane().UHP()
446
+ sage: phi = UHP.coerce_map_from(KM)
447
+ sage: m = matrix([[5/3,0,4/3], [0,1,0], [4/3,0,5/3]])
448
+ sage: phi.image_isometry_matrix(m)
449
+ [2*sqrt(1/3) sqrt(1/3)]
450
+ [ sqrt(1/3) 2*sqrt(1/3)]
451
+ """
452
+ return SO21_to_SL2R(x)
453
+
454
+
455
+ class CoercionKMtoPD(HyperbolicModelCoercion):
456
+ """
457
+ Coercion from the KM to PD model.
458
+ """
459
+ def image_coordinates(self, x):
460
+ """
461
+ Return the image of the coordinates of the hyperbolic point ``x``
462
+ under ``self``.
463
+
464
+ EXAMPLES::
465
+
466
+ sage: KM = HyperbolicPlane().KM()
467
+ sage: PD = HyperbolicPlane().PD()
468
+ sage: phi = PD.coerce_map_from(KM)
469
+ sage: phi.image_coordinates((0, 0))
470
+ 0
471
+ """
472
+ return (x[0]/(1 + (1 - x[0]**2 - x[1]**2).sqrt())
473
+ + I*x[1]/(1 + (1 - x[0]**2 - x[1]**2).sqrt()))
474
+
475
+ def image_isometry_matrix(self, x):
476
+ """
477
+ Return the image of the matrix of the hyperbolic isometry ``x``
478
+ under ``self``.
479
+
480
+ EXAMPLES::
481
+
482
+ sage: KM = HyperbolicPlane().KM()
483
+ sage: PD = HyperbolicPlane().PD()
484
+ sage: phi = PD.coerce_map_from(KM)
485
+ sage: m = matrix([[5/3,0,4/3], [0,1,0], [4/3,0,5/3]])
486
+ sage: phi.image_isometry_matrix(m)
487
+ [2*sqrt(1/3) sqrt(1/3)]
488
+ [ sqrt(1/3) 2*sqrt(1/3)]
489
+ """
490
+ return (matrix(2,[1,-I,-I,1]) * SO21_to_SL2R(x) *
491
+ matrix(2,[1,I,I,1])/Integer(2))
492
+
493
+
494
+ class CoercionKMtoHM(HyperbolicModelCoercion):
495
+ """
496
+ Coercion from the KM to HM model.
497
+ """
498
+ def image_coordinates(self, x):
499
+ """
500
+ Return the image of the coordinates of the hyperbolic point ``x``
501
+ under ``self``.
502
+
503
+ EXAMPLES::
504
+
505
+ sage: KM = HyperbolicPlane().KM()
506
+ sage: HM = HyperbolicPlane().HM()
507
+ sage: phi = HM.coerce_map_from(KM)
508
+ sage: phi.image_coordinates((0, 0))
509
+ (0, 0, 1)
510
+ """
511
+ return (vector((2*x[0], 2*x[1], 1 + x[0]**2 + x[1]**2))
512
+ / (1 - x[0]**2 - x[1]**2))
513
+
514
+ def image_isometry_matrix(self, x):
515
+ """
516
+ Return the image of the matrix of the hyperbolic isometry ``x``
517
+ under ``self``.
518
+
519
+ EXAMPLES::
520
+
521
+ sage: KM = HyperbolicPlane().KM()
522
+ sage: HM = HyperbolicPlane().HM()
523
+ sage: phi = HM.coerce_map_from(KM)
524
+ sage: m = matrix([[5/3,0,4/3], [0,1,0], [4/3,0,5/3]])
525
+ sage: phi.image_isometry_matrix(m)
526
+ [5/3 0 4/3]
527
+ [ 0 1 0]
528
+ [4/3 0 5/3]
529
+ """
530
+ return x
531
+
532
+ ###########
533
+ # From HM #
534
+ ###########
535
+
536
+
537
+ class CoercionHMtoUHP(HyperbolicModelCoercion):
538
+ """
539
+ Coercion from the HM to UHP model.
540
+ """
541
+ def image_coordinates(self, x):
542
+ """
543
+ Return the image of the coordinates of the hyperbolic point ``x``
544
+ under ``self``.
545
+
546
+ EXAMPLES::
547
+
548
+ sage: HM = HyperbolicPlane().HM()
549
+ sage: UHP = HyperbolicPlane().UHP()
550
+ sage: phi = UHP.coerce_map_from(HM)
551
+ sage: phi.image_coordinates( vector((0,0,1)) )
552
+ I
553
+ """
554
+ return -((x[0]*x[2] + x[0]) + I*(x[2] + 1)) / ((x[1] - 1)*x[2]
555
+ - x[0]**2 - x[1]**2 + x[1] - 1)
556
+
557
+ def image_isometry_matrix(self, x):
558
+ """
559
+ Return the image of the matrix of the hyperbolic isometry ``x``
560
+ under ``self``.
561
+
562
+ EXAMPLES::
563
+
564
+ sage: HM = HyperbolicPlane().HM()
565
+ sage: UHP = HyperbolicPlane().UHP()
566
+ sage: phi = UHP.coerce_map_from(HM)
567
+ sage: phi.image_isometry_matrix(identity_matrix(3))
568
+ [1 0]
569
+ [0 1]
570
+ """
571
+ return SO21_to_SL2R(x)
572
+
573
+
574
+ class CoercionHMtoPD(HyperbolicModelCoercion):
575
+ """
576
+ Coercion from the HM to PD model.
577
+ """
578
+ def image_coordinates(self, x):
579
+ """
580
+ Return the image of the coordinates of the hyperbolic point ``x``
581
+ under ``self``.
582
+
583
+ EXAMPLES::
584
+
585
+ sage: HM = HyperbolicPlane().HM()
586
+ sage: PD = HyperbolicPlane().PD()
587
+ sage: phi = PD.coerce_map_from(HM)
588
+ sage: phi.image_coordinates( vector((0,0,1)) )
589
+ 0
590
+ """
591
+ return x[0]/(1 + x[2]) + I*(x[1]/(1 + x[2]))
592
+
593
+ def image_isometry_matrix(self, x):
594
+ """
595
+ Return the image of the matrix of the hyperbolic isometry ``x``
596
+ under ``self``.
597
+
598
+ EXAMPLES::
599
+
600
+ sage: HM = HyperbolicPlane().HM()
601
+ sage: PD = HyperbolicPlane().PD()
602
+ sage: phi = PD.coerce_map_from(HM)
603
+ sage: phi.image_isometry_matrix(identity_matrix(3))
604
+ [1 0]
605
+ [0 1]
606
+ """
607
+ return (matrix(2,[1,-I,-I,1]) * SO21_to_SL2R(x) *
608
+ matrix(2,[1,I,I,1])/Integer(2))
609
+
610
+
611
+ class CoercionHMtoKM(HyperbolicModelCoercion):
612
+ """
613
+ Coercion from the HM to KM model.
614
+ """
615
+ def image_coordinates(self, x):
616
+ """
617
+ Return the image of the coordinates of the hyperbolic point ``x``
618
+ under ``self``.
619
+
620
+ EXAMPLES::
621
+
622
+ sage: HM = HyperbolicPlane().HM()
623
+ sage: KM = HyperbolicPlane().KM()
624
+ sage: phi = KM.coerce_map_from(HM)
625
+ sage: phi.image_coordinates( vector((0,0,1)) )
626
+ (0, 0)
627
+ """
628
+ return (x[0]/(1 + x[2]), x[1]/(1 + x[2]))
629
+
630
+ def image_isometry_matrix(self, x):
631
+ """
632
+ Return the image of the matrix of the hyperbolic isometry ``x``
633
+ under ``self``.
634
+
635
+ EXAMPLES::
636
+
637
+ sage: HM = HyperbolicPlane().HM()
638
+ sage: KM = HyperbolicPlane().KM()
639
+ sage: phi = KM.coerce_map_from(HM)
640
+ sage: phi.image_isometry_matrix(identity_matrix(3))
641
+ [1 0 0]
642
+ [0 1 0]
643
+ [0 0 1]
644
+ """
645
+ return x
646
+
647
+ #####################################################################
648
+ ## Helper functions
649
+
650
+
651
+ def SL2R_to_SO21(A):
652
+ r"""
653
+ Given a matrix in `SL(2, \RR)` return its irreducible representation in
654
+ `O(2,1)`.
655
+
656
+ Note that this is not the only homomorphism, but it is the only one
657
+ that works in the context of the implemented 2D hyperbolic geometry
658
+ models.
659
+
660
+ EXAMPLES::
661
+
662
+ sage: from sage.geometry.hyperbolic_space.hyperbolic_coercion import SL2R_to_SO21
663
+ sage: A = SL2R_to_SO21(identity_matrix(2))
664
+ sage: J = matrix([[1,0,0],[0,1,0],[0,0,-1]]) #Lorentzian Gram matrix
665
+ sage: norm(A.transpose()*J*A - J) < 10**-4 # needs scipy
666
+ True
667
+ """
668
+ a, b, c, d = (A/A.det().sqrt()).list()
669
+
670
+ # Kill ~0 imaginary parts
671
+ components = [
672
+ a*d + b*c, a*c - b*d, a*c + b*d, a*b - c*d,
673
+ Integer(1)/Integer(2)*a**2 - Integer(1)/Integer(2)*b**2 -
674
+ Integer(1)/Integer(2)*c**2 + Integer(1)/Integer(2)*d**2,
675
+ Integer(1)/Integer(2)*a**2 + Integer(1)/Integer(2)*b**2 -
676
+ Integer(1)/Integer(2)*c**2 - Integer(1)/Integer(2)*d**2,
677
+ a*b + c*d, Integer(1)/Integer(2)*a**2 -
678
+ Integer(1)/Integer(2)*b**2 + Integer(1)/Integer(2)*c**2 -
679
+ Integer(1)/Integer(2)*d**2, Integer(1)/Integer(2)*a**2 +
680
+ Integer(1)/Integer(2)*b**2 + Integer(1)/Integer(2)*c**2 +
681
+ Integer(1)/Integer(2)*d**2
682
+ ]
683
+ B = matrix(3, [real(comp) for comp in components])
684
+
685
+ #B = B.apply_map(attrcall('real'))
686
+ if A.det() > 0:
687
+ return B
688
+ else:
689
+ # Orientation-reversing isometries swap the nappes of
690
+ # the lightcone. This fixes that issue.
691
+ return -B
692
+
693
+
694
+ def SO21_to_SL2R(M):
695
+ r"""
696
+ A homomorphism from `SO(2, 1)` to `SL(2, \RR)`.
697
+
698
+ Note that this is not the only homomorphism, but it is the only one
699
+ that works in the context of the implemented 2D hyperbolic geometry
700
+ models.
701
+
702
+ EXAMPLES::
703
+
704
+ sage: from sage.geometry.hyperbolic_space.hyperbolic_coercion import SO21_to_SL2R
705
+ sage: (SO21_to_SL2R(identity_matrix(3)) - identity_matrix(2)).norm() < 10**-4 # needs scipy
706
+ True
707
+ """
708
+ ####################################################################
709
+ # SL(2,R) is the double cover of SO (2,1)^+, so we need to choose #
710
+ # a lift. I have formulas for the absolute values of each entry #
711
+ # a,b ,c,d of the lift matrix(2,[a,b,c,d]), but we need to choose #
712
+ # one entry to be positive. I choose d for no particular reason, #
713
+ # unless d = 0, then we choose c > 0. The basic strategy for this #
714
+ # function is to find the linear map induced by the SO(2,1) #
715
+ # element on the Lie algebra sl(2, R). This corresponds to the #
716
+ # Adjoint action by a matrix A or -A in SL(2,R). To find which #
717
+ # matrix let X,Y,Z be a basis for sl(2,R) and look at the images #
718
+ # of X,Y,Z as well as the second and third standard basis vectors #
719
+ # for 2x2 matrices (these are traceless, so are in the Lie #
720
+ # algebra). These corresponds to AXA^-1 etc and give formulas #
721
+ # for the entries of A. #
722
+ ####################################################################
723
+ (m_1,m_2,m_3,m_4,m_5,m_6,m_7,m_8,m_9) = M.list()
724
+ d = sqrt(Integer(1)/Integer(2)*m_5 - Integer(1)/Integer(2)*m_6 -
725
+ Integer(1)/Integer(2)*m_8 + Integer(1)/Integer(2)*m_9)
726
+ if M.det() > 0: # EPSILON?
727
+ det_sign = 1
728
+ elif M.det() < 0: # EPSILON?
729
+ det_sign = -1
730
+ if d > 0: # EPSILON?
731
+ c = (-Integer(1)/Integer(2)*m_4 + Integer(1)/Integer(2)*m_7)/d
732
+ b = (-Integer(1)/Integer(2)*m_2 + Integer(1)/Integer(2)*m_3)/d
733
+ ad = det_sign*1 + b*c # ad - bc = pm 1
734
+ a = ad/d
735
+ else: # d is 0, so we make c > 0
736
+ c = sqrt(-Integer(1)/Integer(2)*m_5 - Integer(1)/Integer(2)*m_6 +
737
+ Integer(1)/Integer(2)*m_8 + Integer(1)/Integer(2)*m_9)
738
+ d = (-Integer(1)/Integer(2)*m_4 + Integer(1)/Integer(2)*m_7)/c
739
+ # d = 0, so ad - bc = -bc = pm 1.
740
+ b = - (det_sign*1)/c
741
+ a = (Integer(1)/Integer(2)*m_4 + Integer(1)/Integer(2)*m_7)/b
742
+ A = matrix(2, [a, b, c, d])
743
+ return A