sagemath / sage

Main repository of SageMath
https://www.sagemath.org
Other
1.47k stars 487 forks source link

product of manifolds #31371

Open mkoeppe opened 3 years ago

mkoeppe commented 3 years ago

Taking the cartesian product of differentiable manifolds treats them as merely topological spaces.

sage: I = manifolds.OpenInterval(0, 1)                                                                                                                                            
sage: I                                                                                                                                                                           
Real interval (0, 1)
sage: II = I.cartesian_product(I)                                                                                                                                                 
sage: II.category()                                                                                                                                                               
Category of Cartesian products of connected topological spaces

This can be improved.

CC: @mjungmath @egourgoulhon @tscrim @tobiasdiez

Component: manifolds

Issue created by migration from https://trac.sagemath.org/ticket/31371

tscrim commented 3 years ago
comment:1

See Algebras for an example of how to do this. I am leaving for today right now and can push this tomorrow if someone else doesn't do it before then.

mkoeppe commented 3 years ago
comment:2

It's not just that the category needs adjusting; but actually we should add specific cartesian_product methods that take products of charts etc

egourgoulhon commented 3 years ago
comment:3

Replying to @mkoeppe:

It's not just that the category needs adjusting; but actually we should add specific cartesian_product methods that take products of charts etc

Indeed, Cartesian products of manifolds are not implemented yet. The method cartesian_product inherited from the category framework works somehow:

sage: I = manifolds.OpenInterval(0, 1)                                                              
sage: II = I.cartesian_product(I)                                                                   
sage: II.an_element()                                                                               
(Point on the Real interval (0, 1), Point on the Real interval (0, 1))

However the outcome is not a manifold:

sage: II.atlas()
...
AttributeError: 'CartesianProduct_with_category' object has no attribute 'atlas'

I guess the outcome shall belong to a subclass of a manifold class, keeping track of the fact it is a Cartesian product. What is the usage in Sage? For instance, we have

sage: V = QQ^2                                                                                      
sage: V                                                                                             
Vector space of dimension 2 over Rational Field
sage: VV = V.cartesian_product(V)                                                                   
sage: VV                                                                                            
The Cartesian product of (Vector space of dimension 2 over Rational Field, 
 Vector space of dimension 2 over Rational Field)
sage: dim(V)                                                                                        
2
sage: dim(VV)                                                                                       
...
AttributeError: 'CartesianProduct_with_category' object has no attribute '_indices'

So it seems that the Cartesian product of vector spaces is not considered as a vector space.

mkoeppe commented 3 years ago
comment:4

That's right, also vector spaces are missing a specialization of this method. However, combinatorial free modules have an implementation:

sage: W = QQ^[1,2]                                                                                                                                                                 
sage: W                                                                                                                                                                            
Free module generated by {1, 2} over Rational Field
sage: WW = W.cartesian_product(W)                                                                                                                                                  
sage: WW                                                                                                                                                                           
Free module generated by {1, 2} over Rational Field (+) Free module generated by {1, 2} over Rational Field
sage: dim(WW)                                                                                                                                                                      
4
tscrim commented 3 years ago
comment:5

I know this is out of scope of this ticket, but I wanted to just say that for normal vector spaces, one way to do it would be to simply redirect to direct_sum.

mkoeppe commented 3 years ago
comment:6

Setting new milestone based on a cursory review of ticket status, priority, and last modification date.

mjungmath commented 3 years ago
comment:7

It's about time that product manifolds will be added to the inventory. Shouldn't be too hard, at least on the level of charts. Question is: do we want to implement a whole new class such as CartesianProductManifold that also has projection maps?

mkoeppe commented 3 years ago
comment:8

Yes, it should support the protocol of cartesian products of sets defined in sage.categories.sets_cat, including cartesian_factors and cartesian_projection

tobiasdiez commented 3 years ago
comment:9

Maybe it's a good idea to directly implement the more general case of a fibred product $M \times_N M'$ for smooth maps $f, f': M \to N$ (one of them being a submersion). The charts are a bit more complicated, but this more general situation occurs quite often.

(Not sure if sage has an implementation of categorical pullbacks.)

mjungmath commented 3 years ago
comment:10

Replying to @mkoeppe:

Yes, it should support the protocol of cartesian products of sets defined in sage.categories.sets_cat, including cartesian_factors and cartesian_projection

Thanks for the reference.

Replying to @tobiasdiez:

Maybe it's a good idea to directly implement the more general case of a fibred product $M \times_N M'$ for smooth maps $f, f': M \to N$ (one of them being a submersion). The charts are a bit more complicated, but this more general situation occurs quite often.

Sounds good.

Still, one question remains: should our new manifold keep track of changes in the factors or not? The former could result in quite annoying code-writing.

mkoeppe commented 3 years ago
comment:11

Replying to @mjungmath:

Still, one question remains: should our new manifold keep track of changes in the factors or not? The former could result in quite annoying code-writing.

You could consider making it an error if the user tries to take the product of mutable manifolds.

mjungmath commented 3 years ago
comment:12

Replying to @mkoeppe:

You could consider making it an error if the user tries to take the product of mutable manifolds.

Good idea. We should make it possible to turn (mutable) manifolds into immutable objects anyway. But I assume that needs a refactoring of the current use of UniqueRepresentation.

Similarly for vector bundles (and their tensor products) btw.

tscrim commented 3 years ago
comment:13

The immutability would likely require a fairly big refactoring of the manifolds code to have checks when performing "mutations" of the manifold, such as adding a chart, frame, transition map, etc.

mjungmath commented 3 years ago
comment:14

Replying to @tscrim:

The immutability would likely require a fairly big refactoring of the manifolds code to have checks when performing "mutations" of the manifold, such as adding a chart, frame, transition map, etc.

Does it? At least for the latter, one could use the mutability wrappers or _require_(im)mutable method. That's fairly doable I'd say.

As for the UniqueRepresentation part, I honestly don't know. That might be effortful.

egourgoulhon commented 3 years ago
comment:15

Replying to @mjungmath:

As for the UniqueRepresentation part, I honestly don't know. That might be effortful.

Yes it would be desirable to get rid of UniqueRepresentation for manifolds. If I am correct, UniqueRepresentation is used only to provide an effective pickling, which is mandatory for parallel computations.

tscrim commented 3 years ago
comment:16

Replying to @egourgoulhon:

Replying to @mjungmath:

As for the UniqueRepresentation part, I honestly don't know. That might be effortful.

Yes it would be desirable to get rid of UniqueRepresentation for manifolds. If I am correct, UniqueRepresentation is used only to provide an effective pickling, which is mandatory for parallel computations.

Still on my to-do list........

@mjungmath There are a lot of things that "change" the manifold. Thus, there would be a lot of methods that need to be altered to have immutability checks. There are also questions like, "Does creating a new k-form change the manifold?" In many ways, no, but it becomes tied to the manifold as it changes _vector_field_modules attribute. Plus it is something you would want to naturally lift up to the product manifold.

egourgoulhon commented 3 years ago
comment:17

A general question about this ticket: to what extent do we want the outcome of cartesian_product keep track that it has been generated as a product? For instance, if

sage: S1 = manifolds.Sphere(1)                                                                      
sage: T2 = S1.cartesian_product(S1)                                                                 

do we want

sage: T2.an_element()                                                                               
(Point on the 1-sphere S^1 of radius 1 smoothly embedded in the Euclidean plane E^2, 
 Point on the 1-sphere S^1 of radius 1 smoothly embedded in the Euclidean plane E^2)

or something like

sage: T2.an_element()                                                                               
Point on S^1 x S^1
mkoeppe commented 3 years ago
comment:18

No preference here, as long as cartesian_projection is implemented

mjungmath commented 3 years ago
comment:19

I don't care so much either. Though, I think the latter is a bit neater.

vit-tucek commented 1 year ago

comment:17

A general question about this ticket: to what extent do we want the outcome of cartesian_product keep track that it has been generated as a product? For instance, if

sage: S1 = manifolds.Sphere(1)                                                                      
sage: T2 = S1.cartesian_product(S1)                                                                 

do we want

sage: T2.an_element()                                                                               
(Point on the 1-sphere S^1 of radius 1 smoothly embedded in the Euclidean plane E^2, 
 Point on the 1-sphere S^1 of radius 1 smoothly embedded in the Euclidean plane E^2)

or something like

sage: T2.an_element()                                                                               
Point on S^1 x S^1

Product manifolds are special. A lot of calculations simplify if one knows that the manifold has a (warped) product structure. I don't know if that matters for CAS but the potential of turning complexity from O(f(n_1 + n_2)) into O(f(n_1)) + O(f(n_2)) makes it imho worthwhile. Also, for product structures one can paralellize the calculations for different factors.