New user self-registration is disabled due to spam. Please email eigen-core-team @ lists.tuxfamily.org if you need an account.
Before reporting a bug, please make sure that your Eigen version is up-to-date!
View | Details | Raw Unified | Return to bug 557
Collapse All | Expand All

(-)a/Eigen/src/Core/CoreIterators.h (-6 / +9 lines)
Lines 26-61 namespace Eigen { Link Here
26
template<typename Derived> class DenseBase<Derived>::InnerIterator
26
template<typename Derived> class DenseBase<Derived>::InnerIterator
27
{
27
{
28
  protected:
28
  protected:
29
    typedef typename Derived::Scalar Scalar;
29
    typedef typename Derived::Scalar Scalar;
30
    typedef typename Derived::Index Index;
30
    typedef typename Derived::Index Index;
31
31
32
    enum { IsRowMajor = (Derived::Flags&RowMajorBit)==RowMajorBit };
32
    enum { IsRowMajor = (Derived::Flags&RowMajorBit)==RowMajorBit };
33
  public:
33
  public:
34
    InnerIterator() 
35
      : m_expression(0),m_inner(0),m_outer(0),m_end(0)
36
    {}
34
    EIGEN_STRONG_INLINE InnerIterator(const Derived& expr, Index outer)
37
    EIGEN_STRONG_INLINE InnerIterator(const Derived& expr, Index outer)
35
      : m_expression(expr), m_inner(0), m_outer(outer), m_end(expr.innerSize())
38
      : m_expression(&expr), m_inner(0), m_outer(outer), m_end(expr.innerSize())
36
    {}
39
    {}
37
40
38
    EIGEN_STRONG_INLINE Scalar value() const
41
    EIGEN_STRONG_INLINE Scalar value() const
39
    {
42
    {
40
      return (IsRowMajor) ? m_expression.coeff(m_outer, m_inner)
43
      return (IsRowMajor) ? m_expression->coeff(m_outer, m_inner)
41
                          : m_expression.coeff(m_inner, m_outer);
44
                          : m_expression->coeff(m_inner, m_outer);
42
    }
45
    }
43
46
44
    EIGEN_STRONG_INLINE InnerIterator& operator++() { m_inner++; return *this; }
47
    EIGEN_STRONG_INLINE InnerIterator& operator++() { m_inner++; return *this; }
45
48
46
    EIGEN_STRONG_INLINE Index index() const { return m_inner; }
49
    EIGEN_STRONG_INLINE Index index() const { return m_inner; }
47
    inline Index row() const { return IsRowMajor ? m_outer : index(); }
50
    inline Index row() const { return IsRowMajor ? m_outer : index(); }
48
    inline Index col() const { return IsRowMajor ? index() : m_outer; }
51
    inline Index col() const { return IsRowMajor ? index() : m_outer; }
49
52
50
    EIGEN_STRONG_INLINE operator bool() const { return m_inner < m_end && m_inner>=0; }
53
    EIGEN_STRONG_INLINE operator bool() const { return m_inner < m_end && m_inner>=0; }
51
54
52
  protected:
55
  protected:
53
    const Derived& m_expression;
56
    const Derived* m_expression;
54
    Index m_inner;
57
    Index m_inner;
55
    const Index m_outer;
58
    Index m_outer;
56
    const Index m_end;
59
    Index m_end;
57
};
60
};
58
61
59
} // end namespace Eigen
62
} // end namespace Eigen
60
63
61
#endif // EIGEN_COREITERATORS_H
64
#endif // EIGEN_COREITERATORS_H
(-)a/Eigen/src/SparseCore/MappedSparseMatrix.h (-16 / +40 lines)
Lines 111-179 class MappedSparseMatrix Link Here
111
    /** Empty destructor */
111
    /** Empty destructor */
112
    inline ~MappedSparseMatrix() {}
112
    inline ~MappedSparseMatrix() {}
113
};
113
};
114
114
115
template<typename Scalar, int _Flags, typename _Index>
115
template<typename Scalar, int _Flags, typename _Index>
116
class MappedSparseMatrix<Scalar,_Flags,_Index>::InnerIterator
116
class MappedSparseMatrix<Scalar,_Flags,_Index>::InnerIterator
117
{
117
{
118
  public:
118
  public:
119
    InnerIterator()
120
     : m_matrix(0),
121
       m_outer(-1),
122
       m_id(0),
123
       m_start(0),
124
       m_end(0)
125
     { }
126
     
119
    InnerIterator(const MappedSparseMatrix& mat, Index outer)
127
    InnerIterator(const MappedSparseMatrix& mat, Index outer)
120
      : m_matrix(mat),
128
      : m_matrix(&mat),
121
        m_outer(outer),
129
        m_outer(outer),
122
        m_id(mat.outerIndexPtr()[outer]),
130
        m_id(mat.outerIndexPtr()[outer]),
123
        m_start(m_id),
131
        m_start(m_id),
124
        m_end(mat.outerIndexPtr()[outer+1])
132
        m_end(mat.outerIndexPtr()[outer+1])
125
    {}
133
    {}
126
134
127
    inline InnerIterator& operator++() { m_id++; return *this; }
135
    inline InnerIterator& operator++() { m_id++; return *this; }
128
136
129
    inline Scalar value() const { return m_matrix.valuePtr()[m_id]; }
137
    inline Scalar value() const { return m_matrix->valuePtr()[m_id]; }
130
    inline Scalar& valueRef() { return const_cast<Scalar&>(m_matrix.valuePtr()[m_id]); }
138
    inline Scalar& valueRef() { return const_cast<Scalar&>(m_matrix->valuePtr()[m_id]); }
139
    
140
    // Unlike the pos() function in SparseMatrix::InnerIterator, 
141
    // this is rather an offset than a position 
142
    inline Index pos() const {return (m_id - m_start); }
143
    inline InnerIterator& operator+=(Index offset) {m_id += offset; return *this; }
131
144
132
    inline Index index() const { return m_matrix.innerIndexPtr()[m_id]; }
145
    inline Index index() const { return m_matrix->innerIndexPtr()[m_id]; }
133
    inline Index row() const { return IsRowMajor ? m_outer : index(); }
146
    inline Index row() const { return IsRowMajor ? m_outer : index(); }
134
    inline Index col() const { return IsRowMajor ? index() : m_outer; }
147
    inline Index col() const { return IsRowMajor ? index() : m_outer; }
135
148
136
    inline operator bool() const { return (m_id < m_end) && (m_id>=m_start); }
149
    inline operator bool() const { return (m_id < m_end) && (m_id>=m_start); }
137
150
138
  protected:
151
  protected:
139
    const MappedSparseMatrix& m_matrix;
152
    const MappedSparseMatrix *m_matrix;
140
    const Index m_outer;
153
    Index m_outer;
141
    Index m_id;
154
    Index m_id;
142
    const Index m_start;
155
    Index m_start;
143
    const Index m_end;
156
    Index m_end;
144
};
157
};
145
158
146
template<typename Scalar, int _Flags, typename _Index>
159
template<typename Scalar, int _Flags, typename _Index>
147
class MappedSparseMatrix<Scalar,_Flags,_Index>::ReverseInnerIterator
160
class MappedSparseMatrix<Scalar,_Flags,_Index>::ReverseInnerIterator
148
{
161
{
149
  public:
162
  public:
163
    ReverseInnerIterator()
164
     : m_matrix(0),
165
       m_outer(-1),
166
       m_id(0),
167
       m_start(0),
168
       m_end(0)
169
     { }
170
     
150
    ReverseInnerIterator(const MappedSparseMatrix& mat, Index outer)
171
    ReverseInnerIterator(const MappedSparseMatrix& mat, Index outer)
151
      : m_matrix(mat),
172
      : m_matrix(&mat),
152
        m_outer(outer),
173
        m_outer(outer),
153
        m_id(mat.outerIndexPtr()[outer+1]),
174
        m_id(mat.outerIndexPtr()[outer+1]),
154
        m_start(mat.outerIndexPtr()[outer]),
175
        m_start(mat.outerIndexPtr()[outer]),
155
        m_end(m_id)
176
        m_end(m_id)
156
    {}
177
    {}
157
178
158
    inline ReverseInnerIterator& operator--() { m_id--; return *this; }
179
    inline ReverseInnerIterator& operator--() { m_id--; return *this; }
159
180
160
    inline Scalar value() const { return m_matrix.valuePtr()[m_id-1]; }
181
    inline Scalar value() const { return m_matrix->valuePtr()[m_id-1]; }
161
    inline Scalar& valueRef() { return const_cast<Scalar&>(m_matrix.valuePtr()[m_id-1]); }
182
    inline Scalar& valueRef() { return const_cast<Scalar&>(m_matrix->valuePtr()[m_id-1]); }
162
183
163
    inline Index index() const { return m_matrix.innerIndexPtr()[m_id-1]; }
184
    inline Index pos() const {return (m_end - m_id); }
185
    inline ReverseInnerIterator& operator-=(Index offset) {m_id -= offset; return *this; }
186
    
187
    inline Index index() const { return m_matrix->innerIndexPtr()[m_id-1]; }
164
    inline Index row() const { return IsRowMajor ? m_outer : index(); }
188
    inline Index row() const { return IsRowMajor ? m_outer : index(); }
165
    inline Index col() const { return IsRowMajor ? index() : m_outer; }
189
    inline Index col() const { return IsRowMajor ? index() : m_outer; }
166
190
167
    inline operator bool() const { return (m_id <= m_end) && (m_id>m_start); }
191
    inline operator bool() const { return (m_id <= m_end) && (m_id>m_start); }
168
192
169
  protected:
193
  protected:
170
    const MappedSparseMatrix& m_matrix;
194
    const MappedSparseMatrix* m_matrix;
171
    const Index m_outer;
195
    Index m_outer;
172
    Index m_id;
196
    Index m_id;
173
    const Index m_start;
197
    Index m_start;
174
    const Index m_end;
198
    Index m_end;
175
};
199
};
176
200
177
} // end namespace Eigen
201
} // end namespace Eigen
178
202
179
#endif // EIGEN_MAPPED_SPARSEMATRIX_H
203
#endif // EIGEN_MAPPED_SPARSEMATRIX_H
(-)a/Eigen/src/SparseCore/SparseBlock.h (-15 / +32 lines)
Lines 23-49 public: Link Here
23
protected:
23
protected:
24
    enum { OuterSize = IsRowMajor ? BlockRows : BlockCols };
