Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Computing the nullspace of a moderate matrix blows up RAM #14665

Open
emanuel-sygal opened this issue Apr 27, 2018 · 2 comments
Open

Computing the nullspace of a moderate matrix blows up RAM #14665

emanuel-sygal opened this issue Apr 27, 2018 · 2 comments
Labels

Comments

@emanuel-sygal
Copy link

I am trying to find a basis for the nullspace of some matrix $A$ in sympy of size (384, 120).
When calling
A.nullspace()
The RAM usage keeps rising until it crashes, even on a machine with 400 GB free RAM.

The matrix consists of elements that are just 1,-1,0 and mostly zero.
I create the matix like this:
A = sympy.Matrix(vectors_list)

where every element of vectors_list is a tuple of elements of type sympy.core.numbers.
I tried setting the environment variables
"SYMPY_USE_CACHE", "SYMPY_INT_TRACE" to "no"
and it did not make a change.

I posted here a txt file containing a reproducible matrix with the bug: https://groups.google.com/forum/m/#!topic/sympy/R5DQsaIDJbg

@asmeurer
Copy link
Member

I wasn't able to keyboard interrupt the operation, suggesting it is stuck in a C function somewhere.

@rlamy
Copy link
Member

rlamy commented Apr 27, 2018

The problem is that matrix elements grow to humongous sizes (millions of digits, and probably more).

The following patch makes the problem tractable:

diff --git a/sympy/matrices/matrices.py b/sympy/matrices/matrices.py
index 1dd0867..b64d4f1 100644
--- a/sympy/matrices/matrices.py
+++ b/sympy/matrices/matrices.py
@@ -639,6 +639,7 @@ def _row_reduce(self, iszerofunc, simpfunc, normalize_last=True,
         zero_above : whether entries above the pivot should be zeroed.
             If `zero_above=False`, an echelon matrix will be returned.
         """
+        from sympy.core.numbers import igcd
         rows, cols = self.rows, self.cols
         mat = list(self)
         def get_col(i):
@@ -701,7 +702,8 @@ def cross_cancel(a, i, b, j):
                 if iszerofunc(val):
                     continue
 
-                cross_cancel(pivot_val, row, val, piv_row)
+                g = igcd(pivot_val, val)
+                cross_cancel(pivot_val // g, row, val // g, piv_row)
             piv_row += 1
 
         # normalize each row

The patch is obviously incorrect as it only works for integers, but I guess the idea can be generalised.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Projects
None yet
Development

No branches or pull requests

4 participants