Main Page   Namespace List   Class Hierarchy   Alphabetical List   Compound List   File List   Namespace Members   Compound Members  

SparseRowMatrix.h

00001 /****************************************************************************
00002  *                                                                          *
00003  *  Program: FDDlib                                                         *
00004  *  Version: 1.1                                                            *
00005  *                                                                          *
00006  *  Copyright (C) 2002 - 2004 by Eric Miller and Dana Brooks                *
00007  *  All rights reserved.                                                    *
00008  *                                                                          *
00009  *  This software is Version 1.1 of the fddlib tomography toolbox.          *
00010  *  It is not to be redistributed or used for any commercial purpose        *
00011  *  without the prior written consent of the authors and Northeastern       *
00012  *  University.                                                             *
00013  *                                                                          *
00014  *  This software is provided as is, and any express or implied warranties, *
00015  *  including but not limited to the implied warranty of merchantability    *
00016  *  and the implied warranty of fitness for a particular purpose, are dis-  *
00017  *  claimed.  In no event shall the authors or Northeastern University be   *
00018  *  liable for any direct, indirect, incidental, special, exemplary, or     *
00019  *  consequential damages (including but not limited to procurement of      * 
00020  *  substitute goods or services; loss of use, data, or profits; or busi-   *
00021  *  ness interruption) however caused and on any theory of liability,       *
00022  *  whether in contract, strict liability, or tort (including negligence or *
00023  *  otherwise) arising in any way from the use of this software, even if    *
00024  *  advised of the possibility of such damage.                              *
00025  *                                                                          *
00026  *  Portions of this code benefit from ideas from Kyle Guilbert, Greg       *
00027  *  Boverman, Derek Uluski, David Kaeli, and Jennifer Black                 *
00028  *                                                                          *
00029  ****************************************************************************/
00030 
00031 #ifndef _SparseRowMatrix_H_
00032 #define _SparseRowMatrix_H_
00033 
00034 #include <stdlib.h>
00035 #include <stdio.h>
00036 #include <string>
00037 #include "Matrix.h"
00038 #include "RealVector.h"
00039 
00040 namespace FDDlib {
00041 
00048 template <class T>
00049 struct SparseRowEntry
00050 {
00052   int column;
00054   T   val;
00055 };
00056 
00065 template<class T>
00066 class SparseRowMatrix : public Matrix<T>
00067 {
00068 protected:
00070   int              MaxRows_;
00072   int              EntriesPerRow_;
00074   int*             NumCols_;
00076   SparseRowEntry<T>*        Entries_;
00077 
00078 public:
00080   SparseRowMatrix();
00081   
00083   SparseRowMatrix(int maxrows, int max_per_row);
00084   
00086   SparseRowMatrix(const SparseRowMatrix<T>& SRM);
00087   
00089   virtual ~SparseRowMatrix();
00090 
00092   virtual SparseRowMatrix<T>& operator=(const SparseRowMatrix<T>& SRM);
00093 
00095   virtual void init(int maxrows, int max_per_row);
00096 
00098   virtual void deallocate();
00099 
00103   virtual T val(int row, int col) const;
00104 
00106   virtual int getEntriesPerRow() const;
00107 
00109   virtual SparseRowEntry<T>* getRowEntry(int row) const;
00110 
00112   virtual int getCol(int row, int n) const;
00113 
00117   virtual int getCol(int row, int n, T& v) const;
00118 
00120   virtual int getNumCols(int row) const;
00121 
00123   virtual int getNumCols() const;
00124 
00126   virtual int getNumRows() const;
00127 
00131   virtual void set(int row, int col, T val) throw(std::string);
00132 
00136   template<class Vector>
00137   Vector operator*(const Vector& m) const;
00138   
00140   RealVector<T> getRow(int row) const;
00141 
00143   RealVector<T> getColumn(int col) const;
00144 
00145 };
00146 
00147 
00148 template <class T>
00149 SparseRowMatrix<T>::SparseRowMatrix()
00150 {
00151   MaxRows_ = 0;
00152   EntriesPerRow_ = 0;
00153   NumCols_ = (int*) NULL;
00154   Entries_ = (SparseRowEntry<T>*) NULL;
00155 }
00156 
00157 template <class T>
00158 SparseRowMatrix<T>::SparseRowMatrix(int maxrows,
00159                                             int max_per_row)
00160 {
00161   MaxRows_ = maxrows;
00162   EntriesPerRow_ = max_per_row;
00163   NumCols_ = new int[MaxRows_];
00164   Entries_ = new SparseRowEntry<T>[MaxRows_*EntriesPerRow_];
00165   for (int i = 0; i < MaxRows_; i++)
00166   {
00167     NumCols_[i] = 0;
00168   }
00169 }
00170 
00171 template<class T>
00172 SparseRowMatrix<T>::SparseRowMatrix(const SparseRowMatrix<T>& ESR)
00173 {
00174   int       i;
00175   SparseRowEntry<T>* s, *d;
00176 
00177   MaxRows_ =  ESR.getNumRows();
00178   EntriesPerRow_ = ESR.getEntriesPerRow();
00179   NumCols_ = new int[MaxRows_];
00180   Entries_ = new SparseRowEntry<T>[MaxRows_*EntriesPerRow_];
00181   for (i = 0; i < MaxRows_; i++)
00182   {
00183     s = ESR.getRowEntry(i);
00184     d = getRowEntry(i);
00185     NumCols_[i] = ESR.getNumCols(i);
00186     for (j = 0; j < EntriesPerRow_; j++)
00187     {
00188       d[j].column = s[j].column;
00189       d[j].val = s[j].val;
00190     }
00191   }
00192 }
00193 
00194 template<class T>
00195 SparseRowMatrix<T>& SparseRowMatrix<T>::operator=(const SparseRowMatrix<T>& ESR)
00196 {
00197   int       i, j;
00198   SparseRowEntry<T>* s, *d;
00199 
00200   if (getNumRows() > 0)
00201   {
00202     delete[] NumCols_;
00203     delete[] Entries_;
00204   }
00205   
00206   MaxRows_ = ESR.getNumRows();
00207   EntriesPerRow_ = ESR.getEntriesPerRow();
00208 
00209   NumCols_ = new int[ESR.getNumRows()];
00210   Entries_ = new SparseRowEntry<T>[MaxRows_*EntriesPerRow_];
00211   for (i = 0; i < MaxRows_; i++)
00212   {
00213     s = ESR.getRowEntry(i);
00214     d = getRowEntry(i);
00215     NumCols_[i] = ESR.getNumCols(i);
00216     for (j = 0; j < NumCols_[i]; j++)
00217     {
00218       d[j].column = s[j].column;
00219       d[j].val = s[j].val;
00220     }
00221   }
00222 
00223   return *this;
00224 }
00225 
00226 template <class T>
00227 void SparseRowMatrix<T>::init(int maxrows, int max_per_row)
00228 {
00229   MaxRows_ = maxrows;
00230   EntriesPerRow_ = max_per_row;
00231 
00232   if (NumCols_ != (int*) NULL)
00233     delete[] NumCols_;
00234 
00235   if (Entries_ != (SparseRowEntry<T>*) NULL)
00236       delete[] Entries_;
00237 
00238   NumCols_ = new int[MaxRows_];
00239   Entries_ = new SparseRowEntry<T>[MaxRows_*EntriesPerRow_];
00240   for (int i = 0; i < MaxRows_; i++)
00241   {
00242     NumCols_[i] = 0;
00243   }
00244 }
00245 
00246 template<class T>
00247 SparseRowMatrix<T>::~SparseRowMatrix()
00248 {
00249   if (Entries_ != (SparseRowEntry<T>*) NULL)
00250     delete[] Entries_;
00251 
00252   if (NumCols_ != (int*) NULL)
00253     delete[] NumCols_;
00254 }
00255 
00256 template<class T>
00257 void SparseRowMatrix<T>::deallocate()
00258 {
00259   if (Entries_ != (SparseRowEntry<T>*) NULL)
00260     delete[] Entries_;
00261 
00262   if (NumCols_ != (int*) NULL)
00263     delete[] NumCols_;
00264 
00265   Entries_ = (SparseRowEntry<T>*) NULL;
00266   NumCols_ = (int*) NULL;
00267   MaxRows_ = 0;
00268   EntriesPerRow_ = 0;
00269 }
00270 
00271 
00272 template<class T>
00273 inline T SparseRowMatrix<T>::val(int row, int col) const
00274 {
00275   int i;
00276 
00277   for (i = 0; i < NumCols_[row]; i++)
00278   {
00279     if (Entries_[row*EntriesPerRow_ + i].column == col)
00280       return Entries_[row*EntriesPerRow_ + i].val;
00281   }
00282   return 0;
00283 }
00284 
00285 template<class T>
00286 inline int SparseRowMatrix<T>::getEntriesPerRow() const
00287 {
00288   return EntriesPerRow_;
00289 }
00290 
00291 
00292 template<class T>
00293 inline SparseRowEntry<T>* SparseRowMatrix<T>::getRowEntry(int r) const
00294 {
00295   return (Entries_ + r*EntriesPerRow_);
00296 }
00297 
00298 
00299 template<class T>
00300 inline int SparseRowMatrix<T>::getCol(int row, int n) const
00301 {
00302   return (Entries_[row*EntriesPerRow_ + n].column);
00303 }
00304 
00305 
00306 template<class T>
00307 inline int SparseRowMatrix<T>::getCol(int row, int n, T& v) const
00308 {
00309   v = Entries_[row*EntriesPerRow_ + n].val;
00310   return (Entries_[row*EntriesPerRow_ + n].column);
00311 }
00312 
00313 
00314 template<class T>
00315 inline int SparseRowMatrix<T>::getNumCols(int row) const
00316 {
00317   // if we used the default constructor NumCols will be null.
00318   if (NumCols_ == (int*)NULL)
00319     return 0;
00320     
00321   return  NumCols_[row];
00322 }
00323 
00324 template<class T>
00325 inline int SparseRowMatrix<T>::getNumCols() const
00326 {
00327   int i, j;
00328 
00329   int col;
00330 
00331   // Find the maximum column index of all the rows
00332   int maxcol = 0;
00333 
00334   for (i = 0; i < getNumRows(); i++)
00335   {
00336     for (j = 0; j < getNumCols(i); j++)
00337     {
00338       col = getCol(i, j);
00339       if (col > maxcol)
00340       maxcol = col;
00341     }
00342   }
00343 
00344   return maxcol+1;
00345 }
00346 
00347 template<class T>
00348 inline int SparseRowMatrix<T>::getNumRows() const
00349 {
00350   return MaxRows_;
00351 }
00352 
00353 
00354 template<class T>
00355 inline void SparseRowMatrix<T>::set(int row, int col, T val) throw(std::string)
00356 {
00357   int       i;
00358   SparseRowEntry<T>* ep;
00359   
00360   // this will likely prevent a segfault
00361   if (row < 0 || col < 0)
00362     throw std::string("SRM::set: negative row or column parameter");
00363   
00364   ep = getRowEntry(row);
00365   for (i = 0; i < NumCols_[row]; i++)
00366   {
00367     if (ep->column == col)
00368       break;
00369     ep++;
00370   }
00371   if (ep - getRowEntry(row) >= EntriesPerRow_)
00372     throw std::string("SRM::set: hit max number of entries per row");
00373   if (ep - getRowEntry(row) == NumCols_[row])
00374     (NumCols_[row])++;
00375 
00376   ep->val = val;
00377   ep->column = col;
00378 }
00379 
00380 
00381 template<class T>
00382 template<class Vector>
00383 inline Vector SparseRowMatrix<T>::operator*(const Vector& m) const
00384 {
00385   int       i;
00386   int       j;
00387   T         rv;
00388   int       cols;
00389   SparseRowEntry<T>* ep;
00390 
00391   Vector ret(MaxRows_);
00392   for (i = 0; i < MaxRows_; i++)
00393   {
00394     rv = (T) 0;
00395     cols = NumCols_[i];
00396     ep = getRowEntry(i);
00397     for (j = 0; j < cols; j++)
00398     {
00399       rv += m(ep->column) * (ep->val);
00400       ep++;
00401     }
00402     ret(i) = rv;
00403   }
00404 
00405   return ret;
00406 }
00407 
00408 template<class T>
00409 RealVector<T> SparseRowMatrix<T>::getRow(int row) const
00410 {
00411   int i;
00412   const int numcols = getNumCols();
00413   RealVector<T> ret(numcols);
00414   
00415   for(i=0;i<numcols;i++)
00416     ret.set(i,val(row,i));
00417   
00418   return ret;
00419 }
00420 
00421 template<class T>
00422 RealVector<T> SparseRowMatrix<T>::getColumn(int col) const
00423 {
00424   int i;
00425   RealVector<T> ret(MaxRows_);
00426   
00427   for(i=0;i<MaxRows_;i++)
00428     ret.set(i,val(i,col));
00429     
00430   return ret;
00431 }
00432 
00433 } // end namespace
00434 #endif

Generated on Mon Aug 30 15:41:07 2004 for FDDLib by doxygen1.2.18