Skip to content

Instantly share code, notes, and snippets.

@TheBlupper
Last active June 6, 2024 09:10
Show Gist options
  • Save TheBlupper/e88ca6c1f13ee8bbfd0f7c2598b6a75a to your computer and use it in GitHub Desktop.
Save TheBlupper/e88ca6c1f13ee8bbfd0f7c2598b6a75a to your computer and use it in GitHub Desktop.
Approximate closest vector solver. Despite running the whole of LLL it's way faster than the common Gram-Schmidt version since Sage rationals are so slow...
def cvp_coords(B, t, reduce=True):
'''
Returns both the (approximate) closest vector
to t and its coordinates in the lattice B
'''
t = vector(ZZ, t)
if reduce: B, R = B.LLL(transformation=True)
else: R = identity_matrix(ZZ, B.nrows())
# an LLL reduced basis is ordered
# by increasing norm
S = B[-1].norm().round()+1
L = block_matrix([
[B, 0],
[matrix(t), S]
])
L, U = L.LLL(transformation=True)
for u, v in zip(U, L):
if abs(u[-1]) == 1:
# *u[-1] cancels the sign to be positive
# just in case
return t - v[:-1]*u[-1], -u[:-1]*u[-1]*R
raise ValueError("babai failed? plz msg @blupper on discord (unless you didn't reduce?)")
def cvp(B, t, reduce=True):
return cvp_coords(B, t, reduce)[0]
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment