proj home

Files   Classes   Functions   Hierarchy  

gausselim.h

Go to the documentation of this file.
00001 #ifndef GAUSSELIM_H
00002 #define GAUSSELIM_H
00003 
00004 #include <sstream>
00005 using namespace std;
00006 
00007 #include <typedefs.h>
00008 #include <zero.h>
00009 
00033 template< typename T >
00034 class gausselim
00035 {
00036   gausselim() { assert(false); }
00037 public:
00038 
00040   T * mat;
00042   T * row;
00044   uintc dim;  
00045 
00047   gausselim( T * mat_, uintc dim_ )
00048     : mat(mat_), dim(dim_)
00049     { row = new T[dim+1]; }
00051   ~gausselim()
00052     { delete[] row; }
00053 
00056   boolc eval();
00057 
00060   void columnC( T * C ) const;
00061 
00062 
00063   // Possible Individual Operations on the state.
00064 
00066   void rowget( uintc i );
00068   void rowput( uintc i );
00070   void mult(T const alpha);
00071 
00073   void swap( uintc i, uintc k );
00075   void norm( uintc row, uintc col );
00076 
00079   boolc pivot(uintc k);
00080 
00082   void substitute( uintc i );
00083 
00085   operator stringc () const;
00086 };
00087 
00088 
00089 //----------------------------------------------------------
00090 //  Implementation
00091 
00092 
00093 template< typename T >
00094 void gausselim<T>::columnC(T * C) const
00095 {
00096   for (uint i=0; i<dim; ++i)
00097     C[i] = mat[3+i*4];
00098 }
00099 
00100 template< typename T >
00101 boolc gausselim<T>::eval()
00102 {
00103   for (uint i=0; i<dim; ++i)
00104   {
00105     if (pivot(i)==false)
00106       return false;
00107 
00108     substitute(i);
00109   }
00110 
00111   return true;
00112 }
00113 
00114 template< typename T >
00115 void gausselim<T>::substitute( uintc k )
00116 {
00117   norm(k,k);
00118 
00119   rowget(k);
00120   for (uint i=0; i<dim+1; ++i)
00121     row[i] *= -1;
00122 
00123   uint b=0;
00124   T r;
00125 
00126   for (uint i=0; i<dim; ++i)
00127   {
00128     if (i==k)
00129     {
00130       b += (dim+1);
00131       continue;
00132     }
00133 
00134     r = mat[b+k];
00135 
00136     for (uint m=0; m<dim+1; ++m)
00137       mat[b++] += row[m]*r;
00138   }
00139 
00140 }
00141 
00142 template< typename T >
00143 boolc gausselim<T>::pivot( uintc k )
00144 {
00145   assert(k<dim);
00146 
00147   T lgnum = mat[ k*(dim+1) + k ];
00148   T lgnum2 = lgnum*lgnum;
00149   uint lgi = k;
00150   T x;
00151   T x2;
00152   for (uint i=k+1; i<dim; ++i)
00153   {
00154     x = mat[ i*(dim+1) + k ];
00155     x2 = x*x;
00156     if (x2>lgnum2)
00157     {
00158       lgnum2 = x2;
00159       lgnum = x;
00160       lgi = i;
00161     }
00162   }
00163 
00164   if (k!=lgi)
00165     swap(k,lgi);
00166 
00167   if (lgnum2 < zero<T>::val )
00168     return false;
00169 
00170   return true;
00171 }
00172 
00173 template< typename T >
00174 void gausselim<T>::rowget( uintc i )
00175 {
00176   assert(i<dim);
00177 
00178   uint b = i*(dim+1);
00179   for (uint k=0; k<dim+1; ++k)
00180     row[k] = mat[b+k];
00181 } 
00182 
00183 template< typename T >
00184 void gausselim<T>::rowput( uintc i )
00185 {
00186   assert(i<dim);
00187 
00188   uint b = i*(dim+1);
00189   for (uint k=0; k<dim+1; ++k)
00190     mat[b+k] = row[k];
00191 } 
00192 
00193 template< typename T >
00194 void gausselim<T>::mult(T const alpha)
00195 {
00196   for (uint i=0; i<dim+1; ++i)
00197     row[i] *= alpha;
00198 }
00199 
00200 template< typename T >
00201 void gausselim<T>::norm( uintc row, uintc col )
00202 {
00203   assert(row<dim);
00204   assert(col<dim);
00205 
00206   uint b = row*(dim+1);
00207 
00208   T alpha = mat[b+col];
00209   if (alpha==0)
00210     return;
00211 
00212   alpha = 1.0/alpha;
00213 
00214   for (uint i=0; i<dim+1; ++i)
00215     mat[b++] *= alpha;
00216 }
00217 
00218 template< typename T >
00219 void gausselim<T>::swap( uintc i, uintc k )
00220 {
00221   assert(i<dim);
00222   assert(k<dim);
00223 
00224   T t;
00225   uint bi = i*(dim+1);
00226   uint bk = k*(dim+1);
00227   for (uint j=0; j<dim+1; ++j)
00228   {
00229     t = mat[bi];
00230     mat[bi] = mat[bk];
00231     mat[bk] = t;
00232     ++bi;
00233     ++bk;
00234   }
00235 }
00236 
00237 template< typename T >
00238 gausselim<T>::operator stringc () const
00239 {
00240   stringstream ss;
00241   
00242   for (uint i=0; i<dim; ++i)
00243   {
00244     for (uint k=0; k<dim+1; ++k)
00245     {
00246       ss << mat[i*(dim+1)+k] << " ";
00247     }
00248     if (i!=dim-1)
00249       ss << "\n";
00250   }
00251 
00252   return ss.str();
00253 }
00254  
00255 
00256 
00257 #endif
00258 
00259 

Generated on Fri Mar 4 00:49:28 2011 for Chelton Evans Source by  doxygen 1.5.8