From 67c43bf53f572379a7b4aee66decbc0dc2e392e8 Mon Sep 17 00:00:00 2001 From: Joe Rowell Date: Tue, 15 Aug 2023 11:57:03 +0100 Subject: [PATCH 1/6] Add support for converting (integer) numpy arrays to IntegerMatrix. --- src/fpylll/fplll/integer_matrix.pyx | 7 +++++++ src/fpylll/io.pyx | 8 +++++++- src/fpylll/numpy.pyx | 9 +++++++++ 3 files changed, 23 insertions(+), 1 deletion(-) diff --git a/src/fpylll/fplll/integer_matrix.pyx b/src/fpylll/fplll/integer_matrix.pyx index 8764c645..a36cf1d6 100644 --- a/src/fpylll/fplll/integer_matrix.pyx +++ b/src/fpylll/fplll/integer_matrix.pyx @@ -326,6 +326,13 @@ cdef class IntegerMatrix: >>> B[0,0] 1 + IntegerMatrix also supports numpy's integer types:: + >>> import numpy as np + >>> B = np.eye(5, dtype=np.int32) + >>> Bfpy = IntegerMatrix.from_matrix(B) + >>> Bfpy[0,0] + 1 + """ self._type = check_int_type(int_type) diff --git a/src/fpylll/io.pyx b/src/fpylll/io.pyx index 0d4f9d8c..9f595abf 100644 --- a/src/fpylll/io.pyx +++ b/src/fpylll/io.pyx @@ -11,6 +11,7 @@ from .gmp.mpz cimport mpz_t, mpz_set_si, mpz_set from cpython.version cimport PY_MAJOR_VERSION from fplll.fplll cimport FT_DEFAULT, FT_DOUBLE, FT_LONG_DOUBLE, FT_DPE, FT_MPFR from fplll.fplll cimport ZT_MPZ, ZT_LONG +from fpylll.numpy import is_numpy_integer IF HAVE_QD: from fpylll.fplll.fplll cimport FT_DD, FT_QD @@ -36,7 +37,7 @@ cdef int assign_Z_NR_mpz(Z_NR[mpz_t]& t, value) except -1: cdef int assign_mpz(mpz_t& t, value) except -1: """ Assign Python integer to Z_NR[mpz_t] - """ + """ if isinstance(value, int) and PY_MAJOR_VERSION == 2: mpz_set_si(t, PyInt_AS_LONG(value)) return 0 @@ -49,6 +50,11 @@ cdef int assign_mpz(mpz_t& t, value) except -1: mpz_set_pylong(t, value) return 0 + if is_numpy_integer(value): + value = long(value) + mpz_set_pylong(t, value) + return 0 + raise NotImplementedError("Type '%s' not supported"%type(value)) cdef object mpz_get_python(mpz_srcptr z): diff --git a/src/fpylll/numpy.pyx b/src/fpylll/numpy.pyx index 84970ba5..9196c66d 100644 --- a/src/fpylll/numpy.pyx +++ b/src/fpylll/numpy.pyx @@ -15,6 +15,7 @@ IF not HAVE_NUMPY: import numpy from numpy.__init__ cimport ndarray # TODO: that __init__ shouldn't be needed +from numpy.__init__ cimport integer as np_integer def _dump_mu(ndarray[double, ndim=2, mode="c"] mu not None, MatGSO M, int kappa, int block_size): u""" @@ -130,3 +131,11 @@ def dump_r(MatGSO M, int kappa, int block_size): r = ndarray(dtype='float64', shape=block_size) _dump_r(r, M, kappa, block_size) return r + +def is_numpy_integer(value): + """ + Return true if value is a numpy integer, false otherwise. + :param value: the value to be checked. + :returns: True if value is a numpy integer, false otherwise. + """ + return isinstance(value, np_integer) From 8b03f1a4090f8ab8e116ab786c7558bc3d70a435 Mon Sep 17 00:00:00 2001 From: Joe Rowell Date: Wed, 16 Aug 2023 11:14:00 +0100 Subject: [PATCH 2/6] Fix compilation issue. --- src/fpylll/io.pyx | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/src/fpylll/io.pyx b/src/fpylll/io.pyx index 9f595abf..f832b713 100644 --- a/src/fpylll/io.pyx +++ b/src/fpylll/io.pyx @@ -11,7 +11,9 @@ from .gmp.mpz cimport mpz_t, mpz_set_si, mpz_set from cpython.version cimport PY_MAJOR_VERSION from fplll.fplll cimport FT_DEFAULT, FT_DOUBLE, FT_LONG_DOUBLE, FT_DPE, FT_MPFR from fplll.fplll cimport ZT_MPZ, ZT_LONG -from fpylll.numpy import is_numpy_integer + +# Note: this uses fpylll's numpy and not the global numpy package. +from numpy import is_numpy_integer IF HAVE_QD: from fpylll.fplll.fplll cimport FT_DD, FT_QD From 8a86183628ae6e680df852e88a78558a5b59cabd Mon Sep 17 00:00:00 2001 From: Joe Rowell Date: Wed, 16 Aug 2023 11:14:05 +0100 Subject: [PATCH 3/6] Add additional test. --- tests/test_numpy.py | 11 +++++++++++ 1 file changed, 11 insertions(+) diff --git a/tests/test_numpy.py b/tests/test_numpy.py index 5ff06381..3e1728d6 100644 --- a/tests/test_numpy.py +++ b/tests/test_numpy.py @@ -36,3 +36,14 @@ def test_dump_r(nrows=10): for i in range(nrows): assert abs(M.get_r(i, i) - r[i]) < 0.001 + + +def test_is_numpy_integer(nrows=10): + if not have_numpy: + return + + import numpy as np + B = np.eye(nrows, dtype=np.int32) + Bfpy = IntegerMatrix.from_matrix(B) + for i in range(nrows): + assert Bfpy[i][i] == 1 From efdd3267edfad935728e362c0babd4bed9872261 Mon Sep 17 00:00:00 2001 From: Joe Rowell Date: Wed, 16 Aug 2023 14:34:16 +0100 Subject: [PATCH 4/6] Add HAVE_NUMPY guards. --- src/fpylll/io.pyx | 12 +++++++----- 1 file changed, 7 insertions(+), 5 deletions(-) diff --git a/src/fpylll/io.pyx b/src/fpylll/io.pyx index f832b713..8ca10b7c 100644 --- a/src/fpylll/io.pyx +++ b/src/fpylll/io.pyx @@ -13,7 +13,8 @@ from fplll.fplll cimport FT_DEFAULT, FT_DOUBLE, FT_LONG_DOUBLE, FT_DPE, FT_MPFR from fplll.fplll cimport ZT_MPZ, ZT_LONG # Note: this uses fpylll's numpy and not the global numpy package. -from numpy import is_numpy_integer +IF HAVE_NUMPY: + from numpy import is_numpy_integer IF HAVE_QD: from fpylll.fplll.fplll cimport FT_DD, FT_QD @@ -52,10 +53,11 @@ cdef int assign_mpz(mpz_t& t, value) except -1: mpz_set_pylong(t, value) return 0 - if is_numpy_integer(value): - value = long(value) - mpz_set_pylong(t, value) - return 0 + IF HAVE_NUMPY: + if is_numpy_integer(value): + value = long(value) + mpz_set_pylong(t, value) + return 0 raise NotImplementedError("Type '%s' not supported"%type(value)) From 9a630b0b1f0641cf81f5541a9c8715a0e8738b14 Mon Sep 17 00:00:00 2001 From: Martin Albrecht Date: Wed, 16 Aug 2023 14:36:49 +0100 Subject: [PATCH 5/6] numpy guard and relative import --- src/fpylll/io.pyx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/fpylll/io.pyx b/src/fpylll/io.pyx index 8ca10b7c..6aec4a49 100644 --- a/src/fpylll/io.pyx +++ b/src/fpylll/io.pyx @@ -14,7 +14,7 @@ from fplll.fplll cimport ZT_MPZ, ZT_LONG # Note: this uses fpylll's numpy and not the global numpy package. IF HAVE_NUMPY: - from numpy import is_numpy_integer + from .numpy import is_numpy_integer IF HAVE_QD: from fpylll.fplll.fplll cimport FT_DD, FT_QD From 21cde28001df7a478fe1342e460253ce19c428f4 Mon Sep 17 00:00:00 2001 From: Joe Rowell Date: Wed, 16 Aug 2023 18:33:07 +0100 Subject: [PATCH 6/6] Remove doctest. It's already covered in tests/test_numpy.py now. --- src/fpylll/fplll/integer_matrix.pyx | 9 ++------- 1 file changed, 2 insertions(+), 7 deletions(-) diff --git a/src/fpylll/fplll/integer_matrix.pyx b/src/fpylll/fplll/integer_matrix.pyx index a36cf1d6..b0682b8a 100644 --- a/src/fpylll/fplll/integer_matrix.pyx +++ b/src/fpylll/fplll/integer_matrix.pyx @@ -326,13 +326,8 @@ cdef class IntegerMatrix: >>> B[0,0] 1 - IntegerMatrix also supports numpy's integer types:: - >>> import numpy as np - >>> B = np.eye(5, dtype=np.int32) - >>> Bfpy = IntegerMatrix.from_matrix(B) - >>> Bfpy[0,0] - 1 - + IntegerMatrix also supports numpy's integer types, if numpy is supported. + See tests/test_numpy.py for example usage. """ self._type = check_int_type(int_type)