Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix some quasimodular forms rings methods for congruence subgroups #34569

Closed
DavidAyotte opened this issue Sep 22, 2022 · 30 comments
Closed

Fix some quasimodular forms rings methods for congruence subgroups #34569

DavidAyotte opened this issue Sep 22, 2022 · 30 comments

Comments

@DavidAyotte
Copy link
Member

The implementation currently assumes that the congruence subgroup is SL_2(Z) and that the ring is generated by E2, E4 and E6. However, it is possible to create a ring for a congruence subgroup, which leads to some errors like this:

sage: QM = QuasiModularForms(Gamma0(17))
sage: f = QM.0
sage: f.to_polynomial()
---------------------------------------------------------------------------
Traceback (most recent call last):
...
ValueError: too many values to unpack (expected 2)

The goal of this ticket is to make the code for quasimodular forms ring coherent for congruence subgroup and add more doctests.

CC: @videlec

Component: modular forms

Keywords: quasiforms to_polynomial

Author: David Ayotte

Branch/Commit: 51412f3

Reviewer: Vincent Delecroix

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

@DavidAyotte

This comment has been minimized.

@DavidAyotte DavidAyotte changed the title quasimodular forms to_polynomial does not work for congruence subgroups Fix some quasimodular forms rings methods for congruence subgroups Oct 27, 2022
@DavidAyotte
Copy link
Member Author

@sagetrac-git
Copy link
Mannequin

sagetrac-git mannequin commented Oct 28, 2022

Commit: d55eb7e

@sagetrac-git
Copy link
Mannequin

sagetrac-git mannequin commented Oct 28, 2022

Branch pushed to git repo; I updated commit sha1. New commits:

d55eb7eadd various doctests

@videlec
Copy link
Contributor

videlec commented Oct 28, 2022

comment:5

Nice!

  1. The first generators is the weight 2 Eisenstein serie -> The first generator is the weight 2 Eisenstein series (ie remove s and the end of generators and add one in series)

  2. The other generators corresponds -> correspond (plural)

-    def polynomial_ring(self, names='E2, E4, E6'):
+    def polynomial_ring(self, names='g'):

This is a backward incompatible change (maybe not so dramatic?). One possibility would be to use the signature def polynomial_ring(self, names=None) and then, depending whether the group is SL(2,Z) or not, use E2, E4, E6 or g0, g1, g2, .... Also, there might be a better naming than g0, g1, g2, .... For example

  • E2 is always the first generator and could be name as such
  • it could be useful that the other generators carry their degree as part of their names
    Do you know if there is any standard naming in the literature?

@videlec
Copy link
Contributor

videlec commented Oct 28, 2022

Reviewer: Vincent Delecroix

@DavidAyotte
Copy link
Member Author

comment:7

Replying to Vincent Delecroix:

-    def polynomial_ring(self, names='E2, E4, E6'):
+    def polynomial_ring(self, names='g'):

This is a backward incompatible change (maybe not so dramatic?). One possibility would be to use the signature def polynomial_ring(self, names=None) and then, depending whether the group is SL(2,Z) or not, use E2, E4, E6 or g0, g1, g2, .... Also, there might be a better naming than g0, g1, g2, .... For example

  • E2 is always the first generator and could be name as such
  • it could be useful that the other generators carry their degree as part of their names
    Do you know if there is any standard naming in the literature?

Hi Vincent, thanks for your comment! I don't think there is any standard naming in the literature (even for Eisenstein series I've seen the same name for different normalizations). I agree however for a better naming. In line with your suggestion, I propose that we use E2 for the weight 2 Eisenstein series and gki to denote the i-th generator of degree k For example, if the group is Gamma1(3), we would have:

E2, g20, g30, g31, g40

What do you think?

@sagetrac-git
Copy link
Mannequin

sagetrac-git mannequin commented Oct 28, 2022

Changed commit from d55eb7e to 8386a3e

@sagetrac-git
Copy link
Mannequin

sagetrac-git mannequin commented Oct 28, 2022

Branch pushed to git repo; I updated commit sha1. New commits:

8386a3esrc/sage/modular/quasimodform/ring.py: fix comments 1) and 2)

@sagetrac-git
Copy link
Mannequin

sagetrac-git mannequin commented Oct 28, 2022

Branch pushed to git repo; I updated commit sha1. New commits:

1b5c14esrc/sage/modular/quasimodform/ring.py: fix comment 1)

@sagetrac-git
Copy link
Mannequin

sagetrac-git mannequin commented Oct 28, 2022

Changed commit from 8386a3e to 1b5c14e

@videlec
Copy link
Contributor

videlec commented Oct 28, 2022

comment:10

Sounds good. Maybe better to not mix lower and upper case. Also your current suggestion has collision: degree 12 number 0 and degree 1 number 20 give the same string.

Maybe a more readable choice is

  • E2 in degree 2
  • (E4), F4, G4, ... in degree 4 (if you are out of letters you can continue with AA4, AB4, etc). The E4 should be reserved only for the Eisenstein series so that there is no confusion.
  • (E6), F6, G6, ... in degree 6. Idem for E6
  • ...

@sagetrac-git
Copy link
Mannequin

sagetrac-git mannequin commented Oct 29, 2022

Changed commit from 1b5c14e to 2e8855f

@sagetrac-git
Copy link
Mannequin

sagetrac-git mannequin commented Oct 29, 2022

Branch pushed to git repo; I updated commit sha1. New commits:

d8949bbsrc/sage/modular/quasimodform/ring.py: fix names for polynomial_ring method
ea69eb3src/sage/modular/quasimodform/ring.py: fix documentation
2e8855fsrc/sage/modular/quasimodform/element.py: fix doc

@DavidAyotte
Copy link
Member Author

comment:12

Replying to Vincent Delecroix:

Sounds good. Maybe better to not mix lower and upper case. Also your current suggestion has collision: degree 12 number 0 and degree 1 number 20 give the same string.

Well spotted!

Maybe a more readable choice is

  • E2 in degree 2
  • (E4), F4, G4, ... in degree 4 (if you are out of letters you can continue with AA4, AB4, etc). The E4 should be reserved only for the Eisenstein series so that there is no confusion.
  • (E6), F6, G6, ... in degree 6. Idem for E6
  • ...

That's a good suggestion, thanks! I implemented it and fixed some documentation strings. I don't know if it's the most optimal way as I use a couple of for loops, so if you have any suggestions I'm all ears!

@sagetrac-git
Copy link
Mannequin

sagetrac-git mannequin commented Oct 31, 2022

Branch pushed to git repo; I updated commit sha1. New commits:

eac534bsrc/sage/modular/quasimodform/ring.py: delete unused import

@sagetrac-git
Copy link
Mannequin

sagetrac-git mannequin commented Oct 31, 2022

Changed commit from 2e8855f to eac534b

@videlec
Copy link
Contributor

videlec commented Nov 3, 2022

comment:15

Sorry, I find it a bit confusing to have E on the one hand and A, B, C, D, F, G, H on the other. I would rather go with F, G, H as we do not have many generators of the same weight, do we?

Also, it could happen that E4 and E6 are generators for other congruence groups. Could we recognize when it is the case and give them the corresponding name?

@DavidAyotte
Copy link
Member Author

comment:16

Replying to Vincent Delecroix:

Sorry, I find it a bit confusing to have E on the one hand and A, B, C, D, F, G, H on the other. I would rather go with F, G, H as we do not have many generators of the same weight, do we?

Don't be sorry, any comment and suggestion is more than appreciated. Moreover, your comment makes a lot of sense. Concerning the weights, it can happens that we have (relatively) a lot of generators of the same weights. As an example, for the group Gamma1(13), Sage returns 33 generators for the modular form ring, 13 of which are of weight 2 and 20 of weight 3. In this case, if we use the letters F, G, H, then the names for the quasimodular forms ring looks like this:

E2, F2, G2, H2, FF2, FG2, FH2, GF2, GG2, GH2, HF2, HG2, HH2, FFF2,
F3, G3, H3, FF3, FG3, FH3, GF3, GG3, GH3, HF3, HG3, HH3, FFF3, FFG3,
FFH3, FGF3, FGG3, FGH3, FHF3, FHG3

Personally, I would be okay with this.

Replying to Vincent Delecroix:

Also, it could happen that E4 and E6 are generators for other congruence groups. Could we recognize when it is the case and give them the corresponding name?

This is a good question. Yes I think that it would be possible to recognize when it is the case. However, according to my experiments (up to level 30 for Gamma0 and level 20 for Gamma1), it never happens that we have exactly the level 1 E4 and/or E6 as a generator for a ring of level > 1. The closest to these forms that can be returned is their image under the map i_d:f(\tau) |--> f(d\tau) where d is a divisor of the level. This map sends a form of level M to a form of level Nd and "shift" the q-expansion like so: \sum_n a_n q^n |--> \sum_n a_n q^(dn) (the map i_d shows up in Diamond-Shurman. sect. 5.6). I'm a bit hesitant to use the letter E4 to denote i_d(E4) (but I don't think this is what you were suggesting).

Here are the computations I did:

github.com/DavidAyotte/modforms_poly_rel/tree/main/misc.

@videlec
Copy link
Contributor

videlec commented Nov 4, 2022

comment:17

Replying to David Ayotte:

Replying to Vincent Delecroix:

Sorry, I find it a bit confusing to have E on the one hand and A, B, C, D, F, G, H on the other. I would rather go with F, G, H as we do not have many generators of the same weight, do we?

Don't be sorry, any comment and suggestion is more than appreciated. Moreover, your comment makes a lot of sense. Concerning the weights, it can happens that we have (relatively) a lot of generators of the same weights. As an example, for the group Gamma1(13), Sage returns 33 generators for the modular form ring, 13 of which are of weight 2 and 20 of weight 3. In this case, if we use the letters F, G, H, then the names for the quasimodular forms ring looks like this:

E2, F2, G2, H2, FF2, FG2, FH2, GF2, GG2, GH2, HF2, HG2, HH2, FFF2,
F3, G3, H3, FF3, FG3, FH3, GF3, GG3, GH3, HF3, HG3, HH3, FFF3, FFG3,
FFH3, FGF3, FGG3, FGH3, FHF3, FHG3

Personally, I would be okay with this.

Ok for me but not extremly nice. What about using letters after H, eg I, J, ...?

Replying to Vincent Delecroix:

Also, it could happen that E4 and E6 are generators for other congruence groups. Could we recognize when it is the case and give them the corresponding name?

This is a good question. Yes I think that it would be possible to recognize when it is the case. However, according to my experiments (up to level 30 for Gamma0 and level 20 for Gamma1), it never happens that we have exactly the level 1 E4 and/or E6 as a generator for a ring of level > 1. The closest to these forms that can be returned is their image under the map i_d:f(\tau) |--> f(d\tau) where d is a divisor of the level. This map sends a form of level M to a form of level Nd and "shift" the q-expansion like so: \sum_n a_n q^n |--> \sum_n a_n q^(dn) (the map i_d shows up in Diamond-Shurman. sect. 5.6). I'm a bit hesitant to use the letter E4 to denote i_d(E4) (but I don't think this is what you were suggesting).

Here are the computations I did:

github.com/DavidAyotte/modforms_poly_rel/tree/main/misc.

If these i_d(E4), i_d(E6), ... can easily be detected it might be worth introducing a special notation for them (though parenthesis are not allowed in variable names). Is it true that i_d(M(Gamma(e)) is a sub-algebra of M(Gamma(d*e))? I guess that this is related to these concepts of "old forms" and "new forms".

@videlec
Copy link
Contributor

videlec commented Nov 4, 2022

comment:18

Replying to Vincent Delecroix:

Replying to David Ayotte:

Replying to Vincent Delecroix:
Replying to Vincent Delecroix:

Also, it could happen that E4 and E6 are generators for other congruence groups. Could we recognize when it is the case and give them the corresponding name?

This is a good question. Yes I think that it would be possible to recognize when it is the case. However, according to my experiments (up to level 30 for Gamma0 and level 20 for Gamma1), it never happens that we have exactly the level 1 E4 and/or E6 as a generator for a ring of level > 1. The closest to these forms that can be returned is their image under the map i_d:f(\tau) |--> f(d\tau) where d is a divisor of the level. This map sends a form of level M to a form of level Nd and "shift" the q-expansion like so: \sum_n a_n q^n |--> \sum_n a_n q^(dn) (the map i_d shows up in Diamond-Shurman. sect. 5.6). I'm a bit hesitant to use the letter E4 to denote i_d(E4) (but I don't think this is what you were suggesting).

Here are the computations I did:

github.com/DavidAyotte/modforms_poly_rel/tree/main/misc.

If these i_d(E4), i_d(E6), ... can easily be detected it might be worth introducing a special notation for them (though parenthesis are not allowed in variable names). Is it true that i_d(M(Gamma(e)) is a sub-algebra of M(Gamma(d*e))? I guess that this is related to these concepts of "old forms" and "new forms".

Indeed. Old forms are precisely these i_d(f). Maybe they could be "tagged" with the appropriate level d in their names such as

  • for new forms: F4, G4, H4, ...
  • for old forms of level N/2: F4_2, G4_2, ...
  • for old forms of level N/3: F4_3, G4_3, ...
    What do you think?

@DavidAyotte
Copy link
Member Author

comment:19

Replying to Vincent Delecroix:

Indeed. Old forms are precisely these i_d(f). Maybe they could be "tagged" with the appropriate level d in their names such as

  • for new forms: F4, G4, H4, ...
  • for old forms of level N/2: F4_2, G4_2, ...
  • for old forms of level N/3: F4_3, G4_3, ...
    What do you think?

I think that it is a good suggestion (which is definitely possible to implement)! I also have a suggestion: instead of distinguishing the old/new forms, we could simply distinguish whether a generator is an element of a basis for the Eisenstein subspace or the cuspidal subspace. For example, we would have

sage: QM = QuasiModularForms(Gamma0(29))
sage: QM.polynomial_ring()
Multivariate Polynomial Ring in E2, F2, S2_0, S2_1, E4_0, F4, G4, H4 over Rational Field
sage: QM.4.qexp(30)  # E4_0
1 + 240*q^29 + O(q^30)
sage: EisensteinForms(Gamma0(29), 4).0.qexp(30)
1 + 240*q^29 + O(q^30)
sage: QM.2.qexp(10)  # S2_0
q - q^4 - q^5 - q^6 + 2*q^7 - 2*q^8 - 2*q^9 + O(q^10)
sage: CuspForms(Gamma0(29), 2).0.qexp(10)
q - q^4 - q^5 - q^6 + 2*q^7 - 2*q^8 - 2*q^9 + O(q^10)
sage: QM.3.qexp(10)  # S2_1
q^2 - q^3 - 2*q^4 + 2*q^6 + 2*q^7 + q^8 - 2*q^9 + O(q^10)
sage: CuspForms(Gamma0(29), 2).1.qexp(10)
q^2 - q^3 - 2*q^4 + 2*q^6 + 2*q^7 + q^8 - 2*q^9 + O(q^10)

In other words, we would use:

  • Ek_i for the i-th element of a basis of the Eisenstein subspace of weight k
  • Sk_i for the i-th element of a basis of the Cuspidal subspace of weight k (for the chosen group)
  • If the generators are of weight k and are not basis elements, we would use Fk, Gk, Hk,...

Note here the Ek_i are not necessarily Eisenstein series (but linear combination of Eisenstein series), could that be confusing? Do you have any preferences between the two suggestions?

Also, currently the method ModularFormsRing.polynomial_ring (not quasimodular forms), does not have any default option for the names. Should I implement this for the class ModularFormsRing first (as a default) for better consistency?

@videlec
Copy link
Contributor

videlec commented Nov 9, 2022

comment:20

Indeed, distinguishing Eisenstein and cuspidal forms is a more sensible choice. I am a bit confused though. Why the ring generators are not chosen to be basis elements? Isn't it always possible?

I agree that the names for QuasiModularFormsRing should match the ones from ModularFormsRing. That will greatly simplify the ring conversions to have a consistent naming scheme. Though this is going out of scope for the ticket? Going further, we could also make the polynomials live in QQ[E4, E6][E2] rather than QQ[E2, E4, E6] (for SL(2,Z)).

@DavidAyotte
Copy link
Member Author

comment:21

Replying to Vincent Delecroix:

Indeed, distinguishing Eisenstein and cuspidal forms is a more sensible choice. I am a bit confused though. Why the ring generators are not chosen to be basis elements? Isn't it always possible?

I think that you are right and it would be possible to only choose basis elements, however, from what I understand, Sage looks for a minimal set of generators. The algorithm iterates over the spaces of weight up to 8 (which I think could be reduced) and at each step looks for new generators, by multiplying together generators found during previous steps. The idea behind algorithm 1 of this paper (see page 12) seems to describe relatively well what Sage currently does (up to some details).

I agree that the names for QuasiModularFormsRing should match the ones from ModularFormsRing. That will greatly simplify the ring conversions to have a consistent naming scheme. Though this is going out of scope for the ticket? Going further, we could also make the polynomials live in QQ[E4, E6][E2] rather than QQ[E2, E4, E6] (for SL(2,Z)).

Ok lets leave this for an other ticket. Also, I'm a bit curious: what are the advantages of making the polynomials live in QQ[E4, E6][E2] rather than QQ[E2, E4, E6]?

@sagetrac-git
Copy link
Mannequin

sagetrac-git mannequin commented Nov 10, 2022

Branch pushed to git repo; I updated commit sha1. New commits:

ccb9962src/sage/modular/quasimodform/: update the default names in polynomial_ring, fix documentation, fix doctests

@sagetrac-git
Copy link
Mannequin

sagetrac-git mannequin commented Nov 10, 2022

Changed commit from eac534b to ccb9962

@videlec
Copy link
Contributor

videlec commented Nov 20, 2022

comment:24

The code looks good. From pyflakes

src/sage/modular/quasimodform/ring.py:676:9 local variable 'M' is assigned to but never used

@sagetrac-git
Copy link
Mannequin

sagetrac-git mannequin commented Nov 20, 2022

Changed commit from ccb9962 to 51412f3

@sagetrac-git
Copy link
Mannequin

sagetrac-git mannequin commented Nov 20, 2022

Branch pushed to git repo; I updated commit sha1. New commits:

51412f3src/sage/modular/quasimodform/ring.py: delete unused variable assignment

@vbraun
Copy link
Member

vbraun commented Dec 3, 2022

Changed branch from u/gh-DavidAyotte/fix_to_polynomial_quasimodform to 51412f3

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

3 participants