class as_function: def __init__(self, C, g): self.curve = C F = C.base_ring n = C.height variable_names = 'x, y' for i in range(n): variable_names += ', z' + str(i) Rxyz = PolynomialRing(F, n+2, variable_names) x, y = Rxyz.gens()[:2] z = Rxyz.gens()[2:] RxyzQ = FractionField(Rxyz) self.function = RxyzQ(g) #self.function = as_reduction(AS, RxyzQ(g)) def __repr__(self): return str(self.function) def __add__(self, other): C = self.curve g1 = self.function g2 = other.function return as_function(C, g1 + g2) def __sub__(self, other): C = self.curve g1 = self.function g2 = other.function return as_function(C, g1 - g2) def __rmul__(self, constant): C = self.curve g = self.function return as_function(C, constant*g) def __mul__(self, other): C = self.curve g1 = self.function g2 = other.function return as_function(C, g1*g2) def __truediv__(self, other): C = self.curve g1 = self.function g2 = other.function return as_function(C, g1/g2) def __pow__(self, exponent): C = self.curve g1 = self.function return as_function(C, g1^(exponent)) def expansion_at_infty(self, i = 0): C = self.curve delta = C.nb_of_pts_at_infty F = C.base_ring x_series = C.x[i] y_series = C.y[i] z_series = C.z[i] n = C.height variable_names = 'x, y' for j in range(n): variable_names += ', z' + str(j) Rxyz = PolynomialRing(F, n+2, variable_names) x, y = Rxyz.gens()[:2] z = Rxyz.gens()[2:] RxyzQ = FractionField(Rxyz) prec = C.prec Rt. = LaurentSeriesRing(F, default_prec=prec) g = self.function g = RxyzQ(g) sub_list = {x : x_series, y : y_series} | {z[j] : z_series[j] for j in range(n)} return g.substitute(sub_list) def group_action(self, ZN_tuple): C = self.curve n = C.height F = C.base_ring variable_names = 'x, y' for j in range(n): variable_names += ', z' + str(j) Rxyz = PolynomialRing(F, n+2, variable_names) x, y = Rxyz.gens()[:2] z = Rxyz.gens()[2:] RxyzQ = FractionField(Rxyz) sub_list = {x : x, y : y} | {z[j] : z[j]+ZN_tuple[j] for j in range(n)} g = self.function return as_function(C, g.substitute(sub_list)) def trace(self): C = self.curve C_super = C.quotient n = C.height F = C.base_ring variable_names = 'x, y' for j in range(n): variable_names += ', z' + str(j) Rxyz = PolynomialRing(F, n+2, variable_names) x, y = Rxyz.gens()[:2] z = Rxyz.gens()[2:] RxyzQ = FractionField(Rxyz) g = self.function g = as_reduction(C, g) result = RxyzQ(0) g_num = Rxyz(numerator(g)) g_den = Rxyz(denominator(g)) z = prod(z[i] for i in range(n))^(p-1) for a in g_num.monomials(): if (z.divides(a)): result += g_num.monomial_coefficient(a)*a/z result /= g_den result = as_reduction(C, result) Rxy. = PolynomialRing(F, 2) Qxy = FractionField(Rxy) return superelliptic_function(C_super, Qxy(result)) def trace2(self): C = self.curve C_super = C.quotient n = C.height F = C.base_ring variable_names = 'x, y' for j in range(n): variable_names += ', z' + str(j) Rxyz = PolynomialRing(F, n+2, variable_names) x, y = Rxyz.gens()[:2] z = Rxyz.gens()[2:] RxyzQ = FractionField(Rxyz) result = as_function(C, 0) G = C.group for a in G: result += self.group_action(a) result = result.function Rxy. = PolynomialRing(F, 2) Qxy = FractionField(Rxy) return superelliptic_function(C_super, Qxy(result)) def valuation(self, i = 0): '''Return valuation at i-th place at infinity.''' return self.expansion_at_infty(i).valuation()