realroot_doc 0.1.1
|
00001 /********************************************************************* 00002 * This file is part of the source code of realroot kernel. * 00003 * Author(s): B. Mourrain, GALAAD, INRIA * 00004 **********************************************************************/ 00006 #ifndef realroot_array_hpp 00007 #define realroot_array_hpp 00008 //------------------------------------------------------------------------ 00009 #include <cassert> 00010 #include <realroot/assign.hpp> 00011 //====================================================================== 00012 namespace mmx { 00013 //====================================================================== 00014 00036 namespace array { 00037 //---------------------------------------------------------------------- 00039 template <class OS, class R> 00040 inline OS & print(OS & os, const R & v) { 00041 os <<"["; 00042 typename R::const_iterator i=v.begin(); 00043 if (v.size()){ 00044 os<<*i; ++i; 00045 for(; i != v.end(); ++i) {os <<", "; os<<*i;} 00046 } 00047 os <<"]"; 00048 return os; 00049 } 00050 //---------------------------------------------------------------------- 00052 template <class OS, class R> 00053 inline OS & print(OS & os, const R & v, unsigned sz) { 00054 os <<"["; 00055 unsigned i=0; 00056 if (sz){ 00057 os<<v[i]; ++i; 00058 for(; i <sz; ++i) os <<","<<v[i]; 00059 } 00060 os <<"]"; 00061 return os; 00062 } 00063 //---------------------------------------------------------------------- 00068 template <class IS, class R> 00069 inline IS & read(IS & is, R & V) { 00070 typedef typename R::size_type size_type; 00071 size_type s; 00072 is >> s; 00073 V.rep().resize(s); 00074 for(size_type i=0; i< s; ++i) is >> V[i]; 00075 return(is); 00076 } 00077 //---------------------------------------------------------------------- 00078 00079 template <class V1, class V2> inline 00080 bool equal_n( const V1& v1, const V2 & v2, int n ) 00081 { 00082 int i=0; 00083 while(i < n && v1[i] == v2[i]) i++; 00084 return i == n; 00085 }; 00086 00088 template <class V1, class V2> inline 00089 bool equal(const V1 & v1, const V2 & v2) 00090 { return (v1.size() == v2.size()) && equal_n(v1,v2,v1.size()); } 00091 00092 00093 //---------------------------------------------------------------------- 00094 template <class V, class C> inline 00095 void init_n(V & a, const C & v, int n ) { 00096 for ( int i = 0; i < n; a[i] = v, i ++ ) {} }; 00097 00099 template <class V, class C> 00100 void set_cst(V & a, const C & v ) { init_n(a,v,(int)a.size()); }; 00101 00102 00103 template <class V, class W> 00104 void set(V & a, const W & b ) {for ( int i = 0; i < (int)a.size(); a[i] = b[i], i ++ ) {} }; 00105 00106 //---------------------------------------------------------------------- 00108 template <class V> 00109 void reverse_n( V & v, int a, int n ) 00110 { 00111 int k = n - a; 00112 for ( int i = 0; i < k/2; std::swap(v[a+i],v[k-1-i]), i ++ ) {} 00113 }; 00114 00115 template <class V> 00116 void reverse( V & v, int n ) { reverse_n( v, 0, n ); }; 00117 00119 template <class V,class I> 00120 void reverse(V & v, I d) { 00121 for(I i=0;i<d/2; std::swap(v[i],v[d-1-i]),++i) {} 00122 } 00123 00124 //---------------------------------------------------------------------- 00125 template<class V, class W> inline 00126 void neg_range( V & r, const W & w, int a, int b ) { 00127 for ( int i = a; i < b; r[i] = -w[i], i++ ) {} 00128 } 00129 template<class V, class W> inline 00130 void neg_range( V & r, int a, int b ) 00131 { for ( int i = a; i < b; r[i] = -r[i], i++ ){} }; 00132 00133 template<class VI> inline 00134 void neg_i( VI a, VI eda ) { for ( ; a != eda; *a = -(*a), a++ ){} }; 00135 template<class VI> inline 00136 void neg_i( VI a, VI eda, VI b ) { for ( ; a != eda; *a = -(*b), a++, b++ ){} }; 00137 template<class V> inline 00138 void neg( V & v ) { neg_i(v.begin(),v.end()); }; 00139 template<class V> inline 00140 void neg( V & a, const V & b ) 00141 { 00142 a.resize( b.size() ); 00143 neg_i( a.begin(), a.end(), b.begin() ); 00144 }; 00145 00146 template<class V, class W> inline 00147 void copy_range( V & v, const W & w, int a, int b ) { for ( int i = a; i < b; v[i] = w[i], i ++ ){} } 00148 template< class V, class W > 00149 void add_n(V & a, const W & b, int n ) {for ( int i = 0; i < n; a[i] += b[i], i ++ ){} } 00150 template<class VI, class WI> 00151 void add_i( VI a, VI ea, WI b ) { for ( ; a != ea; *a += *b, ++a, ++b ){} }; 00152 //---------------------------------------------------------------------- 00154 template <class V, class W> 00155 void add(V & a, const W & b) 00156 { 00157 int asz, bsz; 00158 asz = a.size(), bsz = b.size(); 00159 if ( asz < bsz ) 00160 { 00161 a.resize(bsz); 00162 add_i(a.begin(),a.end(),b.begin()); 00163 copy_range(a,b,asz,bsz); 00164 } 00165 else 00166 { 00167 // PRINT_DEBUG("add"); 00168 add_n(a,b,bsz); 00169 // add_i(a.begin(),a.begin()+bsz,b.begin()); 00170 } 00171 } 00172 00173 template< class V, class W, class X > inline 00174 void add_n(V & a, const W & b, const X& c, int n ) { for ( int i = 0; i < n; a[i] = b[i]+c[i], i ++ ){} }; 00175 00176 //-------------------------------------------------------------------- 00179 template <class V, class W,class X> 00180 void add_g(V & r, const W & a, const X & b) 00181 { 00182 int asz, bsz, rsz; 00183 asz = a.size(), bsz = b.size(), rsz = r.size(); 00184 if ( asz > bsz ) 00185 { 00186 if ( asz > rsz ) r.resize(asz); 00187 add_n(r,a,b,bsz); 00188 copy_range(r,a,bsz,asz); 00189 } 00190 else 00191 { 00192 if ( bsz > rsz ) r.resize(bsz); 00193 add_n(r,a,b,asz); 00194 copy_range(r,b,asz,bsz); 00195 }; 00196 } 00197 //-------------------------------------------------------------------- 00200 template <class V, class W,class X> inline 00201 void add(V & r, const W & a, const X & b) 00202 { 00203 add_g(r,a,b); 00204 } 00205 //-------------------------------------------------------------------- 00208 template <class V> inline 00209 void add(V & r, const V & a, const V & b) 00210 { 00211 if(&r==&a) { add(r,b); return; }; 00212 if(&r==&b) { add(r,a); return; }; 00213 add_g(r,a,b); 00214 } 00215 //==================================================================== 00216 template< class V, class W > 00217 void sub_n(V & a, const W & b, int n ) { for ( int i = 0; i < n; a[i] -= b[i], i ++ ){} }; 00218 00219 //---------------------------------------------------------------------- 00221 template <class V, class W> 00222 void sub(V & a, const W & b) 00223 { 00224 int asz, bsz; 00225 asz = a.size(), bsz = b.size(); 00226 if ( asz < bsz ) 00227 { 00228 a.resize(bsz); 00229 sub_n(a,b,asz); 00230 neg_range(a,b,asz,bsz); 00231 } 00232 else 00233 sub_n(a,b,bsz); 00234 } 00235 //-------------------------------------------------------------------- 00236 template< class V, class W, class X > inline 00237 void sub_n(V & a, const W & b, const X& c, int n ) { for ( int i = 0; i < n; a[i] = b[i]-c[i], i ++ ){} }; 00238 00239 //-------------------------------------------------------------------- 00240 template <class V, class W,class X> 00241 void sub_g(V & r, const W & a, const X & b) 00242 { 00243 int asz, bsz, rsz; 00244 asz = a.size(), bsz = b.size(), rsz = r.size(); 00245 00246 if ( asz > bsz ) 00247 { 00248 if ( asz > rsz ) r.resize(asz); 00249 sub_n(r,a,b,bsz); 00250 copy_range(r,a,bsz,asz); 00251 } 00252 else 00253 { 00254 if ( bsz > rsz ) r.resize(bsz); 00255 sub_n(r,a,b,asz); 00256 neg_range(r,b,asz,bsz); 00257 }; 00258 } 00261 template <class V, class W,class X> 00262 void sub(V & r, const W & a, const X & b) 00263 { 00264 sub_g(r,a,b); 00265 } 00266 //-------------------------------------------------------------------- 00269 template <class V> 00270 void sub(V & r, const V & a, const V & b) 00271 { 00272 if(&r==&a) { sub(r,b); return; }; 00273 // if(&r==&b) { sub(r,a); mul_ext(r,-1); return; }; 00274 sub_g(r,a,b); 00275 } 00276 //---------------------------------------------------------------------- 00277 template<class V, class W> inline 00278 void mul_ext_n( V & a, const W & c, int n ) 00279 { for ( int i = 0; i < n; a[i] = a[i]*c, i ++ ){} }; 00280 template<class V, class W, class S> inline 00281 void mul_ext_n( V & a, const W & b, const S& c, int n ) 00282 { for ( int i = 0; i < n; a[i] = b[i]*c, i++ ){} }; 00283 template<class VI, class W> inline 00284 void mul_ext_i( VI bga, VI eda, const W & c ) 00285 { for ( VI i = bga; i != eda; *i *= c, ++i ){} }; 00286 template<class VI, class VII, class W> inline 00287 void mul_ext_i( VI bga, VI eda, VII bgb, const W & c ) 00288 { for ( VI a = bga; a != eda; *a = *bgb * c, ++bgb, ++a ){} }; 00289 00291 template <class V,class W> 00292 void mul_ext(V & a, const V & b, const W & c) 00293 { 00294 if(&a != &b) { 00295 a.resize( b.size() ); 00296 mul_ext_i(a.begin(),a.end(),b.begin(),c); 00297 } 00298 else 00299 mul_ext_i(a.begin(),a.end(),c); 00300 } 00301 template <class V,class W> 00302 void mul_ext(V & a, const W & c) { 00303 mul_ext_i(a.begin(),a.end(),c); 00304 } 00305 //---------------------------------------------------------------------- 00306 template<class V, class SC> inline 00307 void div_ext_n( V & a, const SC & sc, int n ) 00308 { for ( int i = 0; i < n; a[i] /= sc, i++){} } 00309 template<class V1, class V2, class SC> 00310 void div_ext_n( V1 & a, const V2 & b, const SC& sc, int n ) 00311 { for ( int i = 0; i < n; a[i] = b[i]/sc, i ++ ){} }; 00312 template<class VI, class SC> inline 00313 void div_ext_i( VI bga, VI eda, const SC & sc ) 00314 { for ( ; bga < eda; *bga /= sc, bga++){} } 00315 template<class VI, class SC> inline 00316 void div_ext_i( VI a, VI eda, VI b, const SC & sc ) 00317 { for ( ; a < eda; *a = *b / sc, a++, b ++ ){} }; 00319 template <class V, class SC> 00320 void div_ext( V & a, const V & b, const SC & sc) 00321 { 00322 if(&a != &b) { 00323 a.resize( b.size() ); 00324 div_ext_i(a.begin(),a.end(),b.begin(),sc); 00325 } 00326 else div_ext_i(a.begin(),a.end(),sc); 00327 } 00329 template <class V, class W> 00330 void div_ext(V & a, const W & c) 00331 { div_ext_i(a.begin(),a.end(),c); } 00332 //---------------------------------------------------------------------- 00334 template <class V, class W> 00335 void div(V & a, const W & c) 00336 { 00337 div_ext(a,c); 00338 //W tmp(c); for(typename V::iterator it=a.begin(); it !=a.end(); ++it) (*it)/=tmp; 00339 } 00340 00341 //---------------------------------------------------------------------- 00342 template <class R, class S, class C> inline 00343 void apply_mult(R & result, const S& a, const C & m) 00344 { 00345 typedef typename S::const_iterator const_iterator; 00346 typedef typename R::iterator iterator; 00347 result.resize(a.size()); 00348 const_iterator b=a.begin(); iterator i=result.begin(); 00349 for(; b!=a.end(); ++i, ++b) *i = (*b) * m; 00350 } 00351 //---------------------------------------------------------------------- 00353 template <class C, class R> 00354 C norm(const R & v) 00355 { 00356 C r=0; 00357 for(typename R::const_iterator it=v.begin(); it !=v.end(); ++it) r+=(*it)*(*it); 00358 return sqrt(r); 00359 } 00360 //---------------------------------------------------------------------- 00362 template <class C,class R> 00363 C norm(const R & v, int p) 00364 { 00365 C r=0; 00366 for(typename R::const_iterator it=v.begin(); it !=v.end(); ++it) r+=pow(*it,p); 00367 return pow(r,1/p); 00368 } 00369 //---------------------------------------------------------------------- 00371 template <class R, class S> 00372 typename R::value_type innerprod_n( const S & v, const R & w, unsigned n ) 00373 { 00374 typename R::value_type r = 0; 00375 for ( unsigned i = 0; i < n; r += v[i]*w[i], i++ ) {} 00376 return r; 00377 }; 00378 00379 template <class R, class S> 00380 typename R::value_type innerprod(const S & v, const R & w) 00381 { 00382 typename R::value_type r =0; 00383 for(unsigned int i=0; i <v.size(); i++){r += (v[i]*w[i]);} 00384 return r; 00385 } 00386 //-------------------------------------------------------------------- 00387 template<class R> 00388 typename R::value_type max_abs(const R& v) 00389 { 00390 typename R::value_type r=0; 00391 for(unsigned i=0; i <(unsigned)v.size(); i++) 00392 { 00393 if(r>v[i]) r=v[i]; 00394 else if(r>-v[i]) r=-v[i]; 00395 } 00396 return r; 00397 } 00398 00399 //-------------------------------------------------------------------- 00400 template<class U, class R> 00401 void lcm_denominator(U& r, const R& v) 00402 { 00403 for(unsigned i=0; i <v.size(); i++) 00404 { 00405 r = lcm(r,denominator(v[i])); 00406 } 00407 } 00408 //---------------------------------------------------------------------- 00409 /* Replace R by its reverse */ 00410 template < typename V> inline 00411 void reverse(V & v) 00412 { 00413 unsigned sz = v.size(); 00414 V temp(v); 00415 for (unsigned i = 0; i < sz; ++i) 00416 v[i] = temp[sz-1-i]; 00417 } 00418 00419 template<class Ia, class Ib> inline 00420 void assign_i( Ia a, Ia eda, Ib b ) 00421 { 00422 for ( ; a != eda; ++a, ++b ) let::assign(*a,*b); 00423 }; 00424 00425 template<class Ra, class Rb> inline 00426 void assign( Ra & a, const Rb & b ) 00427 { 00428 a.resize( b.size() ); 00429 assign_i( a.begin(), a.end(), b.begin() ); 00430 }; 00431 00432 template<class R, class C> inline 00433 void vaddsc( R & r, const C & x ) 00434 { for ( typename R::iterator i = r.begin(); i != r.end(); *i += x, i ++ ){} }; 00435 00436 } //CLOSE 00437 00438 00439 //====================================================================== 00440 } // namespace mmx 00441 //====================================================================== 00442 #endif // realroot_LINALG_VECTOR_H 00443