passagemath-symbolics 10.8.1a1__cp311-cp311-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.
- passagemath_symbolics/.dylibs/libgmp.10.dylib +0 -0
- passagemath_symbolics/__init__.py +3 -0
- passagemath_symbolics-10.8.1a1.dist-info/METADATA +186 -0
- passagemath_symbolics-10.8.1a1.dist-info/RECORD +182 -0
- passagemath_symbolics-10.8.1a1.dist-info/WHEEL +6 -0
- passagemath_symbolics-10.8.1a1.dist-info/top_level.txt +3 -0
- sage/all__sagemath_symbolics.py +17 -0
- sage/calculus/all.py +14 -0
- sage/calculus/calculus.py +2838 -0
- sage/calculus/desolvers.py +1864 -0
- sage/calculus/predefined.py +51 -0
- sage/calculus/tests.py +225 -0
- sage/calculus/var.cpython-311-darwin.so +0 -0
- sage/calculus/var.pyx +401 -0
- sage/dynamics/all__sagemath_symbolics.py +6 -0
- sage/dynamics/complex_dynamics/all.py +5 -0
- sage/dynamics/complex_dynamics/mandel_julia.py +765 -0
- sage/dynamics/complex_dynamics/mandel_julia_helper.cpython-311-darwin.so +0 -0
- sage/dynamics/complex_dynamics/mandel_julia_helper.pyx +1034 -0
- sage/ext/all__sagemath_symbolics.py +1 -0
- sage/ext_data/kenzo/CP2.txt +45 -0
- sage/ext_data/kenzo/CP3.txt +349 -0
- sage/ext_data/kenzo/CP4.txt +4774 -0
- sage/ext_data/kenzo/README.txt +49 -0
- sage/ext_data/kenzo/S4.txt +20 -0
- sage/ext_data/magma/latex/latex.m +1021 -0
- sage/ext_data/magma/latex/latex.spec +1 -0
- sage/ext_data/magma/sage/basic.m +356 -0
- sage/ext_data/magma/sage/sage.spec +1 -0
- sage/ext_data/magma/spec +9 -0
- sage/geometry/all__sagemath_symbolics.py +8 -0
- sage/geometry/hyperbolic_space/all.py +5 -0
- sage/geometry/hyperbolic_space/hyperbolic_coercion.py +755 -0
- sage/geometry/hyperbolic_space/hyperbolic_constants.py +5 -0
- sage/geometry/hyperbolic_space/hyperbolic_geodesic.py +2419 -0
- sage/geometry/hyperbolic_space/hyperbolic_interface.py +206 -0
- sage/geometry/hyperbolic_space/hyperbolic_isometry.py +1083 -0
- sage/geometry/hyperbolic_space/hyperbolic_model.py +1502 -0
- sage/geometry/hyperbolic_space/hyperbolic_point.py +621 -0
- sage/geometry/riemannian_manifolds/all.py +7 -0
- sage/geometry/riemannian_manifolds/parametrized_surface3d.py +1632 -0
- sage/geometry/riemannian_manifolds/surface3d_generators.py +461 -0
- sage/interfaces/all__sagemath_symbolics.py +1 -0
- sage/interfaces/magma.py +2991 -0
- sage/interfaces/magma_free.py +90 -0
- sage/interfaces/maple.py +1402 -0
- sage/interfaces/mathematica.py +1345 -0
- sage/interfaces/mathics.py +1312 -0
- sage/interfaces/sympy.py +1398 -0
- sage/interfaces/sympy_wrapper.py +197 -0
- sage/interfaces/tides.py +938 -0
- sage/libs/all__sagemath_symbolics.py +6 -0
- sage/manifolds/all.py +7 -0
- sage/manifolds/calculus_method.py +553 -0
- sage/manifolds/catalog.py +437 -0
- sage/manifolds/chart.py +4010 -0
- sage/manifolds/chart_func.py +3416 -0
- sage/manifolds/continuous_map.py +2183 -0
- sage/manifolds/continuous_map_image.py +155 -0
- sage/manifolds/differentiable/affine_connection.py +2475 -0
- sage/manifolds/differentiable/all.py +1 -0
- sage/manifolds/differentiable/automorphismfield.py +1383 -0
- sage/manifolds/differentiable/automorphismfield_group.py +604 -0
- sage/manifolds/differentiable/bundle_connection.py +1445 -0
- sage/manifolds/differentiable/characteristic_cohomology_class.py +1840 -0
- sage/manifolds/differentiable/chart.py +1241 -0
- sage/manifolds/differentiable/curve.py +1028 -0
- sage/manifolds/differentiable/de_rham_cohomology.py +541 -0
- sage/manifolds/differentiable/degenerate.py +559 -0
- sage/manifolds/differentiable/degenerate_submanifold.py +1668 -0
- sage/manifolds/differentiable/diff_form.py +1660 -0
- sage/manifolds/differentiable/diff_form_module.py +1062 -0
- sage/manifolds/differentiable/diff_map.py +1315 -0
- sage/manifolds/differentiable/differentiable_submanifold.py +291 -0
- sage/manifolds/differentiable/examples/all.py +1 -0
- sage/manifolds/differentiable/examples/euclidean.py +2517 -0
- sage/manifolds/differentiable/examples/real_line.py +897 -0
- sage/manifolds/differentiable/examples/sphere.py +1186 -0
- sage/manifolds/differentiable/examples/symplectic_space.py +187 -0
- sage/manifolds/differentiable/examples/symplectic_space_test.py +40 -0
- sage/manifolds/differentiable/integrated_curve.py +4035 -0
- sage/manifolds/differentiable/levi_civita_connection.py +841 -0
- sage/manifolds/differentiable/manifold.py +4254 -0
- sage/manifolds/differentiable/manifold_homset.py +1826 -0
- sage/manifolds/differentiable/metric.py +3032 -0
- sage/manifolds/differentiable/mixed_form.py +1507 -0
- sage/manifolds/differentiable/mixed_form_algebra.py +559 -0
- sage/manifolds/differentiable/multivector_module.py +800 -0
- sage/manifolds/differentiable/multivectorfield.py +1522 -0
- sage/manifolds/differentiable/poisson_tensor.py +268 -0
- sage/manifolds/differentiable/pseudo_riemannian.py +755 -0
- sage/manifolds/differentiable/pseudo_riemannian_submanifold.py +1839 -0
- sage/manifolds/differentiable/scalarfield.py +1343 -0
- sage/manifolds/differentiable/scalarfield_algebra.py +472 -0
- sage/manifolds/differentiable/symplectic_form.py +912 -0
- sage/manifolds/differentiable/symplectic_form_test.py +220 -0
- sage/manifolds/differentiable/tangent_space.py +412 -0
- sage/manifolds/differentiable/tangent_vector.py +616 -0
- sage/manifolds/differentiable/tensorfield.py +4665 -0
- sage/manifolds/differentiable/tensorfield_module.py +963 -0
- sage/manifolds/differentiable/tensorfield_paral.py +2450 -0
- sage/manifolds/differentiable/tensorfield_paral_test.py +16 -0
- sage/manifolds/differentiable/vector_bundle.py +1725 -0
- sage/manifolds/differentiable/vectorfield.py +1717 -0
- sage/manifolds/differentiable/vectorfield_module.py +2445 -0
- sage/manifolds/differentiable/vectorframe.py +1832 -0
- sage/manifolds/family.py +270 -0
- sage/manifolds/local_frame.py +1490 -0
- sage/manifolds/manifold.py +3090 -0
- sage/manifolds/manifold_homset.py +452 -0
- sage/manifolds/operators.py +359 -0
- sage/manifolds/point.py +994 -0
- sage/manifolds/scalarfield.py +3718 -0
- sage/manifolds/scalarfield_algebra.py +629 -0
- sage/manifolds/section.py +3111 -0
- sage/manifolds/section_module.py +831 -0
- sage/manifolds/structure.py +229 -0
- sage/manifolds/subset.py +2721 -0
- sage/manifolds/subsets/all.py +1 -0
- sage/manifolds/subsets/closure.py +131 -0
- sage/manifolds/subsets/pullback.py +883 -0
- sage/manifolds/topological_submanifold.py +891 -0
- sage/manifolds/trivialization.py +733 -0
- sage/manifolds/utilities.py +1348 -0
- sage/manifolds/vector_bundle.py +1347 -0
- sage/manifolds/vector_bundle_fiber.py +332 -0
- sage/manifolds/vector_bundle_fiber_element.py +111 -0
- sage/matrix/all__sagemath_symbolics.py +1 -0
- sage/matrix/matrix_symbolic_dense.cpython-311-darwin.so +0 -0
- sage/matrix/matrix_symbolic_dense.pxd +6 -0
- sage/matrix/matrix_symbolic_dense.pyx +1030 -0
- sage/matrix/matrix_symbolic_sparse.cpython-311-darwin.so +0 -0
- sage/matrix/matrix_symbolic_sparse.pxd +6 -0
- sage/matrix/matrix_symbolic_sparse.pyx +1038 -0
- sage/modules/all__sagemath_symbolics.py +1 -0
- sage/modules/vector_callable_symbolic_dense.py +105 -0
- sage/modules/vector_symbolic_dense.py +116 -0
- sage/modules/vector_symbolic_sparse.py +118 -0
- sage/rings/all__sagemath_symbolics.py +4 -0
- sage/rings/asymptotic/all.py +6 -0
- sage/rings/asymptotic/asymptotic_expansion_generators.py +1485 -0
- sage/rings/asymptotic/asymptotic_ring.py +4858 -0
- sage/rings/asymptotic/asymptotics_multivariate_generating_functions.py +4106 -0
- sage/rings/asymptotic/growth_group.py +5373 -0
- sage/rings/asymptotic/growth_group_cartesian.py +1400 -0
- sage/rings/asymptotic/term_monoid.py +5205 -0
- sage/rings/function_field/all__sagemath_symbolics.py +2 -0
- sage/rings/polynomial/all__sagemath_symbolics.py +1 -0
- sage/symbolic/all.py +15 -0
- sage/symbolic/assumptions.py +987 -0
- sage/symbolic/benchmark.py +93 -0
- sage/symbolic/callable.py +456 -0
- sage/symbolic/callable.pyi +66 -0
- sage/symbolic/comparison_impl.pyi +38 -0
- sage/symbolic/complexity_measures.py +35 -0
- sage/symbolic/constants.py +1286 -0
- sage/symbolic/constants_c_impl.pyi +10 -0
- sage/symbolic/expression_conversion_algebraic.py +310 -0
- sage/symbolic/expression_conversion_sympy.py +317 -0
- sage/symbolic/expression_conversions.py +1727 -0
- sage/symbolic/function_factory.py +355 -0
- sage/symbolic/function_factory.pyi +41 -0
- sage/symbolic/getitem_impl.pyi +24 -0
- sage/symbolic/integration/all.py +1 -0
- sage/symbolic/integration/external.py +271 -0
- sage/symbolic/integration/integral.py +1075 -0
- sage/symbolic/maxima_wrapper.py +162 -0
- sage/symbolic/operators.py +267 -0
- sage/symbolic/operators.pyi +61 -0
- sage/symbolic/pynac_constant_impl.pyi +13 -0
- sage/symbolic/pynac_function_impl.pyi +8 -0
- sage/symbolic/random_tests.py +461 -0
- sage/symbolic/relation.py +2062 -0
- sage/symbolic/ring.cpython-311-darwin.so +0 -0
- sage/symbolic/ring.pxd +5 -0
- sage/symbolic/ring.pyi +110 -0
- sage/symbolic/ring.pyx +1393 -0
- sage/symbolic/series_impl.pyi +10 -0
- sage/symbolic/subring.py +1025 -0
- sage/symbolic/symengine.py +19 -0
- sage/symbolic/tests.py +40 -0
- sage/symbolic/units.py +1468 -0
|
@@ -0,0 +1,220 @@
|
|
|
1
|
+
# sage_setup: distribution = sagemath-symbolics
|
|
2
|
+
# pylint: disable=missing-function-docstring
|
|
3
|
+
import pytest
|
|
4
|
+
from _pytest.fixtures import FixtureRequest
|
|
5
|
+
|
|
6
|
+
from sage.manifolds.differentiable.examples.sphere import Sphere
|
|
7
|
+
from sage.manifolds.differentiable.examples.symplectic_space import (
|
|
8
|
+
StandardSymplecticSpace,
|
|
9
|
+
)
|
|
10
|
+
from sage.manifolds.differentiable.manifold import DifferentiableManifold
|
|
11
|
+
from sage.manifolds.differentiable.scalarfield import DiffScalarField
|
|
12
|
+
from sage.manifolds.differentiable.symplectic_form import SymplecticForm
|
|
13
|
+
from sage.manifolds.manifold import Manifold
|
|
14
|
+
from sage.symbolic.function_factory import function
|
|
15
|
+
|
|
16
|
+
|
|
17
|
+
class TestGenericSymplecticForm:
|
|
18
|
+
@pytest.fixture
|
|
19
|
+
def omega(self):
|
|
20
|
+
# Generic 6-dimensional manifold
|
|
21
|
+
M = Manifold(6, "M")
|
|
22
|
+
return SymplecticForm(M, "omega")
|
|
23
|
+
|
|
24
|
+
def test_repr(self, omega: SymplecticForm):
|
|
25
|
+
assert (
|
|
26
|
+
str(omega)
|
|
27
|
+
== "Symplectic form omega on the 6-dimensional differentiable manifold M"
|
|
28
|
+
)
|
|
29
|
+
|
|
30
|
+
def test_new_instance_repr(self, omega: SymplecticForm):
|
|
31
|
+
omega1 = omega._new_instance() # type: ignore reportPrivateUsage
|
|
32
|
+
assert (
|
|
33
|
+
str(omega1)
|
|
34
|
+
== "Symplectic form unnamed symplectic form on the 6-dimensional differentiable manifold M"
|
|
35
|
+
)
|
|
36
|
+
|
|
37
|
+
def test_new_instance_same_type(self, omega: SymplecticForm):
|
|
38
|
+
omega1 = omega._new_instance() # type: ignore reportPrivateUsage
|
|
39
|
+
assert type(omega1) is type(omega)
|
|
40
|
+
|
|
41
|
+
def test_new_instance_same_parent(self, omega: SymplecticForm):
|
|
42
|
+
omega1 = omega._new_instance() # type: ignore reportPrivateUsage
|
|
43
|
+
assert omega1.parent() == omega.parent()
|
|
44
|
+
|
|
45
|
+
def test_init_derived_sets_poisson_tensor(self, omega: SymplecticForm):
|
|
46
|
+
omega._init_derived() # type: ignore reportPrivateUsage
|
|
47
|
+
assert omega._poisson is None # type: ignore reportPrivateUsage
|
|
48
|
+
|
|
49
|
+
def test_del_derived_resets_poisson_tensor(self, omega: SymplecticForm):
|
|
50
|
+
omega._del_derived() # type: ignore reportPrivateUsage
|
|
51
|
+
assert omega._poisson is None # type: ignore reportPrivateUsage
|
|
52
|
+
|
|
53
|
+
|
|
54
|
+
class TestCoherenceOfFormulas:
|
|
55
|
+
r"""
|
|
56
|
+
Test correctness of the implementation, by checking that equivalent formulas give the correct result.
|
|
57
|
+
We check it for the examples of `\R^2` and `S^2`, which should be enough.
|
|
58
|
+
"""
|
|
59
|
+
|
|
60
|
+
@pytest.fixture(params=['R2', 'S2'])
|
|
61
|
+
def M(self, request: FixtureRequest):
|
|
62
|
+
if request.param == 'R2':
|
|
63
|
+
return StandardSymplecticSpace(2, 'R2', symplectic_name='omega')
|
|
64
|
+
elif request.param == 'S2':
|
|
65
|
+
# Init stereographic coordinates to get a complete atlas
|
|
66
|
+
return Sphere(2, coordinates='stereographic')
|
|
67
|
+
|
|
68
|
+
@pytest.fixture()
|
|
69
|
+
def omega(self, M):
|
|
70
|
+
if isinstance(M, StandardSymplecticSpace):
|
|
71
|
+
return M.symplectic_form()
|
|
72
|
+
else:
|
|
73
|
+
return SymplecticForm.wrap(M.metric().volume_form(), "omega")
|
|
74
|
+
|
|
75
|
+
def test_flat_of_hamiltonian_vector_field(
|
|
76
|
+
self, M: DifferentiableManifold, omega: SymplecticForm
|
|
77
|
+
):
|
|
78
|
+
H = generic_scalar_field(M, "H")
|
|
79
|
+
assert omega.flat(omega.hamiltonian_vector_field(H)) == -H.differential()
|
|
80
|
+
|
|
81
|
+
def test_hamiltonian_vector_field_contr_symplectic_form(
|
|
82
|
+
self, M: DifferentiableManifold, omega: SymplecticForm
|
|
83
|
+
):
|
|
84
|
+
H = generic_scalar_field(M, "H")
|
|
85
|
+
# X_H \lrcorner \omega + \dif H = 0
|
|
86
|
+
assert omega.contract(0, omega.hamiltonian_vector_field(H)) == -H.differential()
|
|
87
|
+
|
|
88
|
+
def test_poisson_bracket_as_contraction_symplectic_form(
|
|
89
|
+
self, M: DifferentiableManifold, omega: SymplecticForm
|
|
90
|
+
):
|
|
91
|
+
f = generic_scalar_field(M, "f")
|
|
92
|
+
g = generic_scalar_field(M, "g")
|
|
93
|
+
# {f, g} = \omega(X_f, X_g)
|
|
94
|
+
assert omega.poisson_bracket(f, g) == omega.contract(
|
|
95
|
+
0, omega.hamiltonian_vector_field(f)
|
|
96
|
+
).contract(0, omega.hamiltonian_vector_field(g))
|
|
97
|
+
|
|
98
|
+
def test_poisson_bracket_as_contraction_poisson_tensor(
|
|
99
|
+
self, M: DifferentiableManifold, omega: SymplecticForm
|
|
100
|
+
):
|
|
101
|
+
f = generic_scalar_field(M, "f")
|
|
102
|
+
g = generic_scalar_field(M, "g")
|
|
103
|
+
# {f, g} = \pi(\dif f, \dif g)
|
|
104
|
+
assert omega.poisson_bracket(f, g) == omega.poisson().contract(
|
|
105
|
+
0, f.exterior_derivative()
|
|
106
|
+
).contract(0, g.exterior_derivative())
|
|
107
|
+
|
|
108
|
+
def test_poisson_bracket_as_contraction_hamiltonian_vector_field(
|
|
109
|
+
self, M: DifferentiableManifold, omega: SymplecticForm
|
|
110
|
+
):
|
|
111
|
+
f = generic_scalar_field(M, "f")
|
|
112
|
+
g = generic_scalar_field(M, "g")
|
|
113
|
+
# {f, g} = X_f (g)
|
|
114
|
+
assert omega.poisson_bracket(f, g) == omega.hamiltonian_vector_field(f)(g)
|
|
115
|
+
# {f, g} = -X_g(f)
|
|
116
|
+
assert omega.poisson_bracket(f, g) == -omega.hamiltonian_vector_field(g)(f)
|
|
117
|
+
|
|
118
|
+
def test_poisson_bracket_as_commutator_hamiltonian_vector_fields(
|
|
119
|
+
self, M: DifferentiableManifold, omega: SymplecticForm
|
|
120
|
+
):
|
|
121
|
+
f = generic_scalar_field(M, "f")
|
|
122
|
+
g = generic_scalar_field(M, "g")
|
|
123
|
+
# [X_f, X_g] = X_{{f,g}}
|
|
124
|
+
assert omega.hamiltonian_vector_field(f).bracket(
|
|
125
|
+
omega.hamiltonian_vector_field(g)
|
|
126
|
+
) == omega.hamiltonian_vector_field(omega.poisson_bracket(f, g))
|
|
127
|
+
|
|
128
|
+
def test_hodge_star_of_one_is_volume(
|
|
129
|
+
self, M: DifferentiableManifold, omega: SymplecticForm
|
|
130
|
+
):
|
|
131
|
+
assert M.one_scalar_field().hodge_dual(omega) == omega.volume_form()
|
|
132
|
+
|
|
133
|
+
def test_hodge_star_of_volume_is_one(
|
|
134
|
+
self, M: DifferentiableManifold, omega: SymplecticForm
|
|
135
|
+
):
|
|
136
|
+
assert omega.volume_form().hodge_dual(omega) == M.one_scalar_field()
|
|
137
|
+
|
|
138
|
+
def test_trace_of_two_form_is_given_using_contraction_with_omega(
|
|
139
|
+
self, M: DifferentiableManifold, omega: SymplecticForm
|
|
140
|
+
):
|
|
141
|
+
a = M.diff_form(2)
|
|
142
|
+
a[1,2] = 3
|
|
143
|
+
assert a.trace(using=omega) == a.up(omega, 1).trace()
|
|
144
|
+
|
|
145
|
+
def test_omega_on_forms_is_determinant_for_decomposables(
|
|
146
|
+
self, M: DifferentiableManifold, omega: SymplecticForm
|
|
147
|
+
):
|
|
148
|
+
a = M.one_form(1,2)
|
|
149
|
+
b = M.one_form(3,4)
|
|
150
|
+
c = M.one_form(5,6)
|
|
151
|
+
d = M.one_form(7,8)
|
|
152
|
+
|
|
153
|
+
assert omega.on_forms(a.wedge(b), c.wedge(d)) == omega.on_forms(a,c) * omega.on_forms(b, d) - omega.on_forms(a,d) * omega.on_forms(b,c)
|
|
154
|
+
|
|
155
|
+
def test_omega_on_one_forms_is_omega_on_dual_vectors(
|
|
156
|
+
self, M: DifferentiableManifold, omega: SymplecticForm
|
|
157
|
+
):
|
|
158
|
+
a = M.one_form(1,2)
|
|
159
|
+
b = M.one_form(3,4)
|
|
160
|
+
assert omega.on_forms(a, b) == omega(a.up(omega), b.up(omega))
|
|
161
|
+
|
|
162
|
+
|
|
163
|
+
def generic_scalar_field(M: DifferentiableManifold, name: str) -> DiffScalarField:
|
|
164
|
+
chart_functions = {chart: function(name)(*chart[:]) for chart in M.atlas()}
|
|
165
|
+
return M.scalar_field(chart_functions, name=name)
|
|
166
|
+
|
|
167
|
+
|
|
168
|
+
class TestR2VectorSpace:
|
|
169
|
+
@pytest.fixture
|
|
170
|
+
def M(self):
|
|
171
|
+
return StandardSymplecticSpace(2, 'R2', symplectic_name='omega')
|
|
172
|
+
|
|
173
|
+
@pytest.fixture
|
|
174
|
+
def omega(self, M):
|
|
175
|
+
return M.symplectic_form()
|
|
176
|
+
|
|
177
|
+
def test_display(self, omega: SymplecticForm):
|
|
178
|
+
assert str(omega.display()) == r"omega = -dq∧dp"
|
|
179
|
+
|
|
180
|
+
def test_poisson(self, omega: SymplecticForm):
|
|
181
|
+
# TODO: Shouldn't this be written with wedge product?
|
|
182
|
+
assert str(omega.poisson().display()) == r"poisson_omega = -e_q∧e_p"
|
|
183
|
+
|
|
184
|
+
def test_hamiltonian_vector_field(
|
|
185
|
+
self, M: StandardSymplecticSpace, omega: SymplecticForm
|
|
186
|
+
):
|
|
187
|
+
H = generic_scalar_field(M, "H")
|
|
188
|
+
XH = omega.hamiltonian_vector_field(H)
|
|
189
|
+
assert str(XH.display()) == r"XH = d(H)/dp e_q - d(H)/dq e_p"
|
|
190
|
+
|
|
191
|
+
def test_flat(self, M: StandardSymplecticSpace, omega: SymplecticForm):
|
|
192
|
+
X = M.vector_field(1, 2, name='X')
|
|
193
|
+
assert str(X.display()) == r"X = e_q + 2 e_p"
|
|
194
|
+
assert str(omega.flat(X).display()) == r"X_flat = 2 dq - dp"
|
|
195
|
+
|
|
196
|
+
def test_hodge_star(self, M: StandardSymplecticSpace, omega: SymplecticForm):
|
|
197
|
+
# Standard basis
|
|
198
|
+
e = M.one_form(0,1, name='e')
|
|
199
|
+
f = M.one_form(1,0, name='f')
|
|
200
|
+
assert e.wedge(f) == omega
|
|
201
|
+
|
|
202
|
+
assert M.one_scalar_field().hodge_dual(omega) == omega
|
|
203
|
+
assert e.hodge_dual(omega) == e
|
|
204
|
+
assert f.hodge_dual(omega) == f
|
|
205
|
+
assert omega.hodge_dual(omega) == M.one_scalar_field()
|
|
206
|
+
|
|
207
|
+
def test_omega_on_one_forms(self, M: StandardSymplecticSpace, omega: SymplecticForm):
|
|
208
|
+
# Standard basis
|
|
209
|
+
e = M.one_form(0,1, name='e')
|
|
210
|
+
f = M.one_form(1,0, name='f')
|
|
211
|
+
assert e.wedge(f) == omega
|
|
212
|
+
|
|
213
|
+
assert omega.on_forms(e, f) == 1
|
|
214
|
+
|
|
215
|
+
def test_hodge_star_is_given_using_omega_on_forms(
|
|
216
|
+
self, M: StandardSymplecticSpace, omega: SymplecticForm
|
|
217
|
+
):
|
|
218
|
+
a = M.one_form(1,2)
|
|
219
|
+
b = M.one_form(3,4)
|
|
220
|
+
assert a.wedge(b.hodge_dual(omega)) == omega.on_forms(a, b) * omega.volume_form()
|
|
@@ -0,0 +1,412 @@
|
|
|
1
|
+
# sage_setup: distribution = sagemath-symbolics
|
|
2
|
+
r"""
|
|
3
|
+
Tangent Spaces
|
|
4
|
+
|
|
5
|
+
The class :class:`TangentSpace` implements tangent vector spaces to a
|
|
6
|
+
differentiable manifold.
|
|
7
|
+
|
|
8
|
+
AUTHORS:
|
|
9
|
+
|
|
10
|
+
- Eric Gourgoulhon, Michal Bejger (2014-2015): initial version
|
|
11
|
+
- Travis Scrimshaw (2016): review tweaks
|
|
12
|
+
|
|
13
|
+
REFERENCES:
|
|
14
|
+
|
|
15
|
+
- Chap. 3 of [Lee2013]_
|
|
16
|
+
"""
|
|
17
|
+
|
|
18
|
+
#******************************************************************************
|
|
19
|
+
# Copyright (C) 2015 Eric Gourgoulhon <eric.gourgoulhon@obspm.fr>
|
|
20
|
+
# Copyright (C) 2015 Michal Bejger <bejger@camk.edu.pl>
|
|
21
|
+
#
|
|
22
|
+
# Distributed under the terms of the GNU General Public License (GPL)
|
|
23
|
+
# as published by the Free Software Foundation; either version 2 of
|
|
24
|
+
# the License, or (at your option) any later version.
|
|
25
|
+
# http://www.gnu.org/licenses/
|
|
26
|
+
#******************************************************************************
|
|
27
|
+
from __future__ import annotations
|
|
28
|
+
|
|
29
|
+
from typing import TYPE_CHECKING
|
|
30
|
+
|
|
31
|
+
from sage.manifolds.differentiable.tangent_vector import TangentVector
|
|
32
|
+
from sage.symbolic.ring import SR
|
|
33
|
+
from sage.tensor.modules.finite_rank_free_module import FiniteRankFreeModule
|
|
34
|
+
|
|
35
|
+
if TYPE_CHECKING:
|
|
36
|
+
from sage.manifolds.point import ManifoldPoint
|
|
37
|
+
|
|
38
|
+
|
|
39
|
+
class TangentSpace(FiniteRankFreeModule):
|
|
40
|
+
r"""
|
|
41
|
+
Tangent space to a differentiable manifold at a given point.
|
|
42
|
+
|
|
43
|
+
Let `M` be a differentiable manifold of dimension `n` over a
|
|
44
|
+
topological field `K` and `p \in M`. The tangent space `T_p M` is an
|
|
45
|
+
`n`-dimensional vector space over `K` (without a distinguished basis).
|
|
46
|
+
|
|
47
|
+
INPUT:
|
|
48
|
+
|
|
49
|
+
- ``point`` -- :class:`~sage.manifolds.point.ManifoldPoint`;
|
|
50
|
+
point `p` at which the tangent space is defined
|
|
51
|
+
|
|
52
|
+
EXAMPLES:
|
|
53
|
+
|
|
54
|
+
Tangent space on a 2-dimensional manifold::
|
|
55
|
+
|
|
56
|
+
sage: M = Manifold(2, 'M')
|
|
57
|
+
sage: c_xy.<x,y> = M.chart()
|
|
58
|
+
sage: p = M.point((-1,2), name='p')
|
|
59
|
+
sage: Tp = M.tangent_space(p) ; Tp
|
|
60
|
+
Tangent space at Point p on the 2-dimensional differentiable manifold M
|
|
61
|
+
|
|
62
|
+
Tangent spaces are free modules of finite rank over
|
|
63
|
+
:class:`~sage.symbolic.ring.SymbolicRing`
|
|
64
|
+
(actually vector spaces of finite dimension over the manifold base
|
|
65
|
+
field `K`, with `K=\RR` here)::
|
|
66
|
+
|
|
67
|
+
sage: Tp.base_ring()
|
|
68
|
+
Symbolic Ring
|
|
69
|
+
sage: Tp.category()
|
|
70
|
+
Category of finite dimensional vector spaces over Symbolic Ring
|
|
71
|
+
sage: Tp.rank()
|
|
72
|
+
2
|
|
73
|
+
sage: dim(Tp)
|
|
74
|
+
2
|
|
75
|
+
|
|
76
|
+
The tangent space is automatically endowed with bases deduced from the
|
|
77
|
+
vector frames around the point::
|
|
78
|
+
|
|
79
|
+
sage: Tp.bases()
|
|
80
|
+
[Basis (∂/∂x,∂/∂y) on the Tangent space at Point p on the 2-dimensional
|
|
81
|
+
differentiable manifold M]
|
|
82
|
+
sage: M.frames()
|
|
83
|
+
[Coordinate frame (M, (∂/∂x,∂/∂y))]
|
|
84
|
+
|
|
85
|
+
At this stage, only one basis has been defined in the tangent space, but
|
|
86
|
+
new bases can be added from vector frames on the manifold by means of the
|
|
87
|
+
method :meth:`~sage.manifolds.differentiable.vectorframe.VectorFrame.at`,
|
|
88
|
+
for instance, from the frame associated with some new coordinates::
|
|
89
|
+
|
|
90
|
+
sage: c_uv.<u,v> = M.chart()
|
|
91
|
+
sage: c_uv.frame().at(p)
|
|
92
|
+
Basis (∂/∂u,∂/∂v) on the Tangent space at Point p on the 2-dimensional
|
|
93
|
+
differentiable manifold M
|
|
94
|
+
sage: Tp.bases()
|
|
95
|
+
[Basis (∂/∂x,∂/∂y) on the Tangent space at Point p on the 2-dimensional
|
|
96
|
+
differentiable manifold M,
|
|
97
|
+
Basis (∂/∂u,∂/∂v) on the Tangent space at Point p on the 2-dimensional
|
|
98
|
+
differentiable manifold M]
|
|
99
|
+
|
|
100
|
+
All the bases defined on ``Tp`` are on the same footing. Accordingly the
|
|
101
|
+
tangent space is not in the category of modules with a distinguished
|
|
102
|
+
basis::
|
|
103
|
+
|
|
104
|
+
sage: Tp in ModulesWithBasis(SR)
|
|
105
|
+
False
|
|
106
|
+
|
|
107
|
+
It is simply in the category of modules::
|
|
108
|
+
|
|
109
|
+
sage: Tp in Modules(SR)
|
|
110
|
+
True
|
|
111
|
+
|
|
112
|
+
Since the base ring is a field, it is actually in the category of
|
|
113
|
+
vector spaces::
|
|
114
|
+
|
|
115
|
+
sage: Tp in VectorSpaces(SR)
|
|
116
|
+
True
|
|
117
|
+
|
|
118
|
+
A typical element::
|
|
119
|
+
|
|
120
|
+
sage: v = Tp.an_element() ; v
|
|
121
|
+
Tangent vector at Point p on the
|
|
122
|
+
2-dimensional differentiable manifold M
|
|
123
|
+
sage: v.display()
|
|
124
|
+
∂/∂x + 2 ∂/∂y
|
|
125
|
+
sage: v.parent()
|
|
126
|
+
Tangent space at Point p on the
|
|
127
|
+
2-dimensional differentiable manifold M
|
|
128
|
+
|
|
129
|
+
The zero vector::
|
|
130
|
+
|
|
131
|
+
sage: Tp.zero()
|
|
132
|
+
Tangent vector zero at Point p on the
|
|
133
|
+
2-dimensional differentiable manifold M
|
|
134
|
+
sage: Tp.zero().display()
|
|
135
|
+
zero = 0
|
|
136
|
+
sage: Tp.zero().parent()
|
|
137
|
+
Tangent space at Point p on the
|
|
138
|
+
2-dimensional differentiable manifold M
|
|
139
|
+
|
|
140
|
+
Tangent spaces are unique::
|
|
141
|
+
|
|
142
|
+
sage: M.tangent_space(p) is Tp
|
|
143
|
+
True
|
|
144
|
+
sage: p1 = M.point((-1,2))
|
|
145
|
+
sage: M.tangent_space(p1) is Tp
|
|
146
|
+
True
|
|
147
|
+
|
|
148
|
+
even if points are not::
|
|
149
|
+
|
|
150
|
+
sage: p1 is p
|
|
151
|
+
False
|
|
152
|
+
|
|
153
|
+
Actually ``p1`` and ``p`` share the same tangent space because they
|
|
154
|
+
compare equal::
|
|
155
|
+
|
|
156
|
+
sage: p1 == p
|
|
157
|
+
True
|
|
158
|
+
|
|
159
|
+
The tangent-space uniqueness holds even if the points are created in
|
|
160
|
+
different coordinate systems::
|
|
161
|
+
|
|
162
|
+
sage: xy_to_uv = c_xy.transition_map(c_uv, (x+y, x-y))
|
|
163
|
+
sage: uv_to_xv = xy_to_uv.inverse()
|
|
164
|
+
sage: p2 = M.point((1, -3), chart=c_uv, name='p_2')
|
|
165
|
+
sage: p2 is p
|
|
166
|
+
False
|
|
167
|
+
sage: M.tangent_space(p2) is Tp
|
|
168
|
+
True
|
|
169
|
+
sage: p2 == p
|
|
170
|
+
True
|
|
171
|
+
|
|
172
|
+
An isomorphism of the tangent space with an inner product space with distinguished basis::
|
|
173
|
+
|
|
174
|
+
sage: g = M.metric('g')
|
|
175
|
+
sage: g[:] = ((1, 0), (0, 1))
|
|
176
|
+
sage: Q_Tp_xy = g[c_xy.frame(),:](*p.coordinates(c_xy)); Q_Tp_xy
|
|
177
|
+
[1 0]
|
|
178
|
+
[0 1]
|
|
179
|
+
sage: W_Tp_xy = VectorSpace(SR, 2, inner_product_matrix=Q_Tp_xy)
|
|
180
|
+
sage: Tp.bases()[0]
|
|
181
|
+
Basis (∂/∂x,∂/∂y) on the Tangent space at Point p on the
|
|
182
|
+
2-dimensional differentiable manifold M
|
|
183
|
+
sage: phi_Tp_xy = Tp.isomorphism_with_fixed_basis(Tp.bases()[0], codomain=W_Tp_xy)
|
|
184
|
+
sage: phi_Tp_xy
|
|
185
|
+
Generic morphism:
|
|
186
|
+
From: Tangent space at Point p on the 2-dimensional differentiable manifold M
|
|
187
|
+
To: Ambient quadratic space of dimension 2 over Symbolic Ring
|
|
188
|
+
Inner product matrix:
|
|
189
|
+
[1 0]
|
|
190
|
+
[0 1]
|
|
191
|
+
|
|
192
|
+
sage: Q_Tp_uv = g[c_uv.frame(),:](*p.coordinates(c_uv)); Q_Tp_uv
|
|
193
|
+
[1/2 0]
|
|
194
|
+
[ 0 1/2]
|
|
195
|
+
sage: W_Tp_uv = VectorSpace(SR, 2, inner_product_matrix=Q_Tp_uv)
|
|
196
|
+
sage: Tp.bases()[1]
|
|
197
|
+
Basis (∂/∂u,∂/∂v) on the Tangent space at Point p on the
|
|
198
|
+
2-dimensional differentiable manifold M
|
|
199
|
+
sage: phi_Tp_uv = Tp.isomorphism_with_fixed_basis(Tp.bases()[1], codomain=W_Tp_uv)
|
|
200
|
+
sage: phi_Tp_uv
|
|
201
|
+
Generic morphism:
|
|
202
|
+
From: Tangent space at Point p on the 2-dimensional differentiable manifold M
|
|
203
|
+
To: Ambient quadratic space of dimension 2 over Symbolic Ring
|
|
204
|
+
Inner product matrix:
|
|
205
|
+
[1/2 0]
|
|
206
|
+
[ 0 1/2]
|
|
207
|
+
|
|
208
|
+
sage: t1, t2 = Tp.tensor((1,0)), Tp.tensor((1,0))
|
|
209
|
+
sage: t1[:] = (8, 15)
|
|
210
|
+
sage: t2[:] = (47, 11)
|
|
211
|
+
sage: t1[Tp.bases()[0],:]
|
|
212
|
+
[8, 15]
|
|
213
|
+
sage: phi_Tp_xy(t1), phi_Tp_xy(t2)
|
|
214
|
+
((8, 15), (47, 11))
|
|
215
|
+
sage: phi_Tp_xy(t1).inner_product(phi_Tp_xy(t2))
|
|
216
|
+
541
|
|
217
|
+
|
|
218
|
+
sage: Tp_xy_to_uv = M.change_of_frame(c_xy.frame(), c_uv.frame()).at(p); Tp_xy_to_uv
|
|
219
|
+
Automorphism of the Tangent space at Point p on the
|
|
220
|
+
2-dimensional differentiable manifold M
|
|
221
|
+
sage: Tp.set_change_of_basis(Tp.bases()[0], Tp.bases()[1], Tp_xy_to_uv)
|
|
222
|
+
sage: t1[Tp.bases()[1],:]
|
|
223
|
+
[23, -7]
|
|
224
|
+
sage: phi_Tp_uv(t1), phi_Tp_uv(t2)
|
|
225
|
+
((23, -7), (58, 36))
|
|
226
|
+
sage: phi_Tp_uv(t1).inner_product(phi_Tp_uv(t2))
|
|
227
|
+
541
|
|
228
|
+
|
|
229
|
+
.. SEEALSO::
|
|
230
|
+
|
|
231
|
+
:class:`~sage.tensor.modules.finite_rank_free_module.FiniteRankFreeModule`
|
|
232
|
+
for more documentation.
|
|
233
|
+
"""
|
|
234
|
+
Element = TangentVector
|
|
235
|
+
|
|
236
|
+
def __init__(self, point: ManifoldPoint, base_ring=None):
|
|
237
|
+
r"""
|
|
238
|
+
Construct the tangent space at a given point.
|
|
239
|
+
|
|
240
|
+
TESTS::
|
|
241
|
+
|
|
242
|
+
sage: from sage.manifolds.differentiable.tangent_space import TangentSpace
|
|
243
|
+
sage: M = Manifold(2, 'M')
|
|
244
|
+
sage: X.<x,y> = M.chart()
|
|
245
|
+
sage: p = M.point((1,-2), name='p')
|
|
246
|
+
sage: Tp = TangentSpace(p) ; Tp
|
|
247
|
+
Tangent space at Point p on the 2-dimensional differentiable
|
|
248
|
+
manifold M
|
|
249
|
+
sage: TestSuite(Tp).run()
|
|
250
|
+
"""
|
|
251
|
+
manif = point._manifold
|
|
252
|
+
name = "T_{} {}".format(point._name, manif._name)
|
|
253
|
+
latex_name = r"T_{%s}\,%s" % (point._latex_name, manif._latex_name)
|
|
254
|
+
self._point = point
|
|
255
|
+
self._manif = manif
|
|
256
|
+
if base_ring is None:
|
|
257
|
+
base_ring = SR
|
|
258
|
+
FiniteRankFreeModule.__init__(self, base_ring, manif._dim, name=name,
|
|
259
|
+
latex_name=latex_name,
|
|
260
|
+
start_index=manif._sindex)
|
|
261
|
+
# Initialization of bases of the tangent space from existing vector
|
|
262
|
+
# frames around the point:
|
|
263
|
+
|
|
264
|
+
# dictionary of bases of the tangent space derived from vector
|
|
265
|
+
# frames around the point (keys: vector frames)
|
|
266
|
+
self._frame_bases = {}
|
|
267
|
+
for frame in point.parent()._top_frames:
|
|
268
|
+
# the frame is used to construct a basis of the tangent space
|
|
269
|
+
# only if it is a frame on the current manifold:
|
|
270
|
+
if frame.destination_map().is_identity():
|
|
271
|
+
if point in frame._domain:
|
|
272
|
+
coframe = frame.coframe()
|
|
273
|
+
basis = self.basis(frame._symbol,
|
|
274
|
+
latex_symbol=frame._latex_symbol,
|
|
275
|
+
indices=frame._indices,
|
|
276
|
+
latex_indices=frame._latex_indices,
|
|
277
|
+
symbol_dual=coframe._symbol,
|
|
278
|
+
latex_symbol_dual=coframe._latex_symbol)
|
|
279
|
+
self._frame_bases[frame] = basis
|
|
280
|
+
# The basis induced by the default frame of the manifold subset
|
|
281
|
+
# in which the point has been created is declared the default
|
|
282
|
+
# basis of self:
|
|
283
|
+
def_frame = point.parent()._def_frame
|
|
284
|
+
if def_frame in self._frame_bases:
|
|
285
|
+
self._def_basis = self._frame_bases[def_frame]
|
|
286
|
+
# Initialization of the changes of bases from the existing changes of
|
|
287
|
+
# frames around the point:
|
|
288
|
+
for frame_pair, automorph in point.parent()._frame_changes.items():
|
|
289
|
+
if point in automorph.domain():
|
|
290
|
+
frame1, frame2 = frame_pair[0], frame_pair[1]
|
|
291
|
+
fr1, fr2 = None, None
|
|
292
|
+
for frame in self._frame_bases:
|
|
293
|
+
if frame1 in frame._subframes:
|
|
294
|
+
fr1 = frame
|
|
295
|
+
break
|
|
296
|
+
for frame in self._frame_bases:
|
|
297
|
+
if frame2 in frame._subframes:
|
|
298
|
+
fr2 = frame
|
|
299
|
+
break
|
|
300
|
+
if fr1 is not None and fr2 is not None:
|
|
301
|
+
basis1 = self._frame_bases[fr1]
|
|
302
|
+
basis2 = self._frame_bases[fr2]
|
|
303
|
+
auto = self.automorphism()
|
|
304
|
+
for frame, comp in automorph._components.items():
|
|
305
|
+
try:
|
|
306
|
+
basis = None
|
|
307
|
+
if frame is frame1:
|
|
308
|
+
basis = basis1
|
|
309
|
+
if frame is frame2:
|
|
310
|
+
basis = basis2
|
|
311
|
+
if basis is not None:
|
|
312
|
+
cauto = auto.add_comp(basis=basis)
|
|
313
|
+
for ind, val in comp._comp.items():
|
|
314
|
+
cauto._comp[ind] = val(point)
|
|
315
|
+
except ValueError:
|
|
316
|
+
pass
|
|
317
|
+
self._basis_changes[(basis1, basis2)] = auto
|
|
318
|
+
|
|
319
|
+
def construction(self):
|
|
320
|
+
"""
|
|
321
|
+
TESTS::
|
|
322
|
+
|
|
323
|
+
sage: M = Manifold(2, 'M')
|
|
324
|
+
sage: X.<x,y> = M.chart()
|
|
325
|
+
sage: p = M.point((3,-2), name='p')
|
|
326
|
+
sage: Tp = M.tangent_space(p)
|
|
327
|
+
sage: Tp.construction() is None
|
|
328
|
+
True
|
|
329
|
+
"""
|
|
330
|
+
return None
|
|
331
|
+
|
|
332
|
+
def _repr_(self):
|
|
333
|
+
r"""
|
|
334
|
+
String representation of ``self``.
|
|
335
|
+
|
|
336
|
+
EXAMPLES::
|
|
337
|
+
|
|
338
|
+
sage: M = Manifold(2, 'M')
|
|
339
|
+
sage: X.<x,y> = M.chart()
|
|
340
|
+
sage: p = M.point((3,-2), name='p')
|
|
341
|
+
sage: Tp = M.tangent_space(p)
|
|
342
|
+
sage: Tp
|
|
343
|
+
Tangent space at Point p on the
|
|
344
|
+
2-dimensional differentiable manifold M
|
|
345
|
+
"""
|
|
346
|
+
return "Tangent space at {}".format(self._point)
|
|
347
|
+
|
|
348
|
+
def _an_element_(self):
|
|
349
|
+
r"""
|
|
350
|
+
Construct some (unnamed) vector in ``self``.
|
|
351
|
+
|
|
352
|
+
EXAMPLES::
|
|
353
|
+
|
|
354
|
+
sage: M = Manifold(2, 'M')
|
|
355
|
+
sage: X.<x,y> = M.chart()
|
|
356
|
+
sage: p = M.point((3,-2), name='p')
|
|
357
|
+
sage: Tp = M.tangent_space(p)
|
|
358
|
+
sage: Tp._an_element_()
|
|
359
|
+
Tangent vector at Point p on the 2-dimensional differentiable
|
|
360
|
+
manifold M
|
|
361
|
+
sage: Tp._an_element_().display()
|
|
362
|
+
∂/∂x + 2 ∂/∂y
|
|
363
|
+
"""
|
|
364
|
+
resu = self.element_class(self)
|
|
365
|
+
if self._def_basis is not None:
|
|
366
|
+
resu.set_comp()[:] = range(1, self._rank+1)
|
|
367
|
+
return resu
|
|
368
|
+
|
|
369
|
+
def dimension(self):
|
|
370
|
+
r"""
|
|
371
|
+
Return the vector space dimension of ``self``.
|
|
372
|
+
|
|
373
|
+
EXAMPLES::
|
|
374
|
+
|
|
375
|
+
sage: M = Manifold(2, 'M')
|
|
376
|
+
sage: X.<x,y> = M.chart()
|
|
377
|
+
sage: p = M.point((1,-2), name='p')
|
|
378
|
+
sage: Tp = M.tangent_space(p)
|
|
379
|
+
sage: Tp.dimension()
|
|
380
|
+
2
|
|
381
|
+
|
|
382
|
+
A shortcut is ``dim()``::
|
|
383
|
+
|
|
384
|
+
sage: Tp.dim()
|
|
385
|
+
2
|
|
386
|
+
|
|
387
|
+
One can also use the global function ``dim``::
|
|
388
|
+
|
|
389
|
+
sage: dim(Tp)
|
|
390
|
+
2
|
|
391
|
+
"""
|
|
392
|
+
# The dimension is the rank of self as a free module:
|
|
393
|
+
return self._rank
|
|
394
|
+
|
|
395
|
+
dim = dimension
|
|
396
|
+
|
|
397
|
+
def base_point(self):
|
|
398
|
+
r"""
|
|
399
|
+
Return the manifold point at which ``self`` is defined.
|
|
400
|
+
|
|
401
|
+
EXAMPLES::
|
|
402
|
+
|
|
403
|
+
sage: M = Manifold(2, 'M')
|
|
404
|
+
sage: X.<x,y> = M.chart()
|
|
405
|
+
sage: p = M.point((1,-2), name='p')
|
|
406
|
+
sage: Tp = M.tangent_space(p)
|
|
407
|
+
sage: Tp.base_point()
|
|
408
|
+
Point p on the 2-dimensional differentiable manifold M
|
|
409
|
+
sage: Tp.base_point() is p
|
|
410
|
+
True
|
|
411
|
+
"""
|
|
412
|
+
return self._point
|