24
    enum { OuterSize = IsRowMajor ? BlockRows : BlockCols };
25
public:
25
public:
26
    EIGEN_SPARSE_PUBLIC_INTERFACE(BlockType)
26
    EIGEN_SPARSE_PUBLIC_INTERFACE(BlockType)
27
    
27
    
28
    class InnerIterator: public XprType::InnerIterator
28
    class InnerIterator: public XprType::InnerIterator
29
    {
29
    {
30
      public:
30
      public:
31
        inline InnerIterator() 
32
          : XprType::InnerIterator(), m_outer(-1) 
33
        {}
31
        inline InnerIterator(const BlockType& xpr, Index outer)
34
        inline InnerIterator(const BlockType& xpr, Index outer)
32
          : XprType::InnerIterator(xpr.m_matrix, xpr.m_outerStart + outer), m_outer(outer)
35
          : XprType::InnerIterator(xpr.m_matrix, xpr.m_outerStart + outer), m_outer(outer)
33
        {}
36
        {}
34
        inline Index row() const { return IsRowMajor ? m_outer : this->index(); }
37
        inline Index row() const { return IsRowMajor ? m_outer : this->index(); }
35
        inline Index col() const { return IsRowMajor ? this->index() : m_outer; }
38
        inline Index col() const { return IsRowMajor ? this->index() : m_outer; }
36
      protected:
39
      protected:
37
        Index m_outer;
40
        Index m_outer;
38
    };
41
    };
39
    class ReverseInnerIterator: public XprType::ReverseInnerIterator
42
    class ReverseInnerIterator: public XprType::ReverseInnerIterator
40
    {
43
    {
41
      public:
44
      public:
45
        inline ReverseInnerIterator() 
46
          : XprType::ReverseInnerIterator(), m_outer(-1)
47
        {}
42
        inline ReverseInnerIterator(const BlockType& xpr, Index outer)
48
        inline ReverseInnerIterator(const BlockType& xpr, Index outer)
43
          : XprType::ReverseInnerIterator(xpr.m_matrix, xpr.m_outerStart + outer), m_outer(outer)
49
          : XprType::ReverseInnerIterator(xpr.m_matrix, xpr.m_outerStart + outer), m_outer(outer)
44
        {}
50
        {}
45
        inline Index row() const { return IsRowMajor ? m_outer : this->index(); }
51
        inline Index row() const { return IsRowMajor ? m_outer : this->index(); }
46
        inline Index col() const { return IsRowMajor ? this->index() : m_outer; }
52
        inline Index col() const { return IsRowMajor ? this->index() : m_outer; }
47
      protected:
53
      protected:
48
        Index m_outer;
54
        Index m_outer;
49
    };
55
    };
Lines 83-109 public: Link Here
83
    EIGEN_SPARSE_PUBLIC_INTERFACE(BlockType)
89
    EIGEN_SPARSE_PUBLIC_INTERFACE(BlockType)
84
protected:
90
protected:
85
    enum { OuterSize = IsRowMajor ? BlockRows : BlockCols };
91
    enum { OuterSize = IsRowMajor ? BlockRows : BlockCols };
86
public:
92
public:
87
    
93
    
88
    class InnerIterator: public SparseMatrixType::InnerIterator
94
    class InnerIterator: public SparseMatrixType::InnerIterator
89
    {
95
    {
90
      public:
96
      public:
97
        inline InnerIterator() 
98
          : SparseMatrixType::InnerIterator(),m_outer(-1)
99
        {}
91
        inline InnerIterator(const BlockType& xpr, Index outer)
100
        inline InnerIterator(const BlockType& xpr, Index outer)
92
          : SparseMatrixType::InnerIterator(xpr.m_matrix, xpr.m_outerStart + outer), m_outer(outer)
101
          : SparseMatrixType::InnerIterator(xpr.m_matrix, xpr.m_outerStart + outer), m_outer(outer)
93
        {}
102
        {}
94
        inline Index row() const { return IsRowMajor ? m_outer : this->index(); }
103
        inline Index row() const { return IsRowMajor ? m_outer : this->index(); }
95
        inline Index col() const { return IsRowMajor ? this->index() : m_outer; }
104
        inline Index col() const { return IsRowMajor ? this->index() : m_outer; }
96
      protected:
105
      protected:
97
        Index m_outer;
106
        Index m_outer;
98
    };
107
    };
99
    class ReverseInnerIterator: public SparseMatrixType::ReverseInnerIterator
108
    class ReverseInnerIterator: public SparseMatrixType::ReverseInnerIterator
100
    {
109
    {
101
      public:
110
      public:
111
        inline ReverseInnerIterator() 
112
          : SparseMatrixType::ReverseInnerIterator(),m_outer(-1)
113
        {}
102
        inline ReverseInnerIterator(const BlockType& xpr, Index outer)
114
        inline ReverseInnerIterator(const BlockType& xpr, Index outer)
103
          : SparseMatrixType::ReverseInnerIterator(xpr.m_matrix, xpr.m_outerStart + outer), m_outer(outer)
115
          : SparseMatrixType::ReverseInnerIterator(xpr.m_matrix, xpr.m_outerStart + outer), m_outer(outer)
104
        {}
116
        {}
105
        inline Index row() const { return IsRowMajor ? m_outer : this->index(); }
117
        inline Index row() const { return IsRowMajor ? m_outer : this->index(); }
106
        inline Index col() const { return IsRowMajor ? this->index() : m_outer; }
118
        inline Index col() const { return IsRowMajor ? this->index() : m_outer; }
107
      protected:
119
      protected:
108
        Index m_outer;
120
        Index m_outer;
109
    };
121
    };
Lines 338-393 public: Link Here
338
                    m_startCol.value() + (RowsAtCompileTime == 1 ? index : 0));
350
                    m_startCol.value() + (RowsAtCompileTime == 1 ? index : 0));
339
    }
351
    }
340
    
352
    
341
    inline const _MatrixTypeNested& nestedExpression() const { return m_matrix; }
353
    inline const _MatrixTypeNested& nestedExpression() const { return m_matrix; }
342
    
354
    
343
    class InnerIterator : public _MatrixTypeNested::InnerIterator
355
    class InnerIterator : public _MatrixTypeNested::InnerIterator
344
    {
356
    {
345
      typedef typename _MatrixTypeNested::InnerIterator Base;
357
      typedef typename _MatrixTypeNested::InnerIterator Base;
346
      const BlockType& m_block;
358
      const BlockType *m_block;
347
      Index m_end;
359
      Index m_end;
348
    public:
360
    public:
349
361
362
      InnerIterator() 
363
        : Base(), m_block(0),m_end(0)
364
      {}
350
      EIGEN_STRONG_INLINE InnerIterator(const BlockType& block, Index outer)
365
      EIGEN_STRONG_INLINE InnerIterator(const BlockType& block, Index outer)
351
        : Base(block.derived().nestedExpression(), outer + (IsRowMajor ? block.m_startRow.value() : block.m_startCol.value())),
366
        : Base(block.derived().nestedExpression(), outer + (IsRowMajor ? block.m_startRow.value() : block.m_startCol.value())),
352
          m_block(block),
367
          m_block(&block),
353
          m_end(IsRowMajor ? block.m_startCol.value()+block.m_blockCols.value() : block.m_startRow.value()+block.m_blockRows.value())
368
          m_end(IsRowMajor ? block.m_startCol.value()+block.m_blockCols.value() : block.m_startRow.value()+block.m_blockRows.value())
354
      {
369
      {
355
        while( (Base::operator bool()) && (Base::index() < (IsRowMajor ? m_block.m_startCol.value() : m_block.m_startRow.value())) )
370
        while( (Base::operator bool()) && (Base::index() < (IsRowMajor ? m_block->m_startCol.value() : m_block->m_startRow.value())) )
356
          Base::operator++();
371
          Base::operator++();
357
      }
372
      }
358
373
359
      inline Index index()  const { return Base::index() - (IsRowMajor ? m_block.m_startCol.value() : m_block.m_startRow.value()); }
374
      inline Index index()  const { return Base::index() - (IsRowMajor ? m_block->m_startCol.value() : m_block->m_startRow.value()); }
360
      inline Index outer()  const { return Base::outer() - (IsRowMajor ? m_block.m_startRow.value() : m_block.m_startCol.value()); }
375
      inline Index outer()  const { return Base::outer() - (IsRowMajor ? m_block->m_startRow.value() : m_block->m_startCol.value()); }
361
      inline Index row()    const { return Base::row()   - m_block.m_startRow.value(); }
376
      inline Index row()    const { return Base::row()   - m_block->m_startRow.value(); }
362
      inline Index col()    const { return Base::col()   - m_block.m_startCol.value(); }
377
      inline Index col()    const { return Base::col()   - m_block->m_startCol.value(); }
363
      
378
      
364
      inline operator bool() const { return Base::operator bool() && Base::index() < m_end; }
379
      inline operator bool() const { return Base::operator bool() && Base::index() < m_end; }
365
    };
380
    };
366
    class ReverseInnerIterator : public _MatrixTypeNested::ReverseInnerIterator
381
    class ReverseInnerIterator : public _MatrixTypeNested::ReverseInnerIterator
367
    {
382
    {
368
      typedef typename _MatrixTypeNested::ReverseInnerIterator Base;
383
      typedef typename _MatrixTypeNested::ReverseInnerIterator Base;
369
      const BlockType& m_block;
384
      const BlockType* m_block;
370
      Index m_begin;
385
      Index m_begin;
371
    public:
386
    public:
372
387
      ReverseInnerIterator() 
388
        : m_block(0),m_begin(0)
389
      {}
373
      EIGEN_STRONG_INLINE ReverseInnerIterator(const BlockType& block, Index outer)
390
      EIGEN_STRONG_INLINE ReverseInnerIterator(const BlockType& block, Index outer)
374
        : Base(block.derived().nestedExpression(), outer + (IsRowMajor ? block.m_startRow.value() : block.m_startCol.value())),
391
        : Base(block.derived().nestedExpression(), outer + (IsRowMajor ? block.m_startRow.value() : block.m_startCol.value())),
375
          m_block(block),
392
          m_block(*block),
376
          m_begin(IsRowMajor ? block.m_startCol.value() : block.m_startRow.value())
393
          m_begin(IsRowMajor ? block.m_startCol.value() : block.m_startRow.value())
377
      {
394
      {
378
        while( (Base::operator bool()) && (Base::index() >= (IsRowMajor ? m_block.m_startCol.value()+block.m_blockCols.value() : m_block.m_startRow.value()+block.m_blockRows.value())) )
395
        while( (Base::operator bool()) && (Base::index() >= (IsRowMajor ? m_block->m_startCol.value()+block.m_blockCols.value() : m_block->m_startRow.value()+block.m_blockRows.value())) )
379
          Base::operator--();
396
          Base::operator--();
380
      }
397
      }
381
398
382
      inline Index index()  const { return Base::index() - (IsRowMajor ? m_block.m_startCol.value() : m_block.m_startRow.value()); }
399
      inline Index index()  const { return Base::index() - (IsRowMajor ? m_block->m_startCol.value() : m_block->m_startRow.value()); }
383
      inline Index outer()  const { return Base::outer() - (IsRowMajor ? m_block.m_startRow.value() : m_block.m_startCol.value()); }
400
      inline Index outer()  const { return Base::outer() - (IsRowMajor ? m_block->m_startRow.value() : m_block->m_startCol.value()); }
384
      inline Index row()    const { return Base::row()   - m_block.m_startRow.value(); }
401
      inline Index row()    const { return Base::row()   - m_block->m_startRow.value(); }
385
      inline Index col()    const { return Base::col()   - m_block.m_startCol.value(); }
402
      inline Index col()    const { return Base::col()   - m_block->m_startCol.value(); }
386
      
403
      
387
      inline operator bool() const { return Base::operator bool() && Base::index() >= m_begin; }
404
      inline operator bool() const { return Base::operator bool() && Base::index() >= m_begin; }
388
    };
405
    };
389
  protected:
406
  protected:
390
    friend class InnerIterator;
407
    friend class InnerIterator;
391
    friend class ReverseInnerIterator;
408
    friend class ReverseInnerIterator;
392
409
393
    typename XprType::Nested m_matrix;
410
    typename XprType::Nested m_matrix;
(-)a/Eigen/src/SparseCore/SparseCwiseBinaryOp.h (-1 / +2 lines)
Lines 67-83 class CwiseBinaryOpImpl<BinaryOp, Lhs, R Link Here
67
template<typename BinaryOp, typename Lhs, typename Rhs>
67
template<typename BinaryOp, typename Lhs, typename Rhs>
68
class CwiseBinaryOpImpl<BinaryOp,Lhs,Rhs,Sparse>::InnerIterator
68
class CwiseBinaryOpImpl<BinaryOp,Lhs,Rhs,Sparse>::InnerIterator
69
  : public internal::sparse_cwise_binary_op_inner_iterator_selector<BinaryOp,Lhs,Rhs,typename CwiseBinaryOpImpl<BinaryOp,Lhs,Rhs,Sparse>::InnerIterator>
69
  : public internal::sparse_cwise_binary_op_inner_iterator_selector<BinaryOp,Lhs,Rhs,typename CwiseBinaryOpImpl<BinaryOp,Lhs,Rhs,Sparse>::InnerIterator>
70
{
70
{
71
  public:
71
  public:
72
    typedef typename Lhs::Index Index;
72
    typedef typename Lhs::Index Index;
73
    typedef internal::sparse_cwise_binary_op_inner_iterator_selector<
73
    typedef internal::sparse_cwise_binary_op_inner_iterator_selector<
74
      BinaryOp,Lhs,Rhs, InnerIterator> Base;
74
      BinaryOp,Lhs,Rhs, InnerIterator> Base;
75
75
    
76
    InnerIterator() : Base() {} 
76
    EIGEN_STRONG_INLINE InnerIterator(const CwiseBinaryOpImpl& binOp, typename CwiseBinaryOpImpl::Index outer)
77
    EIGEN_STRONG_INLINE InnerIterator(const CwiseBinaryOpImpl& binOp, typename CwiseBinaryOpImpl::Index outer)
77
      : Base(binOp.derived(),outer)
78
      : Base(binOp.derived(),outer)
78
    {}
79
    {}
79
};
80
};
80
81
81
/***************************************************************************
82
/***************************************************************************
82
* Implementation of inner-iterators
83
* Implementation of inner-iterators
83
***************************************************************************/
84
***************************************************************************/
(-)a/Eigen/src/SparseCore/SparseCwiseUnaryOp.h (-7 / +7 lines)
Lines 32-71 class CwiseUnaryOpImpl<UnaryOp,MatrixTyp Link Here
32
32
33
template<typename UnaryOp, typename MatrixType>
33
template<typename UnaryOp, typename MatrixType>
34
class CwiseUnaryOpImpl<UnaryOp,MatrixType,Sparse>::InnerIterator
34
class CwiseUnaryOpImpl<UnaryOp,MatrixType,Sparse>::InnerIterator
35
    : public CwiseUnaryOpImpl<UnaryOp,MatrixType,Sparse>::MatrixTypeIterator
35
    : public CwiseUnaryOpImpl<UnaryOp,MatrixType,Sparse>::MatrixTypeIterator
