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_TABLE_H 00024 #define O2SCL_TABLE_H 00025 00026 #include <iostream> 00027 #include <fstream> 00028 #include <string> 00029 #include <cmath> 00030 #include <sstream> 00031 #include <o2scl/misc.h> 00032 #include <o2scl/err_hnd.h> 00033 #include <o2scl/multi_funct.h> 00034 #include <o2scl/collection.h> 00035 #include <o2scl/search_vec.h> 00036 #include <o2scl/ovector_tlate.h> 00037 #include <o2scl/smart_interp.h> 00038 00039 #ifndef DOXYGENP 00040 namespace o2scl { 00041 #endif 00042 00043 /** \brief Data table 00044 00045 A class to contain and manipulate several equally-sized columns 00046 of data. The purpose of this class is to provide a structure 00047 which allows one to refer to the columns using a name 00048 represented by a string. Thus for a table object named \c t with 00049 3 columns (named "colx", "coly" and "colz") and three rows, one 00050 could do the following: 00051 \code 00052 // Set the 1st row of column "colx" to 1.0 00053 t.set("colx",0,1.0); 00054 // Set the 2nd row of column "colz" to 2.0 00055 t.set("colz",1,2.0); 00056 // Set the 3rd row of column "coly" to 4.0 00057 t.set("coly",2,4.0); 00058 // This will print out 2.0 00059 cout << t.get("colz",1) << endl; 00060 \endcode 00061 Note that the rows are numbered starting with 0 instead of 00062 starting with 1. 00063 To output all the rows of entire column, one can use 00064 \code 00065 for(size_t i=0;i<t.get_nlines();i++) { 00066 cout << i << " " << t.get("colx",i) << endl; 00067 } 00068 \endcode 00069 To output all the columns of an entire row (in the following 00070 example it is the second row), labeled by their column name, one 00071 can use: 00072 \code 00073 for(size_t i=0;i<t.get_ncolumns();i++) { 00074 cout << t.get_column_name(i) << " "; 00075 } 00076 cout << endl; 00077 for(size_t i=0;i<t.get_ncolumns();i++) { 00078 cout << t.get(i,1) << " "; 00079 } 00080 cout << endl; 00081 \endcode 00082 00083 Methods are provided for interpolating columns, sorting 00084 columns, finding data points, and several other manipulations 00085 of the data. 00086 00087 <B> Data representation </b> \n 00088 00089 Each individual column is just an ovector_view (or any 00090 descendant of an ovector_view) The columns can be referred to in 00091 one of two ways: 00092 - A numerical index from 0 to C-1 (where C is the number of 00093 columns). For example, data can be accessed through \ref 00094 table::get(size_t c, size_t r) and \ref table::set(size_t c, size_t r, 00095 double val), or the overloaded [] operator, table[c][r]. 00096 - A name of the column which is a string with no whitespace. 00097 For example, data can be accessed with table::get(string cname, 00098 int r) and table::set(string cname, int r, double val). 00099 00100 The columns are organized in a both a <map> and a <vector> 00101 structure so that finding a column by its index ( string 00102 table::get_column_name(int index), and double 00103 *table::get_column(int index) ) takes only constant time, and 00104 finding a column by its name ( int \ref lookup_column() and 00105 double * \ref table::get_column() ) is O(log(C)). Insertion of a 00106 column ( \ref new_column() ) is O(log(C)), but deletion ( \ref 00107 delete_column() ) is O(C). Adding a row of data can be either 00108 O(1) or O(C), but row insertion and deletion is slow, since the 00109 all of the columns must be shifted accordingly. 00110 00111 Ownership of any column may be changed at any time, but care 00112 must be taken to ensure that memory allocation errors do not 00113 occur. These errors should not occur when no columns are 00114 owned by the user. 00115 00116 Because of the structure, this class is not suitable for the 00117 matrix manipulation. The classes \ref omatrix and \ref umatrix 00118 are better used for that purpose. 00119 00120 \b Column \b size \n 00121 00122 The columns grow automatically (similar to the STL <vector>) 00123 in reponse to an attempt to call set() for a row that does not 00124 presently exist or in a call to line_of_data() when the table is 00125 already full. However, this forces memory rearrangments that are 00126 O(R*C). Columns which are not owned by the table are not 00127 modified, so the table will not allow an increase in the number 00128 of lines beyond the size of the smallest user-owned column. If 00129 the user has a good estimate of the number of rows beforehand, 00130 it is best to either specify this in the constructor, or in an 00131 explicit call to inc_maxlines(). 00132 00133 <B> Lookup, differentiation, integration, and interpolation </b> 00134 \n Lookup, differentiation, integration, and interpolation are 00135 automatically implemented using splines from the class 00136 smart_interp_vecp. A caching mechanism is implemented so that 00137 successive interpolations, derivative evaluations or 00138 integrations over the same two columns are fast. 00139 00140 <B> Sorting </b>\n 00141 00142 The columns are automatically sorted by name for speed, the 00143 results can be accessed by table::get_sorted_name(i). Individual 00144 columns can be sorted, or the entire table can be sorted by one 00145 column. 00146 00147 <B> Allowable column names</b> \n 00148 00149 In general, column names may be of any form as long as they 00150 don't contain whitespace, e.g. \c 123".#@$%xy~ is a 00151 legitmate column name. The column name should be restricted to contain 00152 only letters, numbers, and underscores and may not begin with a 00153 digit. 00154 00155 <B> Thread-safety </b> \n 00156 00157 Generally, the member functions are thread-safe in the sense 00158 that one would expect. Simple get() and set() functions are 00159 thread-safe, while insertion and deletion operations are not. It 00160 makes little sense to try to make insertion and deletion 00161 thread-safe. The interpolation routines are not thread-safe. 00162 00163 \b I/O \b and \b command-line \b manipulation \n 00164 00165 When data from an object of type \ref table is output to 00166 a file through the \ref collection class, the table 00167 can be manipulated on the command-line through 00168 the acol utility. 00169 00170 There is an example for the usage of this class given 00171 in <tt>examples/ex_table.cpp</tt>. 00172 00173 \todo Better testing of automatic resizing with user- 00174 and class-owned columns 00175 00176 \future Be more restrictive about allowable column names 00177 00178 \future Add interp() and related functions which avoid caching and 00179 can thus be const (This has been started with interp_const() ) 00180 00181 \future The nlines vs. maxlines and automatic resizing of 00182 table-owned vs. user-owned vectors could be reconsidered, 00183 especially now that ovectors can automatically resize on their 00184 own. 10/16/07: This issue may be unimportant, as it might 00185 be better to just move to a template based approach with 00186 a user-specified vector type. The interpolation is now flexible 00187 enough to handle different types. Might check to ensure sorting 00188 works with other types. 00189 00190 \future The present structure, \c 00191 std::map<std::string,col,string_comp> atree and \c 00192 std::vector<aiter> alist; could be replaced with \c 00193 std::vector<col> list and \c std::map<std::string,int> tree 00194 where the map just stores the index of the the column in the 00195 list 00196 */ 00197 class table { 00198 public: 00199 00200 /** \brief Create a new table with space for nlines<=cmaxlines. 00201 */ 00202 table(int cmaxlines=0); 00203 00204 virtual ~table(); 00205 00206 // -------------------------------------------------------- 00207 /** \name Basic get and set methods */ 00208 //@{ 00209 /** \brief Set row \c row of column named \c col to value \c val - 00210 O(log(C)). 00211 00212 This function adds the column \c col if it does not 00213 already exist and adds rows using inc_maxlines() and 00214 set_nlines() to create at least \c (row+1) rows if they do not 00215 already exist. 00216 */ 00217 int set(std::string col, size_t row, double val); 00218 00219 /** \brief Set row \c row of column number \c icol to value \c val - O(1). 00220 */ 00221 int set(size_t icol, size_t row, double val); 00222 00223 /** \brief Get value from row \c row of column named \c col - O(log(C)). 00224 */ 00225 double get(std::string col, size_t row) const; 00226 00227 /** \brief Get value from row \c row of column number \c icol - O(1). 00228 */ 00229 double get(size_t icol, size_t row); 00230 00231 /** \brief Return the number of columns 00232 */ 00233 int get_ncolumns() const {return atree.size();}; 00234 00235 /** \brief Return the number of lines 00236 */ 00237 size_t get_nlines() const {return nlines;}; 00238 00239 /** 00240 \brief Set the number of lines 00241 00242 This function is stingy about increasing the table memory space 00243 and will only increase it enough to fit \c il lines, which 00244 is useful if you have columns not owned by the table. 00245 */ 00246 int set_nlines(size_t il); 00247 00248 /** 00249 \brief Set the number of lines 00250 00251 \todo Resolve whether set() should really use this approach. 00252 Also, resolve whether this should replace set_nlines() (It could 00253 be that the answer is no, because as the documentation 00254 in the other version states, the other version is useful if 00255 you have columns not owned by the table.) 00256 */ 00257 int set_nlines_auto(size_t il); 00258 00259 /** \brief Return the maximum number of lines 00260 */ 00261 int get_maxlines() {return maxlines;}; 00262 00263 /** \brief Returns a pointer to the column named \c col - O(log(C)) 00264 */ 00265 ovector_view *get_column(std::string col); 00266 00267 /** \brief Returns a pointer to the column named \c col - O(log(C)) 00268 */ 00269 const ovector_view *get_column_const(std::string col) const; 00270 00271 /** 00272 \brief Returns a pointer to the column of index \c icol - O(1). 00273 00274 Note that several of the methods require reallocation 00275 of memory and pointers previously returned by this function 00276 will be incorrect. 00277 */ 00278 ovector_view *get_column(size_t icol) { 00279 return (alist[icol]->second.dat); 00280 } 00281 00282 /** 00283 \brief Returns a pointer to the column of index \c icol - O(1). 00284 00285 Note that several of the methods require reallocation 00286 of memory and pointers previously returned by this function 00287 will be incorrect. 00288 */ 00289 const ovector_view *get_column(size_t icol) const { 00290 return (alist[icol]->second.dat); 00291 } 00292 00293 /** 00294 \brief Returns the column of index \c icol - O(1) (const version) 00295 00296 This does not do any sort of bounds checking and is 00297 quite fast. 00298 00299 Note that several of the methods require reallocation of 00300 memory and refereces previously returned by this function will 00301 be incorrect. 00302 */ 00303 const ovector_view &operator[] (size_t icol) const { 00304 return (*alist[icol]->second.dat); 00305 } 00306 00307 /** 00308 \brief Returns the column of index \c icol - O(1). 00309 00310 This does not do any sort of bounds checking and is 00311 quite fast. 00312 00313 Note that several of the methods require reallocation of 00314 memory and refereces previously returned by this function will 00315 be incorrect. 00316 */ 00317 ovector_view &operator[] (size_t icol) { 00318 return (*alist[icol]->second.dat); 00319 } 00320 00321 /** 00322 \brief Returns the column named \c scol - O(log(C)) (const version) 00323 00324 No error checking is performed. 00325 00326 Note that several of the methods require reallocation of 00327 memory and refereces previously returned by this function will 00328 be incorrect. 00329 */ 00330 const ovector_view &operator[](std::string scol) const { 00331 aciter it=atree.find(scol); 00332 return *(it->second.dat); 00333 } 00334 00335 /** 00336 \brief Returns the column named \c scol - O(log(C)) 00337 00338 No error checking is performed. 00339 00340 Note that several of the methods require reallocation of 00341 memory and refereces previously returned by this function will 00342 be incorrect. 00343 */ 00344 ovector_view &operator[](std::string scol) { 00345 aiter it=atree.find(scol); 00346 return *(it->second.dat); 00347 } 00348 00349 /** \brief Returns a copy of the row with value \c val 00350 in column \c col - O(R*C) */ 00351 int get_row(std::string col, double val, ovector &row) const; 00352 00353 /** \brief Returns a copy of row number \c irow - O(C) 00354 */ 00355 int get_row(size_t irow, ovector &row) const; 00356 //@} 00357 00358 // -------------------------------------------------------- 00359 /** \name Column manipulation */ 00360 //@{ 00361 00362 /** \brief Returns the name of column \c col - O(1). 00363 */ 00364 std::string get_column_name(size_t col) const; 00365 00366 /** \brief Returns the name of column \c col in sorted order - O(1). 00367 */ 00368 std::string get_sorted_name(size_t col); 00369 00370 /** \brief Add a new column owned by the table - O(log(C)). 00371 */ 00372 int new_column(std::string name); 00373 00374 /** 00375 \brief Add a new column owned by the user - O(log(C)). 00376 00377 This function does not modify the number of lines of data in 00378 the table. 00379 00380 \todo We've got to figure out what to do if ldat is too small. 00381 If it's smaller than nlines, obviously we should just 00382 fail, but what if it's size is between nlines and maxlines? 00383 */ 00384 int new_column(std::string name, ovector_view *ldat); 00385 00386 /** 00387 \brief Find the index for column named \c name - O(log(C)). 00388 00389 If the column is not present, this does not call the error 00390 handler, but quietly sets \c ix to zero and returns \ref 00391 gsl_notfound. 00392 */ 00393 int lookup_column(std::string name, int &ix); 00394 00395 /** 00396 \brief Rename column named \c olds to \c news - O(C). 00397 00398 This is slow since we have to delete the column and re-insert 00399 it. This process in turn mangles all of the 00400 iterators in the list. 00401 */ 00402 int rename_column(std::string olds, std::string news); 00403 00404 /** \brief Make a new column named \c dest equal to \c src - O(log(C)*R). 00405 */ 00406 int copy_column(std::string src, std::string dest); 00407 00408 /// Create (using \c new) a generic array from column \c col 00409 double *create_array(std::string col) const; 00410 00411 /** \brief Initialize all values of column named \c scol to \c val - 00412 O(log(C)*R). 00413 00414 Note that this does not initialize elements beyond 00415 nlines so that if the number of rows is increased afterwards, the 00416 new rows will have uninitialized values. 00417 */ 00418 int init_column(std::string scol, double val); 00419 00420 /** 00421 \brief Modify ownership - O(log(C)). 00422 00423 \warning columns allocated using malloc() should never be 00424 owned by the table object since it uses delete instead of 00425 free(). 00426 */ 00427 int ch_owner(std::string name, bool ow); 00428 00429 /** \brief Get ownership - O(log(C)). 00430 */ 00431 bool get_owner(std::string name) const; 00432 00433 /** 00434 \brief Get a gsl_vector from column \c name - O(log(C)). 00435 */ 00436 const gsl_vector *get_gsl_vector(std::string name) const; 00437 00438 /** \brief Return 0 if the tree and list are properly synchronized 00439 */ 00440 int check_synchro() const; 00441 00442 /** 00443 \brief Insert a column from a separate table, interpolating 00444 it into a new column 00445 00446 Given a pair of columns ( \c src_index, \c src_col ) in a 00447 separate table (\c source), this creates a new column in the 00448 present table named \c src_col which interpolates \c loc_index 00449 into \c src_index. The interpolation objects from the \c 00450 source table will be used. If there is already a column in the 00451 present table named \c src_col, then this will fail. 00452 00453 If there is an error in the interpolation for any particular 00454 row, then the value of \c src_col in that row will be set to 00455 zero. 00456 */ 00457 int add_col_from_table(std::string loc_index, table &source, 00458 std::string src_index, std::string src_col, 00459 std::string dest_col=""); 00460 //@} 00461 00462 // -------------------------------------------------------- 00463 /** \name Row maninpulation and data input */ 00464 //@{ 00465 00466 /** \brief Insert a row before row \c n 00467 */ 00468 int new_row(size_t n); 00469 00470 /** \brief Copy the data in row \c src to row \c dest 00471 */ 00472 int copy_row(size_t src, size_t dest); 00473 00474 /** \brief Insert a row of data before row \c n 00475 */ 00476 int insert_data(size_t n, size_t nv, double *v); 00477 00478 /** \brief Insert a row of data before row \c n 00479 */ 00480 int insert_data(size_t n, size_t nv, double **v); 00481 00482 /** 00483 \brief Read a new set of names from \c newheads 00484 */ 00485 int line_of_names(std::string newheads); 00486 00487 /** \brief Read a line of data from an array 00488 */ 00489 template<class vec_t> int line_of_data(size_t nv, const vec_t &v) { 00490 if (maxlines==0) inc_maxlines(5); 00491 if (nlines>=maxlines) inc_maxlines(maxlines); 00492 00493 if (intp_set) { 00494 intp_set=false; 00495 delete si; 00496 } 00497 00498 if (nlines<maxlines && nv<=(atree.size())) { 00499 00500 for(size_t i=0;i<nv;i++) { 00501 (*this)[i][nlines]=v[i]; 00502 } 00503 nlines++; 00504 00505 return 0; 00506 } 00507 00508 set_err("Not enough lines or columns in line_of_data().",gsl_einval); 00509 return gsl_einval; 00510 } 00511 //@} 00512 00513 // -------------------------------------------------------- 00514 /** \name Lookup and search methods */ 00515 //@{ 00516 00517 /** 00518 \brief Look for a value in an ordered column 00519 00520 O(log(C)*log(R)) 00521 */ 00522 size_t ordered_lookup(std::string col, double val); 00523 00524 /// Exhaustively search column \c col for the value \c val - O(log(C)*R). 00525 size_t lookup(std::string col, double val) const; 00526 00527 /// Search column \c col for the value \c val and return value in \c col2 00528 double lookup_val(std::string col, double val, std::string col2) const; 00529 00530 /// Exhaustively search column \c col for the value \c val - O(log(C)*R). 00531 size_t lookup(int col, double val) const; 00532 00533 /** \brief Exhaustively search column \c col for many occurences 00534 of \c val - O(log(C)*R). 00535 */ 00536 size_t mlookup(std::string col, double val, std::vector<double> &results, 00537 double threshold=0.0) const; 00538 00539 /** 00540 \brief Search for row with maximum value of formula 00541 00542 This searches the table for the maximum value of the specified 00543 formula. For example, to find the row for which the column \c 00544 mu is 2 and \c T is 3, you can use 00545 \code 00546 table::lookup_form("-abs(mu-2)-abs(T-3)"); 00547 \endcode 00548 00549 */ 00550 int lookup_form(std::string formula, double &maxval); 00551 //@} 00552 00553 // -------------------------------------------------------- 00554 /** \name Interpolation, differentiation, and integration, max, and min */ 00555 //@{ 00556 00557 /** 00558 \brief Interpolate \c x0 from \c sx into \c sy 00559 00560 O(log(C)*log(R)) but can be as bad as O(log(C)*R) if 00561 the relevant columns are not well ordered. 00562 */ 00563 double interp(std::string sx, double x0, std::string sy); 00564 00565 /** 00566 \brief Interpolate \c x0 from \c sx into \c sy 00567 00568 O(log(C)*log(R)) but can be as bad as O(log(C)*R) if 00569 the relevant columns are not well ordered. 00570 */ 00571 double interp_const(std::string sx, double x0, std::string sy) const; 00572 00573 /** 00574 \brief Interpolate \c x0 from \c ix into \c iy 00575 00576 O(log(R)) but can be as bad as O(R) if 00577 the relevant columns are not well ordered. 00578 */ 00579 double interp(size_t ix, double x0, size_t iy); 00580 00581 /** \brief Make a new column \c yp which is the derivative y'(x) - 00582 O(log(C)*R). 00583 */ 00584 int deriv(std::string x, std::string y, std::string yp); 00585 00586 /** 00587 \brief The first derivative of the function sy(sx) at sx=x0. 00588 00589 O(log(C)*log(R)) but can be as bad as O(log(C)*R) if 00590 the relevant columns are not well ordered. 00591 */ 00592 double deriv(std::string sx, double x0, std::string sy); 00593 00594 /** 00595 \brief The first derivative of the function iy(ix) at ix=x0. 00596 00597 O(log(R)) but can be as bad as O(R) if 00598 the relevant columns are not well ordered. 00599 */ 00600 double deriv(size_t ix, double x0, size_t iy); 00601 00602 /** 00603 \brief Make a new column \c yp which is 00604 \f$ y^{\prime \prime}(x) \f$ - O(log(C)*R). 00605 */ 00606 int deriv2(std::string x, std::string y, std::string yp); 00607 00608 /** 00609 \brief The second derivative of the function sy(sx) at sx=x0. 00610 00611 O(log(C)*log(R)) but can be as bad as O(log(C)*R) if 00612 the relevant columns are not well ordered. 00613 */ 00614 double deriv2(std::string sx, double x0, std::string sy); 00615 00616 /** 00617 \brief The second derivative of the function iy(ix) at ix=x0. 00618 00619 O(log(R)) but can be as bad as O(R) if 00620 the relevant columns are not well ordered. 00621 */ 00622 double deriv2(size_t ix, double x0, size_t iy); 00623 00624 /** 00625 \brief The integral of the function sy(sx) from sx=x1 to sx=x2. 00626 00627 O(log(C)*log(R)) but can be as bad as O(log(C)*R) if 00628 the relevant columns are not well ordered. 00629 */ 00630 double integ(std::string sx, double x1, double x2, std::string sy); 00631 00632 /** 00633 \brief The integral of the function iy(ix) from ix=x1 to ix=x2. 00634 00635 O(log(R)) but can be as bad as O(R) if 00636 the relevant columns are not well ordered. 00637 */ 00638 double integ(size_t ix, double x1, double x2, size_t iy); 00639 00640 /** 00641 \brief The integral of the function iy(ix) 00642 00643 O(log(R)) but can be as bad as O(R) if the relevant columns 00644 are not well ordered. 00645 */ 00646 int integ(std::string x, std::string y, std::string ynew); 00647 00648 /** \brief Return column maximum. Makes no assumptions about 00649 ordering - O(R). 00650 */ 00651 double max(std::string col) const; 00652 00653 /** \brief Return column minimum. Makes no assumptions about 00654 ordering - O(R). 00655 */ 00656 double min(std::string col) const; 00657 //@} 00658 00659 // -------------------------------------------------------- 00660 /** \name Subtable method */ 00661 //@{ 00662 00663 /** 00664 \brief Make a subtable 00665 00666 Uses the columns specified in \c list from the row \c top 00667 to the row of index \c bottom. If \c linked is false 00668 the the data will be independent from the original table. 00669 */ 00670 table *subtable(std::string list, size_t top, size_t bottom, 00671 bool linked=true); 00672 //@} 00673 00674 // -------------------------------------------------------- 00675 /** \name Add space */ 00676 //@{ 00677 00678 /** \brief Manually increase the maximum number of lines 00679 */ 00680 int inc_maxlines(size_t llines); 00681 //@} 00682 00683 // -------------------------------------------------------- 00684 /** \name Delete methods */ 00685 //@{ 00686 00687 /** \brief Delete column named \c scol - O(C). 00688 00689 This is slow because 00690 the iterators in alist are mangled and we have to call 00691 reset_list to get them back. 00692 */ 00693 00694 int delete_column(std::string scol); 00695 00696 /** \brief Delete the row with the value \c val in column \c scol. 00697 */ 00698 int delete_row(std::string scol, double val); 00699 00700 /** \brief Delete the row of index \c irow. 00701 */ 00702 int delete_row(size_t irow); 00703 //@} 00704 00705 // -------------------------------------------------------- 00706 /** \name Clear methods */ 00707 //@{ 00708 00709 /** \brief Zero the data entries but keep the column names 00710 and nlines fixed 00711 */ 00712 void zero_table(); 00713 00714 /** \brief Clear the table and the column names 00715 */ 00716 void clear_table(); 00717 00718 /** \brief Remove all of the data by setting the number 00719 of lines to zero 00720 00721 This leaves the column names intact and does not remove 00722 the constants. 00723 */ 00724 void clear_data() { 00725 nlines=0; 00726 if (intp_set==true) { 00727 delete si; 00728 intp_set=false; 00729 } 00730 return; 00731 }; 00732 //@} 00733 00734 // -------------------------------------------------------- 00735 /** \name Sorting methods */ 00736 //@{ 00737 00738 /** \brief Sort the entire table by the column \c scol 00739 */ 00740 int sort_table(std::string scol); 00741 00742 /** \brief Individually sort the column \c scol 00743 */ 00744 int sort_column(std::string scol); 00745 //@} 00746 00747 // -------------------------------------------------------- 00748 /** \name Summary method */ 00749 //@{ 00750 /** \brief Output a summary of the information stored 00751 00752 Outputs the number of constants, the number of columns, 00753 a list of the column names, and the number of lines of 00754 data. 00755 */ 00756 int summary(std::ostream *out, int ncol=79) const; 00757 //@} 00758 00759 /// Set the base interpolation objects 00760 int set_interp(base_interp<ovector_view> &bi1, 00761 base_interp<ovector_const_subvector> &bi2) { 00762 intp1=&bi1; 00763 intp2=&bi2; 00764 return 0; 00765 } 00766 00767 /// \name Constant manipulation 00768 //@{ 00769 /// Add a constant 00770 virtual int add_constant(std::string name, double val) { 00771 if (constants.find(name)!=constants.end()) { 00772 constants.find(name)->second=val; 00773 return 0; 00774 } 00775 constants.insert(make_pair(name,val)); 00776 return 0; 00777 } 00778 00779 /// Add a constant 00780 virtual int set_constant(std::string name, double val) { 00781 if (constants.find(name)!=constants.end()) { 00782 constants.find(name)->second=val; 00783 return 0; 00784 } 00785 set_err_ret("No constant with specified name in set_constant().", 00786 gsl_einval); 00787 } 00788 00789 /// Get a constant 00790 virtual double get_constant(std::string name) { 00791 return constants.find(name)->second; 00792 } 00793 00794 /// Remove a constant 00795 virtual int remove_constant(std::string name) { 00796 constants.erase(name); 00797 return 0; 00798 } 00799 //@} 00800 00801 /// Read a generic data file 00802 int read_generic(std::istream &fin); 00803 00804 protected: 00805 00806 #ifndef DOXYGEN_INTERNAL 00807 00808 /// The list of constants 00809 std::map<std::string,double> constants; 00810 00811 friend class io_tlate<table>; 00812 00813 /** \brief Set the elements of alist with the appropriate 00814 iterators from atree - O(C). 00815 00816 Generally, the end-user shouldn't need this method. It is 00817 only used in delete_column() to rearrange the list when 00818 a column is deleted from the tree. 00819 */ 00820 int reset_list(); 00821 00822 /** 00823 \brief Ensure a variable name does not match a function or contain 00824 non-alphanumeric characters 00825 */ 00826 int make_fp_varname(std::string &s); 00827 00828 /// Make sure a name is unique 00829 int make_unique_name(std::string &col, std::vector<std::string> &cnames); 00830 00831 00832 /// Column structure for \ref table [protected] 00833 typedef struct col_s { 00834 /// Pointer to column 00835 ovector_view *dat; 00836 /// Owner of column 00837 bool owner; 00838 /// Column index 00839 int index; 00840 } col; 00841 00842 /// \name Iterator types 00843 //@{ 00844 typedef std::map<std::string,col,string_comp>::iterator aiter; 00845 typedef std::map<std::string,col,string_comp>::const_iterator aciter; 00846 typedef std::vector<aiter>::iterator aviter; 00847 //@} 00848 00849 /// \name Actual data 00850 //@{ 00851 /// The size of allocated memory 00852 size_t maxlines; 00853 /// The size of presently used memory 00854 size_t nlines; 00855 /// The tree of columns 00856 std::map<std::string,col,string_comp> atree; 00857 /// The list of tree iterators 00858 std::vector<aiter> alist; 00859 //@} 00860 00861 /// \name Column manipulation methods 00862 //@{ 00863 /// Return the iterator for a column 00864 aiter get_iterator(std::string lname); 00865 /// Return the column structure for a column 00866 col *get_col_struct(std::string lname); 00867 /// Return the beginning of the column tree 00868 aiter begin() {return atree.begin();}; 00869 /// Return the end of the column tree 00870 aiter end() {return atree.end();}; 00871 //@} 00872 00873 /// The sorting function 00874 static int sortd_comp(const void *a, const void *b); 00875 00876 /// A structure for sorting in \ref table [protected] 00877 typedef struct sortd_s { 00878 /// Value to sort 00879 double val; 00880 /// Sorted index 00881 int indx; 00882 } sortd; 00883 00884 /// \name Interpolation 00885 //@{ 00886 /// The interpolation object 00887 sm_interp_vec *si; 00888 00889 /// A pointer to the interpolation object 00890 base_interp<ovector_view> *intp1; 00891 /// A pointer to the subvector interpolation object 00892 base_interp<ovector_const_subvector> *intp2; 00893 00894 /// The default interpolation object 00895 cspline_interp<ovector_view> cintp1; 00896 /// The default subvector interpolation object 00897 cspline_interp<ovector_const_subvector> cintp2; 00898 00899 /// The vector-searching object 00900 /* 00901 #ifdef DOXYGENP 00902 search_vec<vec_t> se; 00903 #else 00904 search_vec<ovector> se; 00905 #endif 00906 */ 00907 search_vec<ovector> se; 00908 00909 /// True if the interpolation type has been set 00910 bool intp_set; 00911 00912 /// The last x-column interpolated 00913 std::string intp_colx; 00914 00915 /// The last y-column interpolated 00916 std::string intp_coly; 00917 00918 //@} 00919 00920 #endif 00921 00922 }; 00923 00924 /// Input specialization 00925 template<> int io_tlate<table>::input 00926 (cinput *co, o2scl::in_file_format *ins, table *ta); 00927 /// Output specialization 00928 template<> int io_tlate<table>::output 00929 (coutput *co, o2scl::out_file_format *outs, 00930 table *at); 00931 /// \fn Type specialization 00932 template<> const char *io_tlate<table>::type(); 00933 00934 typedef io_tlate<table> table_io_type; 00935 00936 #ifndef DOXYGENP 00937 } 00938 #endif 00939 00940 #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