Skip to content

Commit

Permalink
sagemathgh-38808: faster comparison of elliptic-curve morphisms
Browse files Browse the repository at this point in the history
    
Here we add two fast checks to the generic comparison method for
elliptic-curve morphisms that will quickly detect some pairs of unequal
morphisms. In the context of sagemath#35949, this speeds up the following
example from 5.9 seconds to 1.8 seconds:
```sage
sage: E = EllipticCurve(GF((5, 2)), [0,1])
sage: %time _ = list(E.isogenies_degree(27))
```
    
URL: sagemath#38808
Reported by: Lorenz Panny
Reviewer(s): Sebastian A. Spindler
  • Loading branch information
Release Manager committed Oct 19, 2024
2 parents b342274 + 64236f9 commit 63a79f3
Showing 1 changed file with 15 additions and 0 deletions.
15 changes: 15 additions & 0 deletions src/sage/schemes/elliptic_curves/hom.py
Original file line number Diff line number Diff line change
Expand Up @@ -270,6 +270,13 @@ def _richcmp_(self, other, op):
if lx != rx:
return richcmp_not_equal(lx, rx, op)

# Check the Weierstraß scaling factor, too (should be fast)

if op == op_EQ or op == op_NE:
lx, rx = self.scaling_factor(), other.scaling_factor()
if lx != rx:
return richcmp_not_equal(lx, rx, op)

# Do self or other have specialized comparison methods?

ret = self._comparison_impl(self, other, op)
Expand Down Expand Up @@ -1174,20 +1181,28 @@ def compare_via_evaluation(left, right):
F = E.base_ring()

if isinstance(F, finite_field_base.FiniteField):
# check at a random rational point first
P = E.random_point()
if left(P) != right(P):
return False

# then extend to a field with enough points to conclude
q = F.cardinality()
d = left.degree()
e = integer_floor(1 + 2 * (2*d.sqrt() + 1).log(q)) # from Hasse bound
e = next(i for i, n in enumerate(E.count_points(e+1), 1) if n > 4*d)
EE = E.base_extend(F.extension(e, 'U')) # named extension is faster
Ps = EE.gens()
return all(left._eval(P) == right._eval(P) for P in Ps)

elif isinstance(F, number_field_base.NumberField):
for _ in range(100):
P = E.lift_x(F.random_element(), extend=True)
if not P.has_finite_order():
return left._eval(P) == right._eval(P)
else:
assert False, "couldn't find a point of infinite order"

else:
raise NotImplementedError('not implemented for this base field')

Expand Down

0 comments on commit 63a79f3

Please sign in to comment.