36
{
36
{
37
    typedef typename CwiseUnaryOpImpl::Scalar Scalar;
37
    typedef typename CwiseUnaryOpImpl::Scalar Scalar;
38
    typedef typename CwiseUnaryOpImpl<UnaryOp,MatrixType,Sparse>::MatrixTypeIterator Base;
38
    typedef typename CwiseUnaryOpImpl<UnaryOp,MatrixType,Sparse>::MatrixTypeIterator Base;
39
  public:
39
  public:
40
40
    InnerIterator() : Base() { }
41
    EIGEN_STRONG_INLINE InnerIterator(const CwiseUnaryOpImpl& unaryOp, typename CwiseUnaryOpImpl::Index outer)
41
    EIGEN_STRONG_INLINE InnerIterator(const CwiseUnaryOpImpl& unaryOp, typename CwiseUnaryOpImpl::Index outer)
42
      : Base(unaryOp.derived().nestedExpression(),outer), m_functor(unaryOp.derived().functor())
42
      : Base(unaryOp.derived().nestedExpression(),outer), m_functor(unaryOp.derived().functor())
43
    {}
43
    {}
44
44
45
    EIGEN_STRONG_INLINE InnerIterator& operator++()
45
    EIGEN_STRONG_INLINE InnerIterator& operator++()
46
    { Base::operator++(); return *this; }
46
    { Base::operator++(); return *this; }
47
47
48
    EIGEN_STRONG_INLINE typename CwiseUnaryOpImpl::Scalar value() const { return m_functor(Base::value()); }
48
    EIGEN_STRONG_INLINE typename CwiseUnaryOpImpl::Scalar value() const { return m_functor(Base::value()); }
49
49
50
  protected:
50
  protected:
51
    const UnaryOp m_functor;
51
    UnaryOp m_functor;
52
  private:
52
  private:
53
    typename CwiseUnaryOpImpl::Scalar& valueRef();
53
    typename CwiseUnaryOpImpl::Scalar& valueRef();
54
};
54
};
55
55
56
template<typename UnaryOp, typename MatrixType>
56
template<typename UnaryOp, typename MatrixType>
57
class CwiseUnaryOpImpl<UnaryOp,MatrixType,Sparse>::ReverseInnerIterator
57
class CwiseUnaryOpImpl<UnaryOp,MatrixType,Sparse>::ReverseInnerIterator
58
    : public CwiseUnaryOpImpl<UnaryOp,MatrixType,Sparse>::MatrixTypeReverseIterator
58
    : public CwiseUnaryOpImpl<UnaryOp,MatrixType,Sparse>::MatrixTypeReverseIterator
