views:

113

answers:

1

In Numpy, ix_() is used to grab rows and columns of a matrix, but it doesn't seem to work with sparse matrices. For instance, this code works because it uses a dense matrix:

>>> import numpy as np
>>> x = np.mat([[1,0,3],[0,4,5],[7,8,0]])
>>> print x
[[1 0 3]
 [0 4 5]
 [7 8 0]]
>>> print x[np.ix_([0,2],[0,2])]
[[1 3]
 [7 0]]

I used ix_() to index the elements corresponding with the 0th and 2nd rows and columns which gives the 4 corners of the matrix.

The problem is that ix_ doesn't seem to work with sparse matrices. Continuing from the previous code, I try the following:

>>> import scipy.sparse as sparse
>>> xspar = sparse.csr_matrix(x)
>>> print xspar
  (0, 0) 1
  (0, 2) 3
  (1, 1) 4
  (1, 2) 5
  (2, 0) 7
  (2, 1) 8
>>> print xspar[np.ix_([0,2],[0,2])]

and get a huge error message saying there is this exception:

  File "C:\Python26\lib\site-packages\scipy\sparse\compressed.py", line 138, in check_format
    raise ValueError('data, indices, and indptr should be rank 1')
ValueError: data, indices, and indptr should be rank 1

I have tried this with the other sparse matrix formats provided by SciPy, but none of them seem to work with ix_() though they don't all raise the same exception.

The example I gave used a matrix that wasn't very big or very sparse, but the ones I am dealing with are quite sparse and potentially very large so it doesn't seem prudent to just list off the elements one by one.

Does anyone know a (hopefully easy) way to do this sort of indexing with sparse matrices in SciPy or is this feature just not built into these sparse matrices?

+2  A: 

Try this instead:

>>> print xspar
  (0, 0) 1
  (0, 2) 3
  (1, 1) 4
  (1, 2) 5
  (2, 0) 7
  (2, 1) 8
>>> print xspar[[[0],[2]],[0,2]]
  (0, 0) 1
  (0, 2) 3
  (2, 0) 7

Note the difference with this:

>>> print xspar[[0,2],[0,2]]
  [[1 0]]
Steve
Works like a charm, thanks! Though it appears to work for csc and csr matrices, but not lil matrices - that's enough for me.
Justin Peel
You're welcome!
Steve