00001 /* 00002 ------------------------------------------------------------------- 00003 00004 Copyright (C) 2006, 2007, 2008, Andrew W. Steiner 00005 00006 This file is part of O2scl. 00007 00008 O2scl is free software; you can redistribute it and/or modify 00009 it under the terms of the GNU General Public License as published by 00010 the Free Software Foundation; either version 3 of the License, or 00011 (at your option) any later version. 00012 00013 O2scl is distributed in the hope that it will be useful, 00014 but WITHOUT ANY WARRANTY; without even the implied warranty of 00015 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00016 GNU General Public License for more details. 00017 00018 You should have received a copy of the GNU General Public License 00019 along with O2scl. If not, see <http://www.gnu.org/licenses/>. 00020 00021 ------------------------------------------------------------------- 00022 */ 00023 #ifndef O2SCL_VECTOR_H 00024 #define O2SCL_VECTOR_H 00025 00026 /** \file vector.h 00027 \brief File for generic vector functions 00028 00029 For overloaded operators involving vectors and matrices, see \ref 00030 vec_arith.h . For statistics operations not included here, see 00031 \ref vec_stats.h in the directory \c src/other . For functions and 00032 classes which are specific to C-style arrays, see \ref array.h . 00033 Also related are the matrix output functions, \ref matrix_out(), 00034 \ref matrix_cx_out_paren(), and \ref matrix_out_paren() which are 00035 defined in \ref columnify.h because they utilize the class \ref 00036 columnify to format the output. 00037 */ 00038 00039 #include <iostream> 00040 #include <cmath> 00041 #include <string> 00042 #include <fstream> 00043 #include <sstream> 00044 #include <o2scl/err_hnd.h> 00045 #include <gsl/gsl_ieee_utils.h> 00046 #include <gsl/gsl_sort.h> 00047 00048 #ifndef DOXYGENP 00049 namespace o2scl 00050 { 00051 #endif 00052 00053 /** 00054 \brief Naive vector copy 00055 00056 \note This ordering is reversed from the GSL function 00057 \c gsl_vector_memcpy . This is to be used with 00058 \code 00059 vector_copy(N,source,destination); 00060 \endcode 00061 instead of 00062 \code 00063 gsl_vector_memcpy(destination,source); 00064 \endcode 00065 */ 00066 template<class vec_t, class vec2_t> 00067 void vector_copy(size_t N, vec_t &src, vec2_t &dest) { 00068 for(size_t i=0;i<N;i++) dest[i]=src[i]; 00069 } 00070 00071 /** 00072 \brief Naive matrix copy 00073 00074 \note This ordering is reversed from the GSL function 00075 \c gsl_matrix_memcpy . This is to be used with 00076 \code 00077 matrix_copy(N,source,destination); 00078 \endcode 00079 instead of 00080 \code 00081 gsl_matrix_memcpy(destination,source); 00082 \endcode 00083 */ 00084 template<class mat_t, class mat2_t> 00085 void matrix_copy(size_t M, size_t N, mat_t &src, mat2_t &dest) { 00086 for(size_t i=0;i<M;i++) { 00087 for(size_t j=0;j<N;j++) { 00088 dest[i][j]=src[i][j]; 00089 } 00090 } 00091 } 00092 00093 /** 00094 \brief GSL complex vector copy 00095 00096 \future At present this works only with complex types based 00097 directly on the GSL complex format. This could be improved. 00098 */ 00099 template<class vec_t, class vec2_t> 00100 void vector_cx_copy_gsl(size_t N, vec_t &src, vec2_t &dest) { 00101 for(size_t i=0;i<N;i++) { 00102 dest[i].dat[0]=src[i].dat[0]; 00103 dest[i].dat[1]=src[i].dat[1]; 00104 } 00105 } 00106 00107 /** 00108 \brief GSL complex matrix copy 00109 00110 \future At present this works only with complex types based 00111 directly on the GSL complex format. This could be improved. 00112 */ 00113 template<class mat_t, class mat2_t> 00114 void matrix_cx_copy_gsl(size_t M, size_t N, mat_t &src, mat2_t &dest) { 00115 for(size_t i=0;i<M;i++) { 00116 for(size_t j=0;j<N;j++) { 00117 dest[i][j].dat[0]=src[i][j].dat[0]; 00118 dest[i][j].dat[1]=src[i][j].dat[1]; 00119 } 00120 } 00121 } 00122 00123 /** 00124 \brief Output a vector to a stream 00125 00126 No trailing space is output after the last element, and an 00127 endline is output only if \c endline is set to \c true. If the 00128 parameter \c n is zero, this function silently does nothing. 00129 00130 Note that the \o2 vector classes also have their own 00131 \c operator<<() defined for them. 00132 */ 00133 template<class vec_t> 00134 int vector_out(std::ostream &os, size_t n, vec_t &v, 00135 bool endline=false) { 00136 // This next line is important since n-1 is not well-defined if n=0 00137 if (n==0) return 0; 00138 for(size_t i=0;i<n-1;i++) os << v[i] << " "; 00139 os << v[n-1]; 00140 if (endline) os << std::endl; 00141 return 0; 00142 } 00143 00144 /** 00145 \brief Provide a downheap() function for vector_sort() 00146 */ 00147 template<class data_t, class vec_t> 00148 void sort_downheap(vec_t &data, const size_t N, size_t k) { 00149 00150 data_t v=data[k]; 00151 00152 while (k<=N/2) { 00153 size_t j=2*k; 00154 00155 if (j<N && data[j] < data[j+1]) j++; 00156 if (!(v < data[j])) break; 00157 data[k]=data[j]; 00158 k=j; 00159 } 00160 00161 data[k]=v; 00162 } 00163 00164 /** 00165 \brief Sort a vector 00166 00167 This is a generic sorting template function. It will work for 00168 any types \c data_t and \c vec_t for which 00169 - \c data_t has an <tt>operator=</tt> 00170 - \c data_t has a less than operator to compare elements 00171 - <tt>vec_t::operator[]</tt> returns a reference 00172 to an object of type \c data_t 00173 00174 In particular, it will work with \ref ovector, \ref uvector, 00175 \ref ovector_int, \ref uvector_int (and other related O2scl 00176 vector classes), the STL template class <tt>std::vector</tt>, 00177 and arrays and pointers of numeric, character, and string 00178 objects. 00179 00180 For example, 00181 \code 00182 std::string list[3]={"dog","cat","fox"}; 00183 vector_sort<std::string, std::string[3]>(3,list); 00184 \endcode 00185 */ 00186 template<class data_t, class vec_t> 00187 int vector_sort(const size_t n, vec_t &data) { 00188 00189 size_t N; 00190 size_t k; 00191 00192 if (n==0) return 0; 00193 00194 N=n-1; 00195 k=N/2; 00196 k++; 00197 do { 00198 k--; 00199 sort_downheap<data_t,vec_t>(data,N,k); 00200 } while (k > 0); 00201 00202 while (N > 0) { 00203 data_t tmp=data[0]; 00204 data[0]=data[N]; 00205 data[N]=tmp; 00206 N--; 00207 sort_downheap<data_t,vec_t>(data,N,0); 00208 } 00209 00210 return 0; 00211 } 00212 00213 /** 00214 \brief "Rotate" a vector so that the kth element is now the beginning 00215 00216 This is a generic template function which will work for 00217 any types \c data_t and \c vec_t for which 00218 - \c data_t has an <tt>operator=</tt> 00219 - <tt>vec_t::operator[]</tt> returns a reference 00220 to an object of type \c data_t 00221 */ 00222 template<class data_t, class vec_t> 00223 int vector_rotate(const size_t n, vec_t &data, size_t k) { 00224 00225 data_t *tmp=new data_t[n]; 00226 for(size_t i=0;i<n;i++) { 00227 tmp[i]=data[(i+k)%n]; 00228 } 00229 for(size_t i=0;i<n;i++) { 00230 data[i]=tmp[i]; 00231 } 00232 delete[] tmp; 00233 00234 return 0; 00235 } 00236 00237 /// Compute the maximum of the first \c n elements of a vector 00238 template<class vec_t> 00239 double vector_max(const size_t n, vec_t &data) { 00240 00241 if (n==0) { 00242 set_err_ret("Sent size=0 to vector_max().",gsl_efailed); 00243 } 00244 double max=data[0]; 00245 for(size_t i=1;i<n;i++) { 00246 if (data[i]>max) { 00247 max=data[i]; 00248 } 00249 } 00250 return max; 00251 } 00252 00253 /// Compute the minimum of the first \c n elements of a vector 00254 template<class vec_t> 00255 double vector_min(const size_t n, vec_t &data) { 00256 00257 if (n==0) { 00258 set_err_ret("Sent size=0 to vector_min().",gsl_efailed); 00259 } 00260 double min=data[0]; 00261 for(size_t i=1;i<n;i++) { 00262 if (data[i]<min) { 00263 min=data[i]; 00264 } 00265 } 00266 return min; 00267 } 00268 00269 /// Compute the minimum and maximum of the first \c n elements of a vector 00270 template<class vec_t> 00271 int vector_minmax(const size_t n, vec_t &data, double &min, double &max) { 00272 00273 if (n==0) { 00274 set_err_ret("Sent size=0 to vector_min().",gsl_efailed); 00275 } 00276 min=data[0]; 00277 max=min; 00278 for(size_t i=1;i<n;i++) { 00279 if (data[i]<min) { 00280 min=data[i]; 00281 } 00282 if (data[i]>max) { 00283 max=data[i]; 00284 } 00285 } 00286 return 0; 00287 } 00288 00289 /// Compute the maximum of the first \c n elements of a vector 00290 template<class vec_t> 00291 size_t vector_max_index(const size_t n, vec_t &data, double &max) { 00292 00293 if (n==0) { 00294 set_err_ret("Sent size=0 to vector_max().",gsl_efailed); 00295 } 00296 size_t ix=0; 00297 max=data[0]; 00298 for(size_t i=1;i<n;i++) { 00299 if (data[i]>max) { 00300 max=data[i]; 00301 ix=i; 00302 } 00303 } 00304 return ix; 00305 } 00306 00307 /// Compute the minimum of the first \c n elements of a vector 00308 template<class vec_t> 00309 int vector_min_index(const size_t n, vec_t &data, double &min) { 00310 00311 if (n==0) { 00312 set_err_ret("Sent size=0 to vector_min().",gsl_efailed); 00313 } 00314 size_t ix=0; 00315 min=data[0]; 00316 for(size_t i=1;i<n;i++) { 00317 if (data[i]<min) { 00318 min=data[i]; 00319 ix=i; 00320 } 00321 } 00322 return ix; 00323 } 00324 00325 /// Compute the minimum and maximum of the first \c n elements of a vector 00326 template<class vec_t> 00327 int vector_minmax_index(const size_t n, vec_t &data, double &min, 00328 size_t &ix, double &max, size_t &ix2) { 00329 00330 if (n==0) { 00331 set_err_ret("Sent size=0 to vector_min().",gsl_efailed); 00332 } 00333 ix=0; 00334 ix2=0; 00335 min=data[0]; 00336 max=min; 00337 for(size_t i=1;i<n;i++) { 00338 if (data[i]<min) { 00339 min=data[i]; 00340 ix=i; 00341 } 00342 if (data[i]>max) { 00343 max=data[i]; 00344 ix2=i; 00345 } 00346 } 00347 return 0; 00348 } 00349 00350 /** 00351 \brief Compute the sum of the first \c n elements of a vector 00352 00353 If \c n is zero, this will set \c avg to zero and return 00354 \ref gsl_success. 00355 */ 00356 template<class vec_t> 00357 double vector_sum(const size_t n, vec_t &data) { 00358 00359 double sum=0; 00360 for(size_t i=0;i<n;i++) { 00361 sum+=data[i]; 00362 } 00363 return sum; 00364 } 00365 00366 /** \brief Reverse a vector 00367 */ 00368 template<class data_t, class vec_t> 00369 int vector_reverse(const size_t n, vec_t &data) { 00370 data_t tmp; 00371 00372 for(size_t i=0;i<n/2;i++) { 00373 tmp=data[n-1-i]; 00374 data[n-1-i]=data[i]; 00375 data[i]=tmp; 00376 } 00377 return 0; 00378 } 00379 00380 #ifndef DOXYGENP 00381 } 00382 #endif 00383 00384 #endif
Documentation generated with Doxygen and provided under the GNU Free Documentation License. See License Information for details.
Project hosting provided by
,
O2scl Sourceforge Project Page