59
{
59
{
60
    typedef typename CwiseUnaryOpImpl::Scalar Scalar;
60
    typedef typename CwiseUnaryOpImpl::Scalar Scalar;
61
    typedef typename CwiseUnaryOpImpl<UnaryOp,MatrixType,Sparse>::MatrixTypeReverseIterator Base;
61
    typedef typename CwiseUnaryOpImpl<UnaryOp,MatrixType,Sparse>::MatrixTypeReverseIterator Base;
62
  public:
62
  public:
63
63
    ReverseInnerIterator() : Base() { }
64
    EIGEN_STRONG_INLINE ReverseInnerIterator(const CwiseUnaryOpImpl& unaryOp, typename CwiseUnaryOpImpl::Index outer)
64
    EIGEN_STRONG_INLINE ReverseInnerIterator(const CwiseUnaryOpImpl& unaryOp, typename CwiseUnaryOpImpl::Index outer)
65
      : Base(unaryOp.derived().nestedExpression(),outer), m_functor(unaryOp.derived().functor())
65
      : Base(unaryOp.derived().nestedExpression(),outer), m_functor(unaryOp.derived().functor())
66
    {}
66
    {}
67
67
68
    EIGEN_STRONG_INLINE ReverseInnerIterator& operator--()
68
    EIGEN_STRONG_INLINE ReverseInnerIterator& operator--()
69
    { Base::operator--(); return *this; }
69
    { Base::operator--(); return *this; }
70
70
71
    EIGEN_STRONG_INLINE typename CwiseUnaryOpImpl::Scalar value() const { return m_functor(Base::value()); }
71
    EIGEN_STRONG_INLINE typename CwiseUnaryOpImpl::Scalar value() const { return m_functor(Base::value()); }
Lines 96-146 class CwiseUnaryViewImpl<ViewOp,MatrixTy Link Here
96
96
97
template<typename ViewOp, typename MatrixType>
97
template<typename ViewOp, typename MatrixType>
98
class CwiseUnaryViewImpl<ViewOp,MatrixType,Sparse>::InnerIterator
98
class CwiseUnaryViewImpl<ViewOp,MatrixType,Sparse>::InnerIterator
99
    : public CwiseUnaryViewImpl<ViewOp,MatrixType,Sparse>::MatrixTypeIterator
99
    : public CwiseUnaryViewImpl<ViewOp,MatrixType,Sparse>::MatrixTypeIterator
100
{
100
{
101
    typedef typename CwiseUnaryViewImpl::Scalar Scalar;
101
    typedef typename CwiseUnaryViewImpl::Scalar Scalar;
102
    typedef typename CwiseUnaryViewImpl<ViewOp,MatrixType,Sparse>::MatrixTypeIterator Base;
102
    typedef typename CwiseUnaryViewImpl<ViewOp,MatrixType,Sparse>::MatrixTypeIterator Base;
103
  public:
103
  public:
104
104
    InnerIterator() : Base() { }
105
    EIGEN_STRONG_INLINE InnerIterator(const CwiseUnaryViewImpl& unaryOp, typename CwiseUnaryViewImpl::Index outer)
105
    EIGEN_STRONG_INLINE InnerIterator(const CwiseUnaryViewImpl& unaryOp, typename CwiseUnaryViewImpl::Index outer)
106
      : Base(unaryOp.derived().nestedExpression(),outer), m_functor(unaryOp.derived().functor())
106
      : Base(unaryOp.derived().nestedExpression(),outer), m_functor(unaryOp.derived().functor())
107
    {}
107
    {}
108
108
109
    EIGEN_STRONG_INLINE InnerIterator& operator++()
109
    EIGEN_STRONG_INLINE InnerIterator& operator++()
110
    { Base::operator++(); return *this; }
110
    { Base::operator++(); return *this; }
111
111
112
    EIGEN_STRONG_INLINE typename CwiseUnaryViewImpl::Scalar value() const { return m_functor(Base::value()); }
112
    EIGEN_STRONG_INLINE typename CwiseUnaryViewImpl::Scalar value() const { return m_functor(Base::value()); }
113
    EIGEN_STRONG_INLINE typename CwiseUnaryViewImpl::Scalar& valueRef() { return m_functor(Base::valueRef()); }
113
    EIGEN_STRONG_INLINE typename CwiseUnaryViewImpl::Scalar& valueRef() { return m_functor(Base::valueRef()); }
114
114
115
  protected:
115
  protected:
116
    const ViewOp m_functor;
116
    ViewOp m_functor;
117
};
117
};
118
118
119
template<typename ViewOp, typename MatrixType>
119
template<typename ViewOp, typename MatrixType>
120
class CwiseUnaryViewImpl<ViewOp,MatrixType,Sparse>::ReverseInnerIterator
120
class CwiseUnaryViewImpl<ViewOp,MatrixType,Sparse>::ReverseInnerIterator
121
    : public CwiseUnaryViewImpl<ViewOp,MatrixType,Sparse>::MatrixTypeReverseIterator
121
    : public CwiseUnaryViewImpl<ViewOp,MatrixType,Sparse>::MatrixTypeReverseIterator
122
{
122
{
123
    typedef typename CwiseUnaryViewImpl::Scalar Scalar;
123
    typedef typename CwiseUnaryViewImpl::Scalar Scalar;
124
    typedef typename CwiseUnaryViewImpl<ViewOp,MatrixType,Sparse>::MatrixTypeReverseIterator Base;
124
    typedef typename CwiseUnaryViewImpl<ViewOp,MatrixType,Sparse>::MatrixTypeReverseIterator Base;
125
  public:
125
  public:
126
126
    ReverseInnerIterator() : Base() { }
127
    EIGEN_STRONG_INLINE ReverseInnerIterator(const CwiseUnaryViewImpl& unaryOp, typename CwiseUnaryViewImpl::Index outer)
127
    EIGEN_STRONG_INLINE ReverseInnerIterator(const CwiseUnaryViewImpl& unaryOp, typename CwiseUnaryViewImpl::Index outer)
128
      : Base(unaryOp.derived().nestedExpression(),outer), m_functor(unaryOp.derived().functor())
128
      : Base(unaryOp.derived().nestedExpression(),outer), m_functor(unaryOp.derived().functor())
129
    {}
129
    {}
130
130
131
    EIGEN_STRONG_INLINE ReverseInnerIterator& operator--()
131
    EIGEN_STRONG_INLINE ReverseInnerIterator& operator--()
132
    { Base::operator--(); return *this; }
132
    { Base::operator--(); return *this; }
133
133
134
    EIGEN_STRONG_INLINE typename CwiseUnaryViewImpl::Scalar value() const { return m_functor(Base::value()); }
134
    EIGEN_STRONG_INLINE typename CwiseUnaryViewImpl::Scalar value() const { return m_functor(Base::value()); }
135
    EIGEN_STRONG_INLINE typename CwiseUnaryViewImpl::Scalar& valueRef() { return m_functor(Base::valueRef()); }
135
    EIGEN_STRONG_INLINE typename CwiseUnaryViewImpl::Scalar& valueRef() { return m_functor(Base::valueRef()); }
136
136
137
  protected:
137
  protected:
138
    const ViewOp m_functor;
138
    ViewOp m_functor;
139
};
139
};
140
140
141
template<typename Derived>
141
template<typename Derived>
142
EIGEN_STRONG_INLINE Derived&
142
EIGEN_STRONG_INLINE Derived&
143
SparseMatrixBase<Derived>::operator*=(const Scalar& other)
143
SparseMatrixBase<Derived>::operator*=(const Scalar& other)
144
{
144
{
145
  for (Index j=0; j<outerSize(); ++j)
145
  for (Index j=0; j<outerSize(); ++j)
146
    for (typename Derived::InnerIterator i(derived(),j); i; ++i)
146
    for (typename Derived::InnerIterator i(derived(),j); i; ++i)
(-)a/Eigen/src/SparseCore/SparseDenseProduct.h (+3 lines)
Lines 107-122 class SparseDenseOuterProduct Link Here
107
    RhsNested m_rhs;
107
    RhsNested m_rhs;
108
};
108
};
109
109
110
template<typename Lhs, typename Rhs, bool Transpose>
110
template<typename Lhs, typename Rhs, bool Transpose>
111
class SparseDenseOuterProduct<Lhs,Rhs,Transpose>::InnerIterator : public _LhsNested::InnerIterator
111
class SparseDenseOuterProduct<Lhs,Rhs,Transpose>::InnerIterator : public _LhsNested::InnerIterator
112
{
112
{
113
    typedef typename _LhsNested::InnerIterator Base;
113
    typedef typename _LhsNested::InnerIterator Base;
114
  public:
114
  public:
115
    InnerIterator()
116
      : Base(),m_outer(-1),m_factor(0)
117
    {}
115
    EIGEN_STRONG_INLINE InnerIterator(const SparseDenseOuterProduct& prod, Index outer)
118
    EIGEN_STRONG_INLINE InnerIterator(const SparseDenseOuterProduct& prod, Index outer)
116
      : Base(prod.lhs(), 0), m_outer(outer), m_factor(prod.rhs().coeff(outer))
119
      : Base(prod.lhs(), 0), m_outer(outer), m_factor(prod.rhs().coeff(outer))
117
    {
120
    {
118
    }
121
    }
119
122
120
    inline Index outer() const { return m_outer; }
123
    inline Index outer() const { return m_outer; }
121
    inline Index row() const { return Transpose ? Base::row() : m_outer; }
124
    inline Index row() const { return Transpose ? Base::row() : m_outer; }
122
    inline Index col() const { return Transpose ? m_outer : Base::row(); }
125
    inline Index col() const { return Transpose ? m_outer : Base::row(); }
(-)a/Eigen/src/SparseCore/SparseMatrix.h (-11 / +25 lines)
Lines 860-937 private: Link Here
860
    RealScalar epsilon;
860
    RealScalar epsilon;
861
  };
861
  };
862
};
862
};
863
863
864
template<typename Scalar, int _Options, typename _Index>
864
template<typename Scalar, int _Options, typename _Index>
865
class SparseMatrix<Scalar,_Options,_Index>::InnerIterator
865
class SparseMatrix<Scalar,_Options,_Index>::InnerIterator
866
{
866
{
867
  public:
867
  public:
868
    InnerIterator()
869
     : m_values(0),m_indices(0),m_outer(-1),m_id(0),m_end(0)
870
     { }
871
     
868
    InnerIterator(const SparseMatrix& mat, Index outer)
872
    InnerIterator(const SparseMatrix& mat, Index outer)
869
      : m_values(mat.valuePtr()), m_indices(mat.innerIndexPtr()), m_outer(outer), m_id(mat.m_outerIndex[outer])
873
      : m_values(mat.valuePtr()+mat.m_outerIndex[outer]), m_indices(mat.innerIndexPtr()+mat.m_outerIndex[outer]), m_outer(outer), m_id(0)
870
    {
874
    {
871
      if(mat.isCompressed())
875
      if(mat.isCompressed())
872
        m_end = mat.m_outerIndex[outer+1];
876
        m_end = mat.m_outerIndex[outer+1]-mat.m_outerIndex[outer];
873
      else
877
      else
874
        m_end = m_id + mat.m_innerNonZeros[outer];
878
        m_end = mat.m_innerNonZeros[outer];
875
    }
879
    }
876
880
877
    inline InnerIterator& operator++() { m_id++; return *this; }
881
    inline InnerIterator& operator++() { m_id++; return *this; }
882
    
883
    inline InnerIterator& operator+=(Index offset) { m_id+=offset; return *this; }
884
    inline Index pos() const { return m_id; }
878
885
879
    inline const Scalar& value() const { return m_values[m_id]; }
886
    inline const Scalar& value() const { return m_values[m_id]; }
880
    inline Scalar& valueRef() { return const_cast<Scalar&>(m_values[m_id]); }
887
    inline Scalar& valueRef() { return const_cast<Scalar&>(m_values[m_id]); }
881
888
882
    inline Index index() const { return m_indices[m_id]; }
889
    inline Index index() const { return m_indices[m_id]; }
883
    inline Index outer() const { return m_outer; }
890
    inline Index outer() const { return m_outer; }
884
    inline Index row() const { return IsRowMajor ? m_outer : index(); }
891
    inline Index row() const { return IsRowMajor ? m_outer : index(); }
885
    inline Index col() const { return IsRowMajor ? index() : m_outer; }
892
    inline Index col() const { return IsRowMajor ? index() : m_outer; }
886
893
887
    inline operator bool() const { return (m_id < m_end); }
894
    inline operator bool() const { return (m_id < m_end); }
888
895
889
  protected:
896
  protected:
890
    const Scalar* m_values;
897
    const Scalar* m_values;
891
    const Index* m_indices;
898
    const Index* m_indices;
892
    const Index m_outer;
899
    Index m_outer;
893
    Index m_id;
900
    Index m_id;
894
    Index m_end;
901
    Index m_end;
895
};
902
};
896
903
904
897
template<typename Scalar, int _Options, typename _Index>
905
template<typename Scalar, int _Options, typename _Index>
898
class SparseMatrix<Scalar,_Options,_Index>::ReverseInnerIterator
906
class SparseMatrix<Scalar,_Options,_Index>::ReverseInnerIterator
899
{
907
{
900
  public:
908
  public:
909
    ReverseInnerIterator()
910
     : m_values(0),m_indices(0),m_outer(-1),m_id(0)
911
     { }
901
    ReverseInnerIterator(const SparseMatrix& mat, Index outer)
912
    ReverseInnerIterator(const SparseMatrix& mat, Index outer)
902
      : m_values(mat.valuePtr()), m_indices(mat.innerIndexPtr()), m_outer(outer), m_start(mat.m_outerIndex[outer])
913
      : m_values(mat.valuePtr()+mat.m_outerIndex[outer]), m_indices(mat.innerIndexPtr()+mat.m_outerIndex[outer]), m_outer(outer)
903
    {
914
    {
904
      if(mat.isCompressed())
915
      if(mat.isCompressed())
905
        m_id = mat.m_outerIndex[outer+1];
916
        m_id = mat.m_outerIndex[outer+1] - mat.m_outerIndex[outer];
906
      else
917
      else
907
        m_id = m_start + mat.m_innerNonZeros[outer];
918
        m_id = mat.m_innerNonZeros[outer];
919
      m_end = m_id;
908
    }
920
    }
909
921
910
    inline ReverseInnerIterator& operator--() { --m_id; return *this; }
922
    inline ReverseInnerIterator& operator--() { --m_id; return *this; }
911
923
    
924
    inline Index pos() const {return m_end - m_id; }
925
    inline ReverseInnerIterator& operator-=(Index offset) { m_id -= offset; return *this; }
926
    
912
    inline const Scalar& value() const { return m_values[m_id-1]; }
927
    inline const Scalar& value() const { return m_values[m_id-1]; }
913
    inline Scalar& valueRef() { return const_cast<Scalar&>(m_values[m_id-1]); }
928
    inline Scalar& valueRef() { return const_cast<Scalar&>(m_values[m_id-1]); }
914
929
915
    inline Index index() const { return m_indices[m_id-1]; }
930
    inline Index index() const { return m_indices[m_id-1]; }
916
    inline Index outer() const { return m_outer; }
931
    inline Index outer() const { return m_outer; }
917
    inline Index row() const { return IsRowMajor ? m_outer : index(); }
932
    inline Index row() const { return IsRowMajor ? m_outer : index(); }
918
    inline Index col() const { return IsRowMajor ? index() : m_outer; }
933
    inline Index col() const { return IsRowMajor ? index() : m_outer; }
919
934
920
    inline operator bool() const { return (m_id > m_start); }
935
    inline operator bool() const { return (m_id > 0); }
921
936
922
  protected:
937
  protected:
923
    const Scalar* m_values;
938
    const Scalar* m_values;
924
    const Index* m_indices;
939
    const Index* m_indices;
925
    const Index m_outer;
940
    const Index m_outer;
926
    Index m_id;
941
    Index m_id;
927
    const Index m_start;
942
    Index m_end;
928
};
943
};
929
930
namespace internal {
944
namespace internal {
931
945
932
template<typename InputIterator, typename SparseMatrixType>
946
template<typename InputIterator, typename SparseMatrixType>
933
void set_from_triplets(const InputIterator& begin, const InputIterator& end, SparseMatrixType& mat, int Options = 0)
947
void set_from_triplets(const InputIterator& begin, const InputIterator& end, SparseMatrixType& mat, int Options = 0)
934
{
948
{
935
  EIGEN_UNUSED_VARIABLE(Options);
949
  EIGEN_UNUSED_VARIABLE(Options);
936
  enum { IsRowMajor = SparseMatrixType::IsRowMajor };
950
  enum { IsRowMajor = SparseMatrixType::IsRowMajor };
937
  typedef typename SparseMatrixType::Scalar Scalar;
951
  typedef typename SparseMatrixType::Scalar Scalar;
(-)a/Eigen/src/SparseCore/SparseTranspose.h (-2 / +3 lines)
Lines 30-59 template<typename MatrixType> class Tran Link Here
30
// a typedef typename TransposeImpl<MatrixType,Sparse>::Index Index;
30
// a typedef typename TransposeImpl<MatrixType,Sparse>::Index Index;
31
// does not fix the issue.
31
// does not fix the issue.
32
// An alternative is to define the nested class in the parent class itself.
32
// An alternative is to define the nested class in the parent class itself.
33
template<typename MatrixType> class TransposeImpl<MatrixType,Sparse>::InnerIterator
33
template<typename MatrixType> class TransposeImpl<MatrixType,Sparse>::InnerIterator
34
  : public _MatrixTypeNested::InnerIterator
34
  : public _MatrixTypeNested::InnerIterator
35
{
35
{
36
    typedef typename _MatrixTypeNested::InnerIterator Base;
36
    typedef typename _MatrixTypeNested::InnerIterator Base;
37
  public:
37
  public:
38
38
    InnerIterator() : Base() { }
39
    
39
    EIGEN_STRONG_INLINE InnerIterator(const TransposeImpl& trans, typename TransposeImpl<MatrixType,Sparse>::Index outer)
40
    EIGEN_STRONG_INLINE InnerIterator(const TransposeImpl& trans, typename TransposeImpl<MatrixType,Sparse>::Index outer)
40
      : Base(trans.derived().nestedExpression(), outer)
41
      : Base(trans.derived().nestedExpression(), outer)
41
    {}
42
    {}
42
    inline typename TransposeImpl<MatrixType,Sparse>::Index row() const { return Base::col(); }
43
    inline typename TransposeImpl<MatrixType,Sparse>::Index row() const { return Base::col(); }
43
    inline typename TransposeImpl<MatrixType,Sparse>::Index col() const { return Base::row(); }
44
    inline typename TransposeImpl<MatrixType,Sparse>::Index col() const { return Base::row(); }
44
};
45
};
45
46
46
template<typename MatrixType> class TransposeImpl<MatrixType,Sparse>::ReverseInnerIterator
47
template<typename MatrixType> class TransposeImpl<MatrixType,Sparse>::ReverseInnerIterator
47
  : public _MatrixTypeNested::ReverseInnerIterator
48
  : public _MatrixTypeNested::ReverseInnerIterator
48
{
49
{
49
    typedef typename _MatrixTypeNested::ReverseInnerIterator Base;
50
    typedef typename _MatrixTypeNested::ReverseInnerIterator Base;
50
  public:
51
  public:
51
52
    ReverseInnerIterator() : Base() { }
52
    EIGEN_STRONG_INLINE ReverseInnerIterator(const TransposeImpl& xpr, typename TransposeImpl<MatrixType,Sparse>::Index outer)
53
    EIGEN_STRONG_INLINE ReverseInnerIterator(const TransposeImpl& xpr, typename TransposeImpl<MatrixType,Sparse>::Index outer)
53
      : Base(xpr.derived().nestedExpression(), outer)
54
      : Base(xpr.derived().nestedExpression(), outer)
54
    {}
55
    {}
55
    inline typename TransposeImpl<MatrixType,Sparse>::Index row() const { return Base::col(); }
56
    inline typename TransposeImpl<MatrixType,Sparse>::Index row() const { return Base::col(); }
56
    inline typename TransposeImpl<MatrixType,Sparse>::Index col() const { return Base::row(); }
57
    inline typename TransposeImpl<MatrixType,Sparse>::Index col() const { return Base::row(); }
57
};
58
};
58
59
59
} // end namespace Eigen
60
} // end namespace Eigen
(-)a/Eigen/src/SparseCore/SparseVector.h (-14 / +20 lines)
Lines 333-406 protected: Link Here
333
    Storage m_data;
333
    Storage m_data;
334
    Index m_size;
334
    Index m_size;
335
};
335
};
336
336
337
template<typename Scalar, int _Options, typename _Index>
337
template<typename Scalar, int _Options, typename _Index>
338
class SparseVector<Scalar,_Options,_Index>::InnerIterator
338
class SparseVector<Scalar,_Options,_Index>::InnerIterator
339
{
339
{
340
  public:
340
  public:
341
    InnerIterator() 
342
      : m_data(0),m_id(0),m_end(0)
343
    {}
341
    InnerIterator(const SparseVector& vec, Index outer=0)
344
    InnerIterator(const SparseVector& vec, Index outer=0)
342
      : m_data(vec.m_data), m_id(0), m_end(static_cast<Index>(m_data.size()))
345
      : m_data(*vec.m_data), m_id(0), m_end(static_cast<Index>(m_data.size()))
343
    {
346
    {
344
      EIGEN_UNUSED_VARIABLE(outer);
347
      EIGEN_UNUSED_VARIABLE(outer);
345
      eigen_assert(outer==0);
348
      eigen_assert(outer==0);
346
    }
349
    }
347
350
348
    InnerIterator(const internal::CompressedStorage<Scalar,Index>& data)
351
    InnerIterator(const internal::CompressedStorage<Scalar,Index>& data)
349
      : m_data(data), m_id(0), m_end(static_cast<Index>(m_data.size()))
352
      : m_data(*data), m_id(0), m_end(static_cast<Index>(m_data.size()))
350
    {}
353
    {}
351
354
352
    inline InnerIterator& operator++() { m_id++; return *this; }
355
    inline InnerIterator& operator++() { m_id++; return *this; }
353
356
354
    inline Scalar value() const { return m_data.value(m_id); }
357
    inline Scalar value() const { return m_data->value(m_id); }
355
    inline Scalar& valueRef() { return const_cast<Scalar&>(m_data.value(m_id)); }
358
    inline Scalar& valueRef() { return const_cast<Scalar&>(m_data->value(m_id)); }
356
359
357
    inline Index index() const { return m_data.index(m_id); }
360
    inline Index index() const { return m_data->index(m_id); }
358
    inline Index row() const { return IsColVector ? index() : 0; }
361
    inline Index row() const { return IsColVector ? index() : 0; }
359
    inline Index col() const { return IsColVector ? 0 : index(); }
362
    inline Index col() const { return IsColVector ? 0 : index(); }
360
363
361
    inline operator bool() const { return (m_id < m_end); }
364
    inline operator bool() const { return (m_id < m_end); }
362
365
363
  protected:
366
  protected:
364
    const internal::CompressedStorage<Scalar,Index>& m_data;
367
    const internal::CompressedStorage<Scalar,Index>* m_data;
365
    Index m_id;
368
    Index m_id;
366
    const Index m_end;
369
    Index m_end;
367
};
370
};
368
371
369
template<typename Scalar, int _Options, typename _Index>
372
template<typename Scalar, int _Options, typename _Index>
370
class SparseVector<Scalar,_Options,_Index>::ReverseInnerIterator
373
class SparseVector<Scalar,_Options,_Index>::ReverseInnerIterator
371
{
374
{
372
  public:
375
  public:
376
    ReverseInnerIterator()
377
      : m_data(0),m_id(0),m_start(0)
378
    {}
373
    ReverseInnerIterator(const SparseVector& vec, Index outer=0)
379
    ReverseInnerIterator(const SparseVector& vec, Index outer=0)
374
      : m_data(vec.m_data), m_id(static_cast<Index>(m_data.size())), m_start(0)
380
      : m_data(*vec.m_data), m_id(static_cast<Index>(m_data.size())), m_start(0)
375
    {
381
    {
376
      EIGEN_UNUSED_VARIABLE(outer);
382
      EIGEN_UNUSED_VARIABLE(outer);
377
      eigen_assert(outer==0);
383
      eigen_assert(outer==0);
378
    }
384
    }
379
385
380
    ReverseInnerIterator(const internal::CompressedStorage<Scalar,Index>& data)
386
    ReverseInnerIterator(const internal::CompressedStorage<Scalar,Index>& data)
381
      : m_data(data), m_id(static_cast<Index>(m_data.size())), m_start(0)
387
      : m_data(*data), m_id(static_cast<Index>(m_data.size())), m_start(0)
382
    {}
388
    {}
383
389
384
    inline ReverseInnerIterator& operator--() { m_id--; return *this; }
390
    inline ReverseInnerIterator& operator--() { m_id--; return *this; }
385
391
386
    inline Scalar value() const { return m_data.value(m_id-1); }
392
    inline Scalar value() const { return m_data->value(m_id-1); }
387
    inline Scalar& valueRef() { return const_cast<Scalar&>(m_data.value(m_id-1)); }
393
    inline Scalar& valueRef() { return const_cast<Scalar&>(m_data->value(m_id-1)); }
388
394
389
    inline Index index() const { return m_data.index(m_id-1); }
395
    inline Index index() const { return m_data->index(m_id-1); }
390
    inline Index row() const { return IsColVector ? index() : 0; }
396
    inline Index row() const { return IsColVector ? index() : 0; }
391
    inline Index col() const { return IsColVector ? 0 : index(); }
397
    inline Index col() const { return IsColVector ? 0 : index(); }
392
398
393
    inline operator bool() const { return (m_id > m_start); }
399
    inline operator bool() const { return (m_id > m_start); }
394
400
395
  protected:
401
  protected:
396
    const internal::CompressedStorage<Scalar,Index>& m_data;
402
    const internal::CompressedStorage<Scalar,Index>* m_data;
397
    Index m_id;
403
    Index m_id;
398
    const Index m_start;
404
    Index m_start;
399
};
405
};
400
406
401
template<typename Scalar, int _Options, typename _Index>
407
template<typename Scalar, int _Options, typename _Index>
402
template<typename OtherDerived>
408
template<typename OtherDerived>
403
EIGEN_DONT_INLINE SparseVector<Scalar,_Options,_Index>& SparseVector<Scalar,_Options,_Index>::assign(const SparseMatrixBase<OtherDerived>& _other)
409
EIGEN_DONT_INLINE SparseVector<Scalar,_Options,_Index>& SparseVector<Scalar,_Options,_Index>::assign(const SparseMatrixBase<OtherDerived>& _other)
404
{
410
{
405
  const OtherDerived& other(_other.derived());
411
  const OtherDerived& other(_other.derived());
406
  const bool needToTranspose = (Flags & RowMajorBit) != (OtherDerived::Flags & RowMajorBit);
412
  const bool needToTranspose = (Flags & RowMajorBit) != (OtherDerived::Flags & RowMajorBit);
(-)a/Eigen/src/SparseCore/SparseView.h (-3 / +5 lines)
Lines 53-90 protected: Link Here
53
  typename NumTraits<Scalar>::Real m_epsilon;
53
  typename NumTraits<Scalar>::Real m_epsilon;
54
};
54
};
55
55
56
template<typename MatrixType>
56
template<typename MatrixType>
57
class SparseView<MatrixType>::InnerIterator : public _MatrixTypeNested::InnerIterator
57
class SparseView<MatrixType>::InnerIterator : public _MatrixTypeNested::InnerIterator
58
{
58
{
59
public:
59
public:
60
  typedef typename _MatrixTypeNested::InnerIterator IterBase;
60
  typedef typename _MatrixTypeNested::InnerIterator IterBase;
61
  InnerIterator() : IterBase(),m_view(0)
62
  {}
61
  InnerIterator(const SparseView& view, Index outer) :
63
  InnerIterator(const SparseView& view, Index outer) :
62
  IterBase(view.m_matrix, outer), m_view(view)
64
  IterBase(view.m_matrix, outer), m_view(&view)
63
  {
65
  {
64
    incrementToNonZero();
66
    incrementToNonZero();
65
  }
67
  }
66
68
67
  EIGEN_STRONG_INLINE InnerIterator& operator++()
69
  EIGEN_STRONG_INLINE InnerIterator& operator++()
68
  {
70
  {
69
    IterBase::operator++();
71
    IterBase::operator++();
70
    incrementToNonZero();
72
    incrementToNonZero();
71
    return *this;
73
    return *this;
72
  }
74
  }
73
75
74
  using IterBase::value;
76
  using IterBase::value;
75
77
76
protected:
78
protected:
77
  const SparseView& m_view;
79
  const SparseView* m_view;
78
80
79
private:
81
private:
80
  void incrementToNonZero()
82
  void incrementToNonZero()
81
  {
83
  {
82
    while((bool(*this)) && internal::isMuchSmallerThan(value(), m_view.m_reference, m_view.m_epsilon))
84
    while((bool(*this)) && internal::isMuchSmallerThan(value(), m_view->m_reference, m_view->m_epsilon))
83
    {
85
    {
84
      IterBase::operator++();
86
      IterBase::operator++();
85
    }
87
    }
86
  }
88
  }
87
};
89
};
88
90
89
template<typename Derived>
91
template<typename Derived>
90
const SparseView<Derived> MatrixBase<Derived>::sparseView(const Scalar& m_reference,
92
const SparseView<Derived> MatrixBase<Derived>::sparseView(const Scalar& m_reference,
(-)a/test/CMakeLists.txt (+1 lines)
Lines 224-239 ei_add_test(prec_inverse_4x4) Link Here
224
ei_add_test(vectorwiseop)
224
ei_add_test(vectorwiseop)
225
ei_add_test(special_numbers)
225
ei_add_test(special_numbers)
226
226
227
ei_add_test(simplicial_cholesky)
227
ei_add_test(simplicial_cholesky)
228
ei_add_test(conjugate_gradient)
228
ei_add_test(conjugate_gradient)
229
ei_add_test(bicgstab)
229
ei_add_test(bicgstab)
230
ei_add_test(sparselu)
230
ei_add_test(sparselu)
231
ei_add_test(sparseqr)
231
ei_add_test(sparseqr)
232
ei_add_test(sparse_iterators)
232
233
233
# ei_add_test(denseLM)
234
# ei_add_test(denseLM)
234
235
235
if(QT4_FOUND)
236
if(QT4_FOUND)
236
  ei_add_test(qtvector "" "${QT_QTCORE_LIBRARY}")
237
  ei_add_test(qtvector "" "${QT_QTCORE_LIBRARY}")
237
endif(QT4_FOUND)
238
endif(QT4_FOUND)
238
239
239
ei_add_test(eigen2support)
240
ei_add_test(eigen2support)
(-)a/test/sparse_iterators.cpp (+150 lines)
Line 0 Link Here
1
// This file is part of Eigen, a lightweight C++ template library
2
// for linear algebra.
3
//
4
// Copyright (C) 2013 Désiré Nuentsa <desire.nuentsa_wakam@inria.fr>
5
//
6
// This Source Code Form is subject to the terms of the Mozilla
7
// Public License v. 2.0. If a copy of the MPL was not distributed
8
// with this file, You can obtain one at http://mozilla.org/MPL/2.0/.
9
10
#include "sparse.h"
11
template<typename SparseMatrixType, typename DenseMatrix>
12
void kernel_sparse_iterator(const SparseMatrixType& mS, const DenseMatrix& refS)
13
{
14
  typedef typename SparseMatrixType::Scalar Scalar;
15
  typedef typename SparseMatrixType::Index Index;
16
  typedef Matrix<Scalar,Dynamic,1> DenseVector;
17
  Index size = mS.cols();
18
  
19
  // Test the function pos() of SparseMatrixType::InnerIterator and ReverseInnerTerator
20
  {
21
    VectorXi forward_pos(size); // for the internal positions of iterator
22
    VectorXi reverse_pos(size); // internal positions of reverse iterator
23
    VectorXi forward_idx(size); // Row Index in each column where to stop iterating
24
    VectorXi reverse_idx(size); // Row Index in each column where to stop reverse iterating
25
    for (Index j = 0; j < size; j++)
26
    {
27
      forward_idx(j) = internal::random<int>(0, j);
28
      reverse_idx(j) = internal::random<int>(j, size - 1);
29
    }
30
    
31
    /* Browse the matrix mS until the selected row indexes or the diagonal element
32
     * and save the positions of the iterators for each column
33
     */
34
    forward_pos.setZero(); reverse_pos.setZero();
35
    for (Index j = 0; j < size; j++)
36
    {
37
      for (typename SparseMatrixType::InnerIterator it(mS,j); it; ++it)
38
      {
39
        if ( (it.index() == forward_idx(j)) || (it.index() == j))
40
        {
41
          forward_pos(j) = it.pos();
42
          forward_idx(j) = it.index();
43
          break;
44
        }
45
      }
46
      for (typename SparseMatrixType::ReverseInnerIterator r_it(mS, j); r_it; --r_it)
47
      {
48
        if ( (r_it.index() == reverse_idx(j)) || (r_it.index() == j))
49
        {
50
          reverse_pos(j) = r_it.pos();
51
          reverse_idx(j) = r_it.index();
52
          break;
53
        }
54
      }
55
    }
56
    // Get the values of refS and mS in the saved positions
57
    DenseVector refdS(size), refsS(size);
58
    for(Index j = 0; j < size; ++j) refdS(j) = refS.coeffByOuterInner(j,forward_idx(j));
59
    //refS.coeffByOuterInner(j,forward_idx(j))
60
    for (Index j = 0; j < size; ++j)
61
    {
62
      typename SparseMatrixType::InnerIterator it(mS, j);
63
      it += forward_pos(j);
64
      refsS(j) = it.value();
65
    }
66
    
67
    VERIFY_IS_APPROX(refdS, refsS);
68
    
69
    for(Index j = 0; j < size; ++j) refdS(j) = refS.coeffByOuterInner(j,reverse_idx(j));
70
    for (Index j = 0; j < size; ++j)
71
    {
72
      typename SparseMatrixType::ReverseInnerIterator it(mS, j);
73
      it -= reverse_pos(j);
74
      refsS(j) = it.value();
75
    }
76
    VERIFY_IS_APPROX(refdS, refsS);
77
  }
78
  
79
  /* Test copy constructors 
80
   * for SparseMatrix::InnerIterator
81
   * and SparseMatrix::ReverseInnerIterator
82
   */
83
  {
84
    Index c = internal::random<int>(0, size - 1);
85
    Index r1 = internal::random<int>(0, c);
86
    typename SparseMatrixType::InnerIterator it(mS, c);
87
    //Iterate until mS(r,c) if it exists otherwise mS(c, c)
88
    for (; it; ++it) 
89
    {
90
      if ( (it.index() == r1) || (it.index() == c))
91
      {
92
        r1 = it.index(); // Save the row index effectively found
93
        break;
94
      }
95
    }
96
    //Copy the constructor
97
    typename SparseMatrixType::InnerIterator itc(it);
98
    VERIFY_IS_EQUAL(itc.value(), refS.coeffByOuterInner(c, r1));
99
    //Same stuffs with ReverseInnerTerator
100
    Index r2 = internal::random<int>(c, size - 1);
101
    typename SparseMatrixType::ReverseInnerIterator r_it(mS, c);
102
    for (; r_it; --r_it)
103
    {
104
      if ( (r_it.index() == r2) || (r_it.index() == c))
105
      {
106
        r2 = r_it.index();
107
        break;
108
      }
109
    }
110
    typename SparseMatrixType::ReverseInnerIterator r_itc(r_it);
111
    VERIFY_IS_EQUAL(r_itc.value(), refS.coeffByOuterInner(c, r2));
112
  }
113
}
114
115
116
template <typename SparseMatrixType>
117
void sparse_iterator()
118
{
119
  typedef typename SparseMatrixType::Index Index;
120
  typedef typename SparseMatrixType::Scalar Scalar;
121
  typedef Matrix<Scalar,Dynamic, Dynamic, SparseMatrixType::Flags&RowMajor ? RowMajor : ColMajor > DenseMatrix;
122
  
123
  // Generate the matrices 
124
  Index n = 100;
125
  const Index size  = internal::random<int>(1,n);
126
  DenseMatrix refS(size,size);
127
  SparseMatrixType mS(size, size);
128
  double density = (std::max)(8./(size*size), 0.1);
129
  initSparse<Scalar>(density, refS, mS, ForceNonZeroDiag);
130
  
131
  // Test with the full matrix 
132
  kernel_sparse_iterator(mS, refS);
133
  const Index r = internal::random<int>(0, n/2);
134
  
135
  // Test with the block matrices
136
  //  kernel_sparse_iterator(mS.topLeftCorner(r, r), refS.topLeftCorner(r,r));
137
  //   kernel_sparse_iterator(mS.bottomRightCorner(r, r), refS.bottomRightCorner(r,r));
138
  // Test with the mapped sparse matrix ... applicable ??
139
}
140
141
void test_sparse_iterators()
142
{
143
  for (int i = 0; i < g_repeat; i++) 
144
  {
145
    CALL_SUBTEST_1( (sparse_iterator<SparseMatrix<double, ColMajor> >()) );
146
    CALL_SUBTEST_1( (sparse_iterator<SparseMatrix<double, RowMajor> >()) );
147
    CALL_SUBTEST_2( (sparse_iterator<SparseMatrix<std::complex<double>, ColMajor> >()) );
148
    CALL_SUBTEST_2( (sparse_iterator<SparseMatrix<std::complex<double>, RowMajor> >()) );
149
  }
150
}
(-)a/unsupported/Eigen/src/SparseExtra/DynamicSparseMatrix.h (-2 / +8 lines)
Lines 320-357 template<typename _Scalar, int _Options, Link Here
320
#   endif
320
#   endif
321
 };
321
 };
