CPPLapack
 All Classes Files Functions Variables Friends
dssmatrix-misc.hpp
Go to the documentation of this file.
00001 //=============================================================================
00002 /*! clear all the matrix data and set the sizes 0 */
00003 inline void dssmatrix::clear()
00004 {VERBOSE_REPORT;
00005   n =0;
00006   data.clear();
00007   line.clear();
00008 }
00009 
00010 //=============================================================================
00011 /*! change the matrix into a zero matrix */
00012 inline dssmatrix& dssmatrix::zero()
00013 {VERBOSE_REPORT;
00014   data.resize(0);
00015   for(long i=0; i<n; i++){ line[i].resize(0); }
00016   return *this;
00017 }
00018 
00019 //=============================================================================
00020 /*! change sign(+/-) of the matrix */
00021 inline void dssmatrix::chsign()
00022 {VERBOSE_REPORT;
00023   for(std::vector<dcomponent>::iterator it=data.begin(); it!=data.end(); it++){
00024     it->v =-it->v;
00025   }
00026 }
00027 
00028 //=============================================================================
00029 /*! make a deep copy of the matrix */
00030 inline void dssmatrix::copy(const dssmatrix& mat)
00031 {VERBOSE_REPORT;
00032   n =mat.n;
00033   data =mat.data;
00034   line =mat.line;
00035 }
00036 
00037 //=============================================================================
00038 /*! make a shallow copy of the matrix\n
00039   This function is not designed to be used in project codes. */
00040 inline void dssmatrix::shallow_copy(const _dssmatrix& mat)
00041 {VERBOSE_REPORT;
00042   data.clear();
00043   line.clear();
00044   
00045   n =mat.n;
00046   data.swap(mat.data);
00047   line.swap(mat.line);
00048   
00049   mat.nullify();
00050 }
00051 
00052 //=============================================================================
00053 /*! resize the matrix */
00054 inline dssmatrix& dssmatrix::resize(const long& _n, const long _c, const long _l)
00055 {VERBOSE_REPORT;
00056 #ifdef  CPPL_DEBUG
00057   if( _n<0 || _c<0 || _l<0 ){
00058     ERROR_REPORT;
00059     std::cerr << "Matrix sizes, the length of arrays, and line size must be positive integers. " << std::endl
00060               << "Your input was (" << _n << "," << _c << "," << _l << ")." << std::endl;
00061     exit(1);
00062   }
00063 #endif//CPPL_DEBUG
00064   
00065   n =_n;
00066   data.resize(0);
00067   data.reserve(_c);
00068   line.resize(n);
00069   for(long i=0; i<n; i++){
00070     line[i].resize(0); 
00071     line[i].reserve(_l);
00072   }
00073   
00074   return *this;
00075 }
00076 
00077 //=============================================================================
00078 /*! stretch the matrix size */
00079 inline void dssmatrix::stretch(const long& dn)
00080 {VERBOSE_REPORT;
00081 #ifdef  CPPL_DEBUG
00082   if( n+dn<0 ){
00083     ERROR_REPORT;
00084     std::cerr << "The new matrix size must be larger than zero." << std::endl
00085               << "Your input was (" << dn << ")." << std::endl;
00086     exit(1);
00087   }
00088 #endif//CPPL_DEBUG
00089   
00090   //////// zero ////////
00091   if(dn==0){ return; }
00092 
00093   //////// non-zero ////////
00094   n +=dn;
00095   
00096   if(dn<0){
00097     //// delete components over the new size ////
00098     for(std::vector<dcomponent>::reverse_iterator it=data.rbegin(); it!=data.rend(); it++){
00099       if( long(it->i)>=n ){ del(data.rend()-it-1); }
00100     }
00101     //// shrink line ////
00102     for(long i=0; i<-dn; i++){
00103       line.pop_back();
00104     }
00105   }
00106   else{//dn>0
00107     //// expand line ////
00108     for(long i=0; i<dn; i++){
00109       line.push_back( std::vector<uint32_t>(0) );
00110     }
00111   }
00112 }
00113 
00114 //=============================================================================
00115 /*! check if the component is listed */
00116 inline bool dssmatrix::isListed(const long& i, const long& j) const
00117 {VERBOSE_REPORT;
00118 #ifdef  CPPL_DEBUG
00119   if( i<0 || j<0 || n<=i || n<=j ){
00120     ERROR_REPORT;
00121     std::cerr << "The required component is out of the matrix size." << std::endl
00122               << "Your input was (" << i << "," << j << ")." << std::endl;
00123     exit(1);
00124   }
00125 #endif//CPPL_DEBUG
00126   
00127   const uint32_t ii(std::max(i,j)), jj(std::min(i,j));
00128   for(std::vector<uint32_t>::const_iterator p=line[ii].begin(); p!=line[ii].end(); p++){
00129     if(data[*p].i==ii && data[*p].j==jj){ return 1; }
00130   }
00131   
00132   return 0;
00133 }
00134 
00135 //=============================================================================
00136 /*! return the element number of the component */
00137 inline long dssmatrix::number(const long& i, const long& j) const
00138 {VERBOSE_REPORT;
00139 #ifdef  CPPL_DEBUG
00140   if( i<0 || j<0 || n<=i || n<=j ){
00141     ERROR_REPORT;
00142     std::cerr << "The required component is out of the matrix size." << std::endl
00143               << "Your input was (" << i << "," << j << ")." << std::endl;
00144     exit(1);
00145   }
00146 #endif//CPPL_DEBUG
00147   
00148   const uint32_t ii(std::max(i,j)), jj(std::min(i,j));
00149   for(std::vector<uint32_t>::const_iterator p=line[ii].begin(); p!=line[ii].end(); p++){
00150     if(data[*p].i==ii && data[*p].j==jj){ return *p; }
00151   }
00152   
00153   return -1;
00154 }
00155 
00156 ///////////////////////////////////////////////////////////////////////////////
00157 ///////////////////////////////////////////////////////////////////////////////
00158 ///////////////////////////////////////////////////////////////////////////////
00159 
00160 //=============================================================================
00161 /*! get row of the matrix */
00162 inline _drovector dssmatrix::row(const long& _m) const
00163 {VERBOSE_REPORT;
00164 #ifdef  CPPL_DEBUG
00165   if( _m<0 || _m>m ){
00166     ERROR_REPORT;
00167     std::cerr << "Input row number must be between 0 and " << m << "." << std::endl
00168               << "Your input was " << _m << "." << std::endl;
00169     exit(1);
00170   }
00171 #endif//CPPL_DEBUG
00172   
00173   drovector vec(n);
00174   vec.zero();
00175   for(std::vector<uint32_t>::const_iterator p=line[_m].begin(); p!=line[_m].end(); p++){
00176     if(long(data[*p].i)==_m){
00177       vec(data[*p].j) =data[*p].v;
00178     }
00179     else{
00180       vec(data[*p].i) =data[*p].v;
00181     }
00182   }
00183   return _(vec);
00184 }
00185 
00186 //=============================================================================
00187 /*! get column of the matrix */
00188 inline _dcovector dssmatrix::col(const long& _n) const
00189 {VERBOSE_REPORT;
00190 #ifdef  CPPL_DEBUG
00191   if( _n<0 || _n>n ){
00192     ERROR_REPORT;
00193     std::cerr << "Input row number must be between 0 and " << n << "." << std::endl
00194               << "Your input was " << _n << "." << std::endl;
00195     exit(1);
00196   }
00197 #endif//CPPL_DEBUG
00198   
00199   dcovector vec(m);
00200   vec.zero();
00201   for(std::vector<uint32_t>::const_iterator p=line[_n].begin(); p!=line[_n].end(); p++){
00202     if(long(data[*p].i)==_n){
00203       vec(data[*p].j) =data[*p].v;
00204     }
00205     else{
00206       vec(data[*p].i) =data[*p].v;
00207     }
00208   }
00209   return _(vec);
00210 }
00211 
00212 ///////////////////////////////////////////////////////////////////////////////
00213 ///////////////////////////////////////////////////////////////////////////////
00214 ///////////////////////////////////////////////////////////////////////////////
00215 
00216 //=============================================================================
00217 /*! erase components less than DBL_MIN */
00218 inline void dssmatrix::diet(const double eps)
00219 {VERBOSE_REPORT;
00220   for(std::vector<dcomponent>::reverse_iterator it=data.rbegin(); it!=data.rend(); it++){
00221     if( fabs(it->v)<eps ){ del(data.rend()-it-1); }
00222   }
00223 }
00224 
00225 //=============================================================================
00226 /*! reorder components so that all diagonal componets are placed in front */
00227 inline long dssmatrix::diag_front()
00228 {VERBOSE_REPORT;
00229   //////// set initial dsize ////////
00230   long dsize(0);
00231   for(std::vector<dcomponent>::iterator it=data.begin(); it!=data.end(); it++){
00232     if(it->i==it->j){ dsize++; }
00233     else{ break; }
00234   }
00235   
00236   //////// swapping loop ////////
00237   for(std::vector<dcomponent>::reverse_iterator it=data.rbegin(); it!=data.rend()-dsize; it++){
00238     if(it->i==it->j){//is diag
00239       long c(data.rend()-it-1);//current it's index
00240       long i(data[dsize].i), j(data[dsize].j), k(it->i);
00241       //// search (k,k) line ////
00242       for(std::vector<uint32_t>::iterator p=line[k].begin(); p!=line[k].end(); p++){
00243         if(long(data[*p].i)==k && long(data[*p].j)==k){ *p=dsize; }
00244       }
00245       //// search (i,j) line ////
00246       for(std::vector<uint32_t>::iterator p=line[i].begin(); p!=line[i].end(); p++){
00247         if(long(*p)==dsize){ *p=c; }
00248       }
00249       //// search (j,i) line ////
00250       if(i!=j){
00251         for(std::vector<uint32_t>::iterator p=line[j].begin(); p!=line[j].end(); p++){
00252           if(long(*p)==dsize){ *p=c; }
00253         }
00254       }
00255       else{//i==j
00256         it--;
00257       }
00258       //// swap ////
00259       std::swap(data[dsize],data[c]);
00260       //// update ////
00261       dsize++;
00262     }
00263   }
00264   
00265   return dsize;
00266 }
00267 
00268 //=============================================================================
00269 /*! reorder components */
00270 inline void dssmatrix::reorder(const bool mode)
00271 {VERBOSE_REPORT;
00272   //// sort data ////
00273   if(mode==0){
00274     std::sort(data.begin(), data.end(), dcomponent::ilt);
00275   }
00276   else{
00277     std::sort(data.begin(), data.end(), dcomponent::jlt);
00278   }
00279   //// rebuild line ////
00280   rebuild();
00281 }
00282 
00283 //=============================================================================
00284 /*! rebuild line */
00285 inline void dssmatrix::rebuild()
00286 {VERBOSE_REPORT;
00287   //// clear line ////
00288   for(long i=0; i<n; i++){ line[i].resize(0); }
00289   
00290   //// build line ////
00291   uint32_t c(0);
00292   for(std::vector<dcomponent>::iterator it=data.begin(); it!=data.end(); it++){
00293     line[it->i].push_back(c);
00294     if( (it->i) != (it->j) ){
00295       line[it->j].push_back(c);
00296     }
00297     c++;
00298   }
00299 }
00300 
00301 ///////////////////////////////////////////////////////////////////////////////
00302 ///////////////////////////////////////////////////////////////////////////////
00303 ///////////////////////////////////////////////////////////////////////////////
00304 
00305 //=============================================================================
00306 /*! health checkup */
00307 inline void dssmatrix::checkup()
00308 {VERBOSE_REPORT;
00309   //////// write ////////
00310   for(std::vector<dcomponent>::const_iterator it=data.begin(); it!=data.end(); it++){
00311     std::cerr << "array[" << it-data.begin() << "] = (" << it->i << "," << it->j << ") = " << it->v << std::endl;
00312   }
00313   std::cerr << std::endl;
00314   
00315   for(long i=0; i<n; i++){
00316     std::cerr << "line[" << i << "] =" << std::flush;
00317     for(unsigned long k=0; k<line[i].size(); k++){
00318       std::cerr << " " << line[i][k] << std::flush;
00319     }
00320     std::cerr << std::endl;
00321   }
00322   std::cerr << std::endl;
00323   
00324   //////// Elements ////////
00325   for(std::vector<dcomponent>::const_iterator it=data.begin(); it!=data.end(); it++){
00326     //// m bound ////
00327     if(long(it->i)>=n){
00328       ERROR_REPORT;
00329       std::cerr << "The indx of the " << it-data.begin() << "th element is out of the matrix size." << std::endl
00330                 << "Its i index was " << it->i << "." << std::endl;
00331       exit(1);
00332     }
00333     
00334     //// n bound ////
00335     if(long(it->j)>=n){
00336       ERROR_REPORT;
00337       std::cerr << "The jndx of the " << it-data.begin() << "th element is out of the matrix size." << std::endl
00338                 << "Its j index was " << it->j << "." << std::endl;
00339       exit(1);
00340     }
00341     
00342     //// double-listed ////
00343     for(std::vector<dcomponent>::const_iterator IT=it+1; IT!=data.end(); IT++){
00344       if( it->i==IT->i && it->j==IT->j ){
00345         ERROR_REPORT;
00346         std::cerr << "The (" << it->i << ", " << it->j << ") component is double-listed at the " << it-data.begin() << "th and the" << IT-data.begin() << "the elements."<< std::endl;
00347         exit(1);
00348       }
00349     }
00350   }
00351   
00352   //////// NOTE ////////
00353   std::cerr << "# [NOTE]@dssmatrix::checkup(): This symmetric sparse matrix is fine." << std::endl;
00354 }
00355 
00356 ///////////////////////////////////////////////////////////////////////////////
00357 ///////////////////////////////////////////////////////////////////////////////
00358 ///////////////////////////////////////////////////////////////////////////////
00359 
00360 //=============================================================================
00361 /*! swap two matrices */
00362 inline void swap(dssmatrix& A, dssmatrix& B)
00363 {VERBOSE_REPORT;
00364   std::swap(A.n,B.n);
00365   std::swap(A.data,B.data);
00366   std::swap(A.line,B.line);
00367 }
00368 
00369 //=============================================================================
00370 /*! convert user object to smart-temporary object */
00371 inline _dssmatrix _(dssmatrix& mat)
00372 {VERBOSE_REPORT;
00373   _dssmatrix newmat;
00374   
00375   //////// shallow copy ////////
00376   newmat.n =mat.n;
00377   std::swap(newmat.data,mat.data);
00378   std::swap(newmat.line,mat.line);
00379   
00380   //////// nullify ////////
00381   mat.n =0;
00382   
00383   return newmat;
00384 }
 All Classes Files Functions Variables Friends