From 174d4a44589b154e69911e27993d819a85f2710b Mon Sep 17 00:00:00 2001 From: Xavier Caruso Date: Sat, 28 Dec 2024 12:13:20 +0100 Subject: [PATCH 1/5] add keyword prec to log and exp --- .../charzero_drinfeld_module.py | 66 ++++++++++++++----- 1 file changed, 48 insertions(+), 18 deletions(-) diff --git a/src/sage/rings/function_field/drinfeld_modules/charzero_drinfeld_module.py b/src/sage/rings/function_field/drinfeld_modules/charzero_drinfeld_module.py index 6142ec2fa2d..c69cb6c4dbb 100644 --- a/src/sage/rings/function_field/drinfeld_modules/charzero_drinfeld_module.py +++ b/src/sage/rings/function_field/drinfeld_modules/charzero_drinfeld_module.py @@ -25,11 +25,13 @@ from .drinfeld_module import DrinfeldModule from sage.rings.integer_ring import ZZ +from sage.rings.infinity import Infinity from sage.misc.cachefunc import cached_method from sage.misc.lazy_import import lazy_import lazy_import('sage.rings.lazy_series_ring', 'LazyPowerSeriesRing') +lazy_import('sage.rings.power_series_ring', 'PowerSeriesRing') class DrinfeldModule_charzero(DrinfeldModule): @@ -149,7 +151,7 @@ def _compute_coefficient_exp(self, k): c += self._compute_coefficient_exp(i)*self._compute_coefficient_log(j)**(q**i) return -c - def exponential(self, name='z'): + def exponential(self, prec=Infinity, name='z'): r""" Return the exponential of this Drinfeld module. @@ -158,28 +160,37 @@ def exponential(self, name='z'): INPUT: + - ``prec`` -- an integer or ``Infinity`` (default: ``Infinity``); + the precision at which the series is returned; if ``Infinity``, + a lazy power series in returned + - ``name`` -- string (default: ``'z'``); the name of the generator of the lazy power series ring - OUTPUT: a lazy power series over the base field - EXAMPLES:: sage: A = GF(2)['T'] sage: K. = Frac(A) sage: phi = DrinfeldModule(A, [T, 1]) sage: q = A.base_ring().cardinality() - sage: exp = phi.exponential(); exp - z + ((1/(T^2+T))*z^2) + ((1/(T^8+T^6+T^5+T^3))*z^4) + O(z^8) - The exponential is returned as a lazy power series, meaning that - any of its coefficients can be computed on demands:: + When ``prec`` is ``Infinity`` (which is the default), + the exponential is returned as a lazy power series, meaning + that any of its coefficients can be computed on demands:: + sage: exp = phi.exponential(); exp + z + ((1/(T^2+T))*z^2) + ((1/(T^8+T^6+T^5+T^3))*z^4) + O(z^8) sage: exp[2^4] 1/(T^64 + T^56 + T^52 + ... + T^27 + T^23 + T^15) sage: exp[2^5] 1/(T^160 + T^144 + T^136 + ... + T^55 + T^47 + T^31) + On the contrary, when ``prec`` is a finite number, all the + required coefficients are computed at once:: + + sage: phi.exponential(prec=10) + z + (1/(T^2 + T))*z^2 + (1/(T^8 + T^6 + T^5 + T^3))*z^4 + (1/(T^24 + T^20 + T^18 + T^17 + T^14 + T^13 + T^11 + T^7))*z^8 + O(z^10) + Example in higher rank:: sage: A = GF(5)['T'] @@ -216,7 +227,6 @@ def exponential(self, name='z'): See section 4.6 of [Gos1998]_ for the definition of the exponential. """ - L = LazyPowerSeriesRing(self._base, name) zero = self._base.zero() q = self._Fq.cardinality() @@ -228,7 +238,13 @@ def coeff_exp(k): return self._compute_coefficient_exp(v) else: return zero - return L(coeff_exp, valuation=1) + + if prec is Infinity: + L = LazyPowerSeriesRing(self._base, name) + return L(coeff_exp, valuation=1) + else: + L = PowerSeriesRing(self._base, name, default_prec=prec) + return L([0] + [coeff_exp(i) for i in range(1,prec)], prec=prec) @cached_method def _compute_coefficient_log(self, k): @@ -264,7 +280,7 @@ def _compute_coefficient_log(self, k): c += self._compute_coefficient_log(i)*self._gen[j]**(q**i) return c/(T - T**(q**k)) - def logarithm(self, name='z'): + def logarithm(self, prec=Infinity, name='z'): r""" Return the logarithm of the given Drinfeld module. @@ -275,27 +291,36 @@ def logarithm(self, name='z'): INPUT: + - ``prec`` -- an integer or ``Infinity`` (default: ``Infinity``); + the precision at which the series is returned; if ``Infinity``, + a lazy power series in returned + - ``name`` -- string (default: ``'z'``); the name of the generator of the lazy power series ring - OUTPUT: a lazy power series over the base field - EXAMPLES:: sage: A = GF(2)['T'] sage: K. = Frac(A) sage: phi = DrinfeldModule(A, [T, 1]) - sage: log = phi.logarithm(); log - z + ((1/(T^2+T))*z^2) + ((1/(T^6+T^5+T^3+T^2))*z^4) + O(z^8) - The logarithm is returned as a lazy power series, meaning that - any of its coefficients can be computed on demands:: + When ``prec`` is ``Infinity`` (which is the default), + the logarithm is returned as a lazy power series, meaning + that any of its coefficients can be computed on demands:: + sage: log = phi.logarithm(); log + z + ((1/(T^2+T))*z^2) + ((1/(T^6+T^5+T^3+T^2))*z^4) + O(z^8) sage: log[2^4] 1/(T^30 + T^29 + T^27 + ... + T^7 + T^5 + T^4) sage: log[2^5] 1/(T^62 + T^61 + T^59 + ... + T^8 + T^6 + T^5) + On the contrary, when ``prec`` is a finite number, all the + required coefficients are computed at once:: + + sage: phi.logarithm(prec=10) + z + (1/(T^2 + T))*z^2 + (1/(T^6 + T^5 + T^3 + T^2))*z^4 + (1/(T^14 + T^13 + T^11 + T^10 + T^7 + T^6 + T^4 + T^3))*z^8 + O(z^10) + Example in higher rank:: sage: A = GF(5)['T'] @@ -317,7 +342,6 @@ def logarithm(self, name='z'): sage: log[2**3] == -1/((T**q - T)*(T**(q**2) - T)*(T**(q**3) - T)) # expected value True """ - L = LazyPowerSeriesRing(self._base, name) q = self._Fq.cardinality() def coeff_log(k): @@ -328,7 +352,13 @@ def coeff_log(k): return self._compute_coefficient_log(v) else: return self._base.zero() - return L(coeff_log, valuation=1) + + if prec is Infinity: + L = LazyPowerSeriesRing(self._base, name) + return L(coeff_log, valuation=1) + else: + L = PowerSeriesRing(self._base, name, default_prec=prec) + return L([0] + [coeff_log(i) for i in range(1, prec)], prec=prec) @cached_method def _compute_goss_polynomial(self, n, q, poly_ring, X): From f182fdab05901ed7ba7c83249c79ba9821f8025a Mon Sep 17 00:00:00 2001 From: Xavier Caruso Date: Fri, 3 Jan 2025 09:47:05 +0100 Subject: [PATCH 2/5] simplify doctest Co-authored-by: Martin Rubey --- .../function_field/drinfeld_modules/charzero_drinfeld_module.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/sage/rings/function_field/drinfeld_modules/charzero_drinfeld_module.py b/src/sage/rings/function_field/drinfeld_modules/charzero_drinfeld_module.py index c69cb6c4dbb..77ec8905aa4 100644 --- a/src/sage/rings/function_field/drinfeld_modules/charzero_drinfeld_module.py +++ b/src/sage/rings/function_field/drinfeld_modules/charzero_drinfeld_module.py @@ -315,7 +315,7 @@ def logarithm(self, prec=Infinity, name='z'): sage: log[2^5] 1/(T^62 + T^61 + T^59 + ... + T^8 + T^6 + T^5) - On the contrary, when ``prec`` is a finite number, all the + If ``prec`` is a finite number, all the required coefficients are computed at once:: sage: phi.logarithm(prec=10) From cb99e9e26d93722f743a4cf1bcd264a628009719 Mon Sep 17 00:00:00 2001 From: Xavier Caruso Date: Fri, 3 Jan 2025 09:47:32 +0100 Subject: [PATCH 3/5] remove useless else in coeff_exp Co-authored-by: Martin Rubey --- .../drinfeld_modules/charzero_drinfeld_module.py | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/src/sage/rings/function_field/drinfeld_modules/charzero_drinfeld_module.py b/src/sage/rings/function_field/drinfeld_modules/charzero_drinfeld_module.py index 77ec8905aa4..d51dae1ba57 100644 --- a/src/sage/rings/function_field/drinfeld_modules/charzero_drinfeld_module.py +++ b/src/sage/rings/function_field/drinfeld_modules/charzero_drinfeld_module.py @@ -356,9 +356,8 @@ def coeff_log(k): if prec is Infinity: L = LazyPowerSeriesRing(self._base, name) return L(coeff_log, valuation=1) - else: - L = PowerSeriesRing(self._base, name, default_prec=prec) - return L([0] + [coeff_log(i) for i in range(1, prec)], prec=prec) + L = PowerSeriesRing(self._base, name, default_prec=prec) + return L([0] + [coeff_log(i) for i in range(1, prec)], prec=prec) @cached_method def _compute_goss_polynomial(self, n, q, poly_ring, X): From 492fcd4a4b8c3d082175dfe24df84158c7eb7aec Mon Sep 17 00:00:00 2001 From: Xavier Caruso Date: Fri, 3 Jan 2025 09:47:46 +0100 Subject: [PATCH 4/5] remove useless else in coeff_log Co-authored-by: Martin Rubey --- .../drinfeld_modules/charzero_drinfeld_module.py | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/src/sage/rings/function_field/drinfeld_modules/charzero_drinfeld_module.py b/src/sage/rings/function_field/drinfeld_modules/charzero_drinfeld_module.py index d51dae1ba57..27a4373bb9a 100644 --- a/src/sage/rings/function_field/drinfeld_modules/charzero_drinfeld_module.py +++ b/src/sage/rings/function_field/drinfeld_modules/charzero_drinfeld_module.py @@ -242,9 +242,8 @@ def coeff_exp(k): if prec is Infinity: L = LazyPowerSeriesRing(self._base, name) return L(coeff_exp, valuation=1) - else: - L = PowerSeriesRing(self._base, name, default_prec=prec) - return L([0] + [coeff_exp(i) for i in range(1,prec)], prec=prec) + L = PowerSeriesRing(self._base, name, default_prec=prec) + return L([0] + [coeff_exp(i) for i in range(1,prec)], prec=prec) @cached_method def _compute_coefficient_log(self, k): From 1fa959b45b95f11465b73ffbc33b934628724587 Mon Sep 17 00:00:00 2001 From: Xavier Caruso Date: Tue, 11 Feb 2025 22:04:30 +0100 Subject: [PATCH 5/5] Update src/sage/rings/function_field/drinfeld_modules/charzero_drinfeld_module.py MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Co-authored-by: Antoine Leudière --- .../drinfeld_modules/charzero_drinfeld_module.py | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/sage/rings/function_field/drinfeld_modules/charzero_drinfeld_module.py b/src/sage/rings/function_field/drinfeld_modules/charzero_drinfeld_module.py index 27a4373bb9a..e9de0b8b1f6 100644 --- a/src/sage/rings/function_field/drinfeld_modules/charzero_drinfeld_module.py +++ b/src/sage/rings/function_field/drinfeld_modules/charzero_drinfeld_module.py @@ -162,7 +162,8 @@ def exponential(self, prec=Infinity, name='z'): - ``prec`` -- an integer or ``Infinity`` (default: ``Infinity``); the precision at which the series is returned; if ``Infinity``, - a lazy power series in returned + a lazy power series in returned, else, a classical power series + is returned. - ``name`` -- string (default: ``'z'``); the name of the generator of the lazy power series ring