322
322
323
template<typename Scalar, int _Options, typename _Index>
323
template<typename Scalar, int _Options, typename _Index>
324
class DynamicSparseMatrix<Scalar,_Options,_Index>::InnerIterator : public SparseVector<Scalar,_Options,_Index>::InnerIterator
324
class DynamicSparseMatrix<Scalar,_Options,_Index>::InnerIterator : public SparseVector<Scalar,_Options,_Index>::InnerIterator
325
{
325
{
326
    typedef typename SparseVector<Scalar,_Options,_Index>::InnerIterator Base;
326
    typedef typename SparseVector<Scalar,_Options,_Index>::InnerIterator Base;
327
  public:
327
  public:
328
    InnerIterator() 
329
      : Base(),m_outer(-1)
330
    {}
328
    InnerIterator(const DynamicSparseMatrix& mat, Index outer)
331
    InnerIterator(const DynamicSparseMatrix& mat, Index outer)
329
      : Base(mat.m_data[outer]), m_outer(outer)
332
      : Base(mat.m_data[outer]), m_outer(outer)
330
    {}
333
    {}
331
334
332
    inline Index row() const { return IsRowMajor ? m_outer : Base::index(); }
335
    inline Index row() const { return IsRowMajor ? m_outer : Base::index(); }
333
    inline Index col() const { return IsRowMajor ? Base::index() : m_outer; }
336
    inline Index col() const { return IsRowMajor ? Base::index() : m_outer; }
334
337
335
  protected:
338
  protected:
336
    const Index m_outer;
339
    Index m_outer;
337
};
340
};
338
341
339
template<typename Scalar, int _Options, typename _Index>
342
template<typename Scalar, int _Options, typename _Index>
340
class DynamicSparseMatrix<Scalar,_Options,_Index>::ReverseInnerIterator : public SparseVector<Scalar,_Options,_Index>::ReverseInnerIterator
343
class DynamicSparseMatrix<Scalar,_Options,_Index>::ReverseInnerIterator : public SparseVector<Scalar,_Options,_Index>::ReverseInnerIterator
341
{
344
{
342
    typedef typename SparseVector<Scalar,_Options,_Index>::ReverseInnerIterator Base;
345
    typedef typename SparseVector<Scalar,_Options,_Index>::ReverseInnerIterator Base;
343
  public:
346
  public:
347
    ReverseInnerIterator() 
348
      : Base(),m_outer(-1)
349
    {}
344
    ReverseInnerIterator(const DynamicSparseMatrix& mat, Index outer)
350
    ReverseInnerIterator(const DynamicSparseMatrix& mat, Index outer)
345
      : Base(mat.m_data[outer]), m_outer(outer)
351
      : Base(mat.m_data[outer]), m_outer(outer)
346
    {}
352
    {}
347
353
348
    inline Index row() const { return IsRowMajor ? m_outer : Base::index(); }
354
    inline Index row() const { return IsRowMajor ? m_outer : Base::index(); }
349
    inline Index col() const { return IsRowMajor ? Base::index() : m_outer; }
355
    inline Index col() const { return IsRowMajor ? Base::index() : m_outer; }
350
356
351
  protected:
357
  protected:
352
    const Index m_outer;
358
    Index m_outer;
353
};
359
};
354
360
355
} // end namespace Eigen
361
} // end namespace Eigen
356
362
357
#endif // EIGEN_DYNAMIC_SPARSEMATRIX_H
363
#endif // EIGEN_DYNAMIC_SPARSEMATRIX_H

Return to bug 557