find.h 2.6 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495
  1. #ifndef IGL_FIND_H
  2. #define IGL_FIND_H
  3. #define EIGEN_YES_I_KNOW_SPARSE_MODULE_IS_NOT_STABLE_YET
  4. #include <Eigen/Dense>
  5. #include <Eigen/Sparse>
  6. namespace igl
  7. {
  8. // Find the non-zero entries and there respective indices in a sparse matrix.
  9. // Like matlab's [I,J,V] = find(X)
  10. //
  11. // Templates:
  12. // T should be a eigen sparse matrix primitive type like int or double
  13. // Input:
  14. // X m by n matrix whose entries are to be found
  15. // Outputs:
  16. // I nnz vector of row indices of non zeros entries in X
  17. // J nnz vector of column indices of non zeros entries in X
  18. // V nnz vector of type T non-zeros entries in X
  19. //
  20. template <typename T>
  21. inline void find(
  22. const Eigen::SparseMatrix<T>& X,
  23. Eigen::Matrix<int,Eigen::Dynamic,1> & I,
  24. Eigen::Matrix<int,Eigen::Dynamic,1> & J,
  25. Eigen::Matrix<T,Eigen::Dynamic,1> & V);
  26. // Find the non-zero entries and there respective indices in a sparse vector.
  27. // Similar to matlab's [I,J,V] = find(X), but instead of [I,J] being
  28. // subscripts into X, since X is a vector we just return I, a list of indices
  29. // into X
  30. //
  31. // Templates:
  32. // T should be a eigen sparse matrix primitive type like int or double
  33. // Input:
  34. // X vector whose entries are to be found
  35. // Outputs:
  36. // I nnz vector of indices of non zeros entries in X
  37. // V nnz vector of type T non-zeros entries in X
  38. template <typename T>
  39. inline void find(
  40. const Eigen::SparseVector<T>& X,
  41. Eigen::Matrix<int,Eigen::Dynamic,1> & I,
  42. Eigen::Matrix<T,Eigen::Dynamic,1> & V);
  43. }
  44. // Implementation
  45. #include "verbose.h"
  46. template <typename T>
  47. inline void igl::find(
  48. const Eigen::SparseMatrix<T>& X,
  49. Eigen::Matrix<int,Eigen::Dynamic,1> & I,
  50. Eigen::Matrix<int,Eigen::Dynamic,1> & J,
  51. Eigen::Matrix<T,Eigen::Dynamic,1> & V)
  52. {
  53. // Resize outputs to fit nonzeros
  54. I.resize(X.nonZeros());
  55. J.resize(X.nonZeros());
  56. V.resize(X.nonZeros());
  57. int i = 0;
  58. // Iterate over outside
  59. for(int k=0; k<X.outerSize(); ++k)
  60. {
  61. // Iterate over inside
  62. for(typename Eigen::SparseMatrix<T>::InnerIterator it (X,k); it; ++it)
  63. {
  64. V(i) = it.value();
  65. I(i) = it.row();
  66. J(i) = it.col();
  67. i++;
  68. }
  69. }
  70. }
  71. template <typename T>
  72. inline void igl::find(
  73. const Eigen::SparseVector<T>& X,
  74. Eigen::Matrix<int,Eigen::Dynamic,1> & I,
  75. Eigen::Matrix<T,Eigen::Dynamic,1> & V)
  76. {
  77. // Resize outputs to fit nonzeros
  78. I.resize(X.nonZeros());
  79. V.resize(X.nonZeros());
  80. int i = 0;
  81. // loop over non-zeros
  82. for(typename Eigen::SparseVector<T>::InnerIterator it(X); it; ++it)
  83. {
  84. I(i) = it.index();
  85. V(i) = it.value();
  86. i++;
  87. }
  88. }
  89. #endif