Changeset 907
- Timestamp:
- 04/19/10 12:44:57 (15 years ago)
- Location:
- library
- Files:
-
- 19 modified
Legend:
- Unmodified
- Added
- Removed
-
library/bdm/base/bdmbase.cpp
r899 r907 99 99 } 100 100 101 RV::RV ( int sz, int tm ) { 102 Array<string> A ( 1 ); 103 A ( 0 ) = ""; 104 init ( A, vec_1 ( sz ), vec_1 ( tm ) ); 105 } 106 101 107 bool RV::add ( const RV &rv2 ) { 102 108 if ( rv2.len > 0 ) { //rv2 is nonempty … … 426 432 } 427 433 428 int logger::add_vector ( const RV &rv, const string &prefix, const string &name ) { 429 int id; 430 if ( rv._dsize() > 0 ) { 431 id = entries.length(); 432 if( name.length() > 0 ) { 433 names = concat ( names, prefix + separator + name); // diff 434 } else { 435 names = concat ( names, prefix ); // diff 436 } 437 entries.set_length ( id + 1, true ); 438 entries ( id ) = rv; 439 } else { 440 id = -1; 441 } 442 return id; // identifier of the last entry 443 } 444 445 int logger::add_setting ( const string &prefix ) { 446 Setting &root = setting_conf.getRoot(); 447 int id = root.getLength(); //root must be group!! 448 if ( prefix.length() > 0 ) { 449 settings.set_length ( id + 1, true ); 450 settings ( id ) = &root.add ( prefix, Setting::TypeList ); 451 } else { 452 id = -1; 453 } 454 return id; 434 435 string logger::remove_log_prefix_if_possible( string name_with_prefix ) 436 { 437 string possible_log_prefix = name_with_prefix.substr(0,3); 438 if( possible_log_prefix == "log" ) 439 return name_with_prefix.substr(3,name_with_prefix.length()-3); 440 else return name_with_prefix; 455 441 } 456 442 457 443 void epdf::log_register ( logger &L, const string &prefix ) { 444 root::log_register ( L, prefix ); 445 458 446 RV r; 459 447 if ( isnamed() ) { 460 448 r = _rv(); 461 449 } else { 462 r = RV ( "",dimension() );450 r = RV ( dimension() ); 463 451 }; 464 root::log_register ( L, prefix ); 465 466 // log full data 452 467 453 if ( log_level[logfull] ) { 468 logrec->ids.set_size ( 1 );469 logrec->ids ( 0 ) = logrec->L.add_setting (prefix );454 // log full data 455 registered_logger->add_setting ( log_level, logfull, prefix ); 470 456 } else { 471 457 // log only 472 logrec->ids.set_size ( 3 ); 473 if ( log_level[logmean] ) { 474 logrec->ids ( 0 ) = logrec->L.add_vector ( r, prefix, "mean" ); 475 } 476 if ( log_level[loglbound] ) { 477 logrec->ids ( 1 ) = logrec->L.add_vector ( r, prefix, "lb" ); 478 } 479 if ( log_level[logubound] ) { 480 logrec->ids ( 2 ) = logrec->L.add_vector ( r, prefix, "ub" ); 481 } 482 458 459 if ( log_level[logmean] ) 460 registered_logger->add_vector ( log_level, logmean, r, prefix ); 461 if ( log_level[loglbound] ) 462 registered_logger->add_vector ( log_level, loglbound, r, prefix ); 463 if ( log_level[logubound] ) 464 registered_logger->add_vector ( log_level, logubound, r, prefix ); 483 465 } 484 466 } … … 486 468 void epdf::log_write() const { 487 469 if ( log_level[logfull] ) { 488 UI::save(this, logrec->L.log_to_setting ( logrec->ids ( 0 ) ));470 log_level.store( logfull, this ); 489 471 } else { 490 472 if ( log_level[logmean] ) { 491 log rec->L.log_vector ( logrec->ids ( 0 ), mean() );473 log_level.store( logmean, mean() ); 492 474 } 493 475 if ( log_level[loglbound] || log_level[logubound] ) { … … 496 478 qbounds ( lb, ub ); 497 479 if (log_level[loglbound]) 498 log rec->L.log_vector ( logrec->ids ( 1 ), lb );480 log_level.store( loglbound, lb ); 499 481 if (log_level[logubound]) 500 log rec->L.log_vector ( logrec->ids ( 2 ), ub );482 log_level.store( logubound, ub ); 501 483 } 502 484 } … … 543 525 544 526 root::log_register ( L, prefix ); 545 //we know that 546 if ( log_level.any() ) { 547 logrec->ids.set_size ( 1 );548 logrec->ids ( 0 ) = logrec->L.add_vector ( Drv, prefix );549 // logrec->ids ( 1 ) = logrec->L.add_vector ( Urv, prefix );550 }527 528 529 if ( log_level[logdt] ) 530 registered_logger->add_vector ( log_level, logdt, Drv, prefix ); 531 if ( log_level[logut] ) 532 registered_logger->add_vector ( log_level, logut, Urv, prefix ); 551 533 } 552 534 553 535 void DS::log_write ( ) const { 554 if ( log_level.any()) {536 if( log_level[logdt] ) { 555 537 vec tmp ( Drv._dsize()); 556 538 getdata ( tmp ); 557 539 // d is first in getdata 558 logrec->L.log_vector ( logrec->ids ( 0 ), tmp ); 540 log_level.store( logdt, tmp ); 541 } 542 if( log_level[logut] ) { 543 bdm_warning("We are sorry, but DS::log_write() is not able to log \"ut\" at the moment, would you be so kind and code this functionality?"); 544 } 545 } 546 547 548 void DS::from_setting ( const Setting &set ) { 549 shared_ptr<RV> r = UI::build<RV> ( set, "drv", UI::optional ); 550 if ( r ) 551 set_drv ( *r, RV() ); 552 } 553 554 void DS::validate() { 555 if( !Drv._dsize() && dtsize > 0 ) 556 { 557 RV *r = new RV(); 558 for ( int i = 0; i < dtsize; i++ ) { 559 r->add ( RV ( "ch" + num2str ( i ), 1, 0 ) ); 560 } 561 set_drv ( *r, RV() ); 562 delete r; 559 563 } 560 564 } … … 563 567 root::log_register ( L, prefix ); 564 568 565 if ( log_level.any() ) { 566 logrec->ids.set_size ( 1 ); 567 logrec->ids ( 0) = L.add_vector ( RV ( "", 1 ), prefix, "ll" ); 568 } 569 569 if ( log_level[logevidence] ) 570 registered_logger->add_vector ( log_level, logevidence, RV ( 1 ), prefix ); 571 570 572 if (log_level[logbounds]){ 571 573 prior().log_level[epdf::loglbound]=true; … … 580 582 void BM::log_write ( ) const { 581 583 posterior().log_write(); 582 if ( log_level.any() ) { 583 logrec->L.logit ( logrec->ids ( 0 ), ll );584 }584 585 if( log_level[logevidence] ) 586 log_level.store( logevidence, ll ); 585 587 } 586 588 -
library/bdm/base/bdmbase.h
r896 r907 86 86 //! Internal global variable storing names of RVs 87 87 static Array<string> NAMES; 88 89 88 //! TODO 90 89 const static int BUFFER_STEP; 91 92 90 //! TODO 93 91 static str2int_map MAP; … … 141 139 RV() : dsize ( 0 ), len ( 0 ), ids ( 0 ), times ( 0 ) {} 142 140 143 //! Constructor of a single RV with given id141 //! Constructor of a single RV 144 142 RV ( string name, int sz, int tm = 0 ); 143 144 //! Constructor of a single nameless RV 145 RV ( int sz, int tm = 0 ); 145 146 146 147 // compiler-generated copy constructor is used … … 295 296 RV concat ( const RV &rv1, const RV &rv2 ); 296 297 298 299 //! This class stores a details that will be logged to a logger 300 template<class T> class log_level_template : public log_level_base { 301 //! this is necessary to allow logger to set ids vector appropriately and also to set registered_logger 302 friend class logger; 303 304 //! vector of log IDs - one element for each entry 305 ivec ids; 306 307 //! internal pointer to the logger to which this log_level is registered 308 //! 309 //! it is set to NULL at the beginning 310 logger * registered_logger; 311 312 public: 313 //! default constructor 314 log_level_template() { 315 registered_logger = NULL; 316 ids.set_size( T::log_level_names().length() ); 317 ids = -1; 318 } 319 320 //! This method stores a vector to the proper place in registered logger 321 void store( const enum T::log_level_enums log_level_enum, const vec &vect ) const 322 { 323 bdm_assert_debug( registered_logger != NULL, "You have to register instance to a logger first! Use root::log_register(...) method."); 324 bdm_assert_debug( ids( log_level_enum ) >= 0, "This particular vector was not added to logger! Use logger::add_vector(...) method."); 325 registered_logger->log_vector( ids( log_level_enum ), vect ); 326 } 327 328 //! This method stores a double to the proper place in registered logger 329 void store( const enum T::log_level_enums log_level_enum, const double &dbl ) const 330 { 331 bdm_assert_debug( registered_logger != NULL, "You have to register instance to a logger first! See root::log_register(...) method."); 332 bdm_assert_debug( ids( log_level_enum ) >= 0, "This particular double was not added to logger! Use logger::add_vector(...) method."); 333 registered_logger->log_double( ids( log_level_enum ), dbl ); 334 } 335 336 //! This method stores a Setting obtained by call of UI::save( data, .. ) to the proper place in registered logger 337 template<class U> void store( const enum T::log_level_enums log_level_enum, const U data ) const 338 { 339 bdm_assert_debug( registered_logger != NULL, "You have to register instance to a logger first! See root::log_register(...) method."); 340 bdm_assert_debug( ids( log_level_enum ) >= 0, "This particular vector was not added to logger! Use logger::add_setting(...) method."); 341 registered_logger->log_setting( ids( log_level_enum ), data); 342 } 343 344 345 //! string equivalents of the used enumerations which are filled with a help of #LOG_LEVEL macro within class T 346 const Array<string> &names() const 347 { 348 return T::log_level_names(); 349 } 350 351 //! read only operator for testing individual fields of log_level 352 //! 353 //! it is necessary to acces it with a proper enumeration type, thus this approach is type-safe 354 bool operator [] (const enum T::log_level_enums &log_level_enum ) const 355 { 356 return values[log_level_enum]; 357 } 358 359 //! operator for setting an individual field of log_level 360 //! 361 //! it is necessary to acces it with a proper enumeration type, thus this approach is type-safe 362 bitset<32>::reference operator [] (const enum T::log_level_enums &log_level_enum ) 363 { 364 return values[log_level_enum]; 365 } 366 }; 367 368 /*! 369 \def LOG_LEVEL(classname,...) 370 \brief Macro for defining a log_level attribute with a specific set of enumerations related to a specific class 371 372 This macro has to be called within a class declaration. Its argument \a classname has to correspond to that wrapping class. 373 This macro defines a log_level instance which can be modified either directly or by the means of #UI class. 374 375 One of the main purposes of this macro is to allow variability in using enumerations. By relating them to their names through 376 an array of strings, we are no more dependant on their precise ordering. What is more, we can add or remove any without harming 377 any applications which are using this library. 378 379 \todo Write a more detailed explanation including also examples 380 381 \ref ui 382 */ 383 #define LOG_LEVEL(classname,...) public: enum log_level_enums { __VA_ARGS__ }; log_level_template<classname> log_level; private: friend class log_level_template<classname>; static const Array<string> &log_level_names() { static const Array<string> log_level_names = log_level_base::string2Array( #__VA_ARGS__ ); return log_level_names; } 384 385 297 386 /*! 298 387 @brief Class for storing results (and semi-results) of an experiment … … 301 390 */ 302 391 class logger : public root { 392 private: 393 //! this method removes a "log" prefix from a string, i.e., it transforms "logevidence" to "evidence" 394 //! 395 //! for other cases, it keeps string unchanged 396 static string remove_log_prefix_if_possible( string name_with_prefix ); 303 397 protected: 304 398 //! RVs of all logged variables. … … 310 404 //! list of Settings for specific ids 311 405 Array<Setting*> settings; 312 public: 313 //!Default constructor 314 logger ( const string separator0 ) : entries ( 0 ), names ( 0 ), separator ( separator0 ) {} 315 406 407 //! log this instance to Setting 408 //! 409 //! this method has to be called only through \c log_level class to assure the validity of the passed id 410 template<class U> void log_setting ( int id, const U data ) { 411 UI::save(data, *settings ( id ) ); 412 } 413 414 //! log this vector 415 //! 416 //! this method has to be called only through \c log_level class to assure the validity of the passed id 417 virtual void log_vector ( int id, const vec &v ) NOT_IMPLEMENTED_VOID; 418 419 //! log this double 420 //! 421 //! this method has to be called only through \c log_level class to assure the validity of the passed id 422 virtual void log_double ( int id, const double &d ) NOT_IMPLEMENTED_VOID; 423 424 //! it is necessary to allow log_levels to call log_setting, log_vector and log_double methods 425 template<class T> friend class log_level_template; 426 public: 316 427 //!separator of prefixes of entries 317 428 //! … … 319 430 const string separator; 320 431 321 322 //! returns an identifier which will be later needed for calling the \c logit() function 323 //! For empty RV it returns -1, this entry will be ignored by \c logit(). 324 virtual int add_vector ( const RV &rv, const string &prefix, const string &name = "" ); 325 326 virtual int add_setting ( const string &prefix ); 327 328 //! log this vector 329 virtual void log_vector ( int id, const vec &v ) = 0; 330 331 virtual Setting & log_to_setting ( int id ) { 332 return settings ( id )->add ( Setting::TypeGroup ); 333 } 334 //! log this double 335 virtual void logit ( int id, const double &d ) = 0; 432 //!Default constructor 433 logger ( const string separator ) : entries ( 0 ), names ( 0 ), separator ( separator ) {} 434 435 //!Destructor calls the finalize method 436 ~logger() { 437 finalize(); 438 } 439 440 //! sets up the ids identifier in the passed log_level instance to permit future calls of the log_level_template<T>::store(...) method 441 //! 442 //! It also sets a pointer to logger or justify it is correctly assigned from previous call to this procedure 443 //! Entries with empty RV will be ignored 444 template<class T> void add_vector ( log_level_template<T> &log_level, enum T::log_level_enums const log_level_enum, const RV &rv, const string &prefix ) 445 { 446 if( !log_level.registered_logger ) 447 log_level.registered_logger = this; 448 else 449 bdm_assert_debug ( log_level.registered_logger == this, "This log_level is already registered to another logger!"); 450 451 452 if ( rv._dsize() == 0 ) 453 return; 454 455 int id = entries.length(); 456 string adjusted_name = remove_log_prefix_if_possible( log_level.names()(log_level_enum) ); 457 names = concat ( names, prefix + separator + adjusted_name ); // diff 458 entries.set_length ( id + 1, true ); 459 entries ( id ) = rv; 460 log_level.ids(log_level_enum) = id; 461 } 462 463 //! sets up the ids identifier in the passed log_level instance to permit future calls of the log_level_template<T>::store(...) method 464 //! 465 //! It also sets a pointer to logger or justify it is correctly assigned from previous call to this procedure 466 template<class T> void add_setting ( log_level_template<T> &log_level, enum T::log_level_enums const log_level_enum, const string &prefix ) { 467 if( !log_level.registered_logger ) 468 log_level.registered_logger = this; 469 else 470 bdm_assert_debug ( log_level.registered_logger == this, "This log_level is already registered to another logger!"); 471 472 Setting &root = setting_conf.getRoot(); 473 int id = root.getLength(); //root must be group!! 474 settings.set_length ( id + 1, true ); 475 string adjusted_name = remove_log_prefix_if_possible( log_level.names()(log_level_enum) ); 476 settings ( id ) = &root.add ( prefix + separator + adjusted_name, Setting::TypeList ); 477 log_level.ids(log_level_enum) = id; 478 } 336 479 337 480 //! Shifts storage position for another time step. … … 339 482 340 483 //! Finalize storing information 484 //! 485 //! This method is called either directly or via destructor ~logger(), therefore it has to permit repetitive calls for the case it is called twice 341 486 virtual void finalize() {}; 342 487 … … 344 489 virtual void init() {}; 345 490 }; 346 347 348 491 349 492 //! Class representing function \f$f(x)\f$ of variable \f$x\f$ represented by \c rv … … 907 1050 908 1051 class DS : public root { 909 //! \var log_level_enums dt1052 //! \var log_level_enums logdt 910 1053 //! TODO DOPLNIT 911 LOG_LEVEL(DS, dt); 1054 1055 //! \var log_level_enums logut 1056 //! TODO DOPLNIT 1057 LOG_LEVEL(DS,logdt,logut); 912 1058 913 1059 protected: … … 923 1069 //! default constructors 924 1070 DS() : dtsize ( 0 ), utsize ( 0 ), Drv(), Urv(){ 925 log_level[dt] = true; 1071 log_level[logdt] = true; 1072 log_level[logut] = true; 926 1073 }; 927 1074 … … 967 1114 Urv = urv; 968 1115 } 1116 1117 void from_setting ( const Setting &set ); 1118 1119 void validate(); 969 1120 }; 970 1121 -
library/bdm/base/datasources.cpp
r896 r907 36 36 time = 0; 37 37 } 38 39 shared_ptr<RV> r = UI::build<RV> ( set, "drv", UI::optional ); 40 if ( !r ) { 41 r = new RV(); 42 for ( int i = 0; i < Data.rows(); i++ ) { 43 r->add ( RV ( "ch" + num2str ( i ), 1, 0 ) ); 44 } 45 } 46 47 set_drv ( *r ); 48 dtsize = r->_dsize(); 38 } 39 40 void MemDS::validate() 41 { 42 dtsize = Data.rows(); 49 43 utsize = 0; 44 DS::validate(); 50 45 } 46 51 47 52 48 void FileDS::from_setting ( const Setting & set ) { … … 58 54 59 55 time = 0; 60 61 shared_ptr<RV> r = UI::build<RV> ( set, "drv", UI::optional );62 if ( !r ) {63 r = new RV();64 for ( int i = 0; i < Data.rows(); i++ ) {65 r->add ( RV ( "ch" + num2str ( i ), 1, 0 ) );66 }67 }68 69 set_drv ( *r );70 dtsize = r->_dsize();71 utsize = 0;72 56 } 73 57 … … 92 76 } 93 77 78 void CsvFileDS::validate() { 79 // TODO NASTASVIT DSIZE, OKOMENTOVAT PRO VOLAM DS::VALIDATE AZ PAK 80 } 81 94 82 void ITppFileDS::from_setting ( const Setting & set ) { 95 83 FileDS::from_setting ( set ); … … 101 89 it << Name ( varname ); 102 90 it >> Data; 91 } 92 93 void ITppFileDS::validate() { 94 // TODO NASTASVIT DSIZE, OKOMENTOVAT PRO VOLAM DS::VALIDATE AZ PAK 103 95 } 104 96 -
library/bdm/base/datasources.h
r896 r907 89 89 */ 90 90 void from_setting ( const Setting &set ); 91 92 void validate(); 91 93 }; 92 94 UIREGISTER ( MemDS ); … … 127 129 // TODO dodelat void to_setting( Setting &set ) const; 128 130 131 void validate(); 129 132 }; 130 133 … … 142 145 public: 143 146 void from_setting ( const Setting & set ); 147 148 void validate(); 144 149 }; 145 150 -
library/bdm/base/loggers.cpp
r899 r907 167 167 168 168 void dirfilelog::finalize ( ) { 169 if ( ind > 0 )169 if ( ind > 0 && !buffers_written) { 170 170 write_buffers ( ind ); //assuming here that i+1 was not filled 171 buffers_written = true; 172 } 171 173 } 172 174 -
library/bdm/base/loggers.h
r899 r907 34 34 //! name of file to save results (IT file for vectors and cfg for settings) 35 35 string filename; 36 37 //! this flag is only to assure reentrance of the finalize() method 38 bool file_saved; 36 39 public: 37 40 //! convenience constructor 38 memlog ( int maxlen0, string fn = "" ) : logger ( "_" ), maxlen ( maxlen0 ), ind ( 0 ), vectors ( 0 ), filename ( fn ) {}41 memlog ( int maxlen0, string fn = "" ) : logger ( "_" ), maxlen ( maxlen0 ), ind ( 0 ), vectors ( 0 ), filename ( fn ), file_saved(false) {} 39 42 40 43 //!Default constructor 41 memlog() : logger ( "_" ), maxlen ( 0 ), ind ( 0 ), vectors ( 0 ) {}44 memlog() : logger ( "_" ), maxlen ( 0 ), ind ( 0 ), vectors ( 0 ), file_saved(false) {} 42 45 43 46 //! Initialize storage … … 66 69 //! 67 70 void finalize() { 68 if ( filename.length() > 0 ) {71 if ( filename.length() > 0 && !file_saved ) { 69 72 itsave ( ( filename + ".it" ).c_str() ); 70 73 if ( settings.length() > 0 ) { 71 74 setting_conf.writeFile ( ( filename + ".cfg" ).c_str() ); 72 75 } 76 file_saved = true; 73 77 } 74 78 … … 153 157 //! Automatically generated 154 158 Array<string> scalarnames; 159 160 //! this flag is only to assure reentrance of the finalize() method 161 bool buffers_written; 155 162 public: 156 163 /*!\brief Default constructor 157 164 @param dirname0 name of the directory in which to store the results 158 165 @param maxlen0 length of the memory buffers, when full the buffers will be dumped to HDD and returned to the beginning. */ 159 dirfilelog ( string dirname0, int maxlen0 ) : memlog ( maxlen0 ), dirname ( dirname0 ), scalarnames ( 0 ) {}166 dirfilelog ( string dirname0, int maxlen0 ) : memlog ( maxlen0 ), dirname ( dirname0 ), scalarnames ( 0 ), buffers_written(false) {} 160 167 161 dirfilelog() {}168 dirfilelog() : buffers_written(false) {} 162 169 163 170 //! Initialize storage -
library/bdm/base/user_info.cpp
r771 r907 235 235 } 236 236 237 void UI::save ( const log_level_base &log_level, Setting &element, const string &name ) { 238 assert_type ( element, Setting::TypeGroup ); 239 240 string string_to_write; 241 242 Setting *list; 243 if( element.exists( name ) ) 244 { 245 list = &element[name]; 246 assert_type ( *list, Setting::TypeString ); 247 string_to_write = ( const char* ) *list; 248 } 249 else 250 list = &element.add ( name, Setting::TypeString ); 251 252 for( unsigned int i = 0; i < log_level.values.size(); i++ ) 253 if( log_level.values[i] ) // a jeste zkontrolovat zda to jmeno uz neni obsazeno? 254 { 255 if( string_to_write.length() > 0 ) 256 string_to_write = string_to_write + ','; 257 string_to_write = string_to_write + log_level.names()(i); 258 } 259 260 *list = string_to_write; 261 } 262 237 263 void UI::from_setting ( mat& matrix, const Setting &element ) { 238 264 const SettingResolver link ( element ); … … 367 393 } 368 394 395 void UI::from_setting ( log_level_base &log_level, const Setting &element ) 396 { 397 string raw_log_level; 398 UI::get( raw_log_level, element ); 399 Array<string> loaded_log_level = log_level_base::string2Array( raw_log_level ); 400 401 log_level.values.reset(); 402 403 for( int i = 0; i < loaded_log_level.length(); i++ ) 404 for( int j = 0; j < log_level.names().length(); j++ ){ 405 if( loaded_log_level(i) == log_level.names()(j) ) 406 { 407 log_level.values[j] = true; 408 break; 409 } 410 } 411 } 412 369 413 }//namespace -
library/bdm/base/user_info.h
r870 r907 304 304 //! This method converts a Setting into a real scalar 305 305 static void from_setting ( double &real, const Setting &element ); 306 307 //! This method converts a Setting into a specific log_level_template<T> variant and initialize options properly 308 template< class T> static void from_setting ( log_level_template<T> &log_level, const Setting &element ) 309 { 310 string raw_log_level; 311 UI::get( raw_log_level, element ); 312 Array<string> loaded_log_level = log_level_template<T>::string2Array( raw_log_level ); 313 314 log_level.values.reset(); 315 316 for( int i = 0; i < loaded_log_level.length(); i++ ) 317 for( int j = 0; j < log_level.names().length(); j++ ){ 318 if( loaded_log_level(i) == log_level.names()(j) ) 319 { 320 log_level.values[j] = true; 321 break; 322 } 323 } 324 } 306 //! This method converts a Setting into a log_level variant and initialize options properly 307 static void from_setting ( log_level_base &log_level, const Setting &element ); 325 308 326 309 //! This method converts a Setting into a class T descendant … … 374 357 375 358 //! This method converts a Setting into a descendant of class 376 //! T, wrapped in an instance of shared_ptr<T> .359 //! T, wrapped in an instance of bdm::shared_ptr<T> . 377 360 template<class T> 378 static void from_setting ( shared_ptr<T> &instance, const Setting &element ) {361 static void from_setting ( bdm::shared_ptr<T> &instance, const Setting &element ) { 379 362 T *tmp_inst = 0; 380 363 from_setting ( tmp_inst, element ); … … 398 381 } 399 382 400 401 383 //! This is dummy version of the from_setting method for other, unsupported types. It just throws an exception. 402 384 //! 403 385 //! At the moment, this is the only way how to compile the library without obtaining the compiler error c2665. 404 386 //! The exception can help to find the place where the template is misused and also to correct it. 405 template<class T> static void from_setting ( T &variable_to_load, const Setting &element ) {406 std::string msg = "UIException: from_setting is not implemented for type ";387 // template<class T> static void from_setting ( T &variable_to_load, const Setting &element ) { 388 // std::string msg = "UIException: from_setting is not implemented for type "; 407 389 // try{ 408 variable_to_load.from_setting(element);390 // variable_to_load.from_setting(element); 409 391 /* } catch (...){ 410 392 msg += typeid ( T ).name(); … … 412 394 throw UISettingException ( msg, element ); 413 395 }*/ 414 }396 // } 415 397 416 398 … … 432 414 //! The new instance of type T* is constructed and initialized with values stored in the Setting element[name] 433 415 //! 434 //! If there is not any sub-element named #name and settingPresence is #optional, an empty shared_ptr<T> is returned. When settingPresence is #compulsory, the returnedshared_ptr<T> is never empty (an exception is thrown when the object isn't found).416 //! If there is not any sub-element named #name and settingPresence is #optional, an empty bdm::shared_ptr<T> is returned. When settingPresence is #compulsory, the returned bdm::shared_ptr<T> is never empty (an exception is thrown when the object isn't found). 435 417 template<class T> 436 static shared_ptr<T> build ( const Setting &element, const string &name, SettingPresence settingPresence = optional ) {418 static bdm::shared_ptr<T> build ( const Setting &element, const string &name, SettingPresence settingPresence = optional ) { 437 419 if ( !element.exists ( name ) ) { 438 420 if ( settingPresence == optional ) 439 return shared_ptr<T>();421 return bdm::shared_ptr<T>(); 440 422 else 441 423 throw UISettingException ( "UIException: the compulsory Setting named \"" + name + "\" is missing.", element ); 442 424 } 443 425 444 shared_ptr<T> instance;426 bdm::shared_ptr<T> instance; 445 427 from_setting<T> ( instance, to_child_setting ( element, name ) ); 446 428 return instance; … … 449 431 //! The new instance of type T* is constructed and initialized with values stored in the Setting element[index] 450 432 //! 451 //! If there is not any sub-element indexed by #index, and settingPresence is #optional, an empty shared_ptr<T> is returned. When settingPresence is #compulsory, the returnedshared_ptr<T> is never empty (an exception is thrown when the object isn't found).433 //! If there is not any sub-element indexed by #index, and settingPresence is #optional, an empty bdm::shared_ptr<T> is returned. When settingPresence is #compulsory, the returned bdm::shared_ptr<T> is never empty (an exception is thrown when the object isn't found). 452 434 template<class T> 453 static shared_ptr<T> build ( const Setting &element, const int index, SettingPresence settingPresence = optional ) {435 static bdm::shared_ptr<T> build ( const Setting &element, const int index, SettingPresence settingPresence = optional ) { 454 436 if ( element.getLength() <= index ) { 455 437 if ( settingPresence == optional ) 456 return shared_ptr<T>();438 return bdm::shared_ptr<T>(); 457 439 else { 458 440 stringstream stream; … … 462 444 } 463 445 464 shared_ptr<T> instance;446 bdm::shared_ptr<T> instance; 465 447 from_setting<T> ( instance, to_child_setting ( element, index ) ); 466 448 return instance; … … 471 453 //! Handy in mex files. Use with care. 472 454 template<class T> 473 static shared_ptr<T> build ( const Setting &element, SettingPresence settingPresence = optional ) {474 shared_ptr<T> instance;455 static bdm::shared_ptr<T> build ( const Setting &element, SettingPresence settingPresence = optional ) { 456 bdm::shared_ptr<T> instance; 475 457 from_setting<T> ( instance, element ); 476 458 return instance; … … 545 527 if ( element.getLength() <= index ) { 546 528 if ( settingPresence == optional ) 547 return shared_ptr<T>();529 return bdm::shared_ptr<T>(); 548 530 else { 549 531 stringstream stream; … … 590 572 } 591 573 592 template< class T> static void save ( const shared_ptr<T> &instance, Setting &element, const string &name = "" ) {574 template< class T> static void save ( const bdm::shared_ptr<T> &instance, Setting &element, const string &name = "" ) { 593 575 save<T> ( instance.get(), element, name ); 594 576 } … … 603 585 } 604 586 605 // The only difference from classical UserInfo approach to log_level_template is the fact 587 //! A matrix(of type mat) is stored in the new child Setting appended to the passed element 588 static void save ( const mat &matrix, Setting &element, const string &name = "" ); 589 590 //! An integer vector (of type ivec) is stored in the new child Setting appended to the passed element 591 static void save ( const ivec &vec, Setting &element, const string &name = "" ); 592 593 //! A double vector (of type vec) is stored in the new child Setting appended to the passed element 594 static void save ( const vec &vector, Setting &element, const string &name = "" ); 595 596 //! A string is stored in the new child Setting appended to the passed element 597 static void save ( const string &str, Setting &element, const string &name = "" ); 598 599 //! An integer is stored in the new child Setting appended to the passed element 600 static void save ( const int &integer, Setting &element, const string &name = "" ); 601 602 //! A double is stored in the new child Setting appended to the passed element 603 static void save ( const double &real, Setting &element, const string &name = "" ); 604 605 // The only difference from classical UserInfo approach to log_level_template is the fact 606 606 // that the actual UI element related to log_level_template could possibly exists yet. In this case, 607 607 // we do not want to throw an exception like in the case of any other type being loaded … … 609 609 // possible that more instances of log_level_template class (templated with different classes) 610 610 // can be stored in only one line in a configuration file 611 template< class T> static void save ( const log_level_template<T> &log_level, Setting &element, const string &name = "log_level" ) { 612 assert_type ( element, Setting::TypeGroup ); 613 614 string string_to_write; 615 616 Setting *list; 617 if( element.exists( name ) ) 618 { 619 list = &element[name]; 620 assert_type ( *list, Setting::TypeString ); 621 string_to_write = ( const char* ) *list; 622 } 623 else 624 list = &element.add ( name, Setting::TypeString ); 625 626 for( unsigned int i = 0; i < log_level.values.size(); i++ ) 627 if( log_level.values[i] ) // a jeste zkontrolovat zda to jmeno uz neni obsazeno? 628 { 629 if( string_to_write.length() > 0 ) 630 string_to_write = string_to_write + ','; 631 string_to_write = string_to_write + log_level.names()(i); 632 } 633 634 *list = string_to_write; 635 } 636 637 638 //! A matrix(of type mat) is stored in the new child Setting appended to the passed element 639 static void save ( const mat &matrix, Setting &element, const string &name = "" ); 640 641 //! An integer vector (of type ivec) is stored in the new child Setting appended to the passed element 642 static void save ( const ivec &vec, Setting &element, const string &name = "" ); 643 644 //! A double vector (of type vec) is stored in the new child Setting appended to the passed element 645 static void save ( const vec &vector, Setting &element, const string &name = "" ); 646 647 //! A string is stored in the new child Setting appended to the passed element 648 static void save ( const string &str, Setting &element, const string &name = "" ); 649 650 //! An integer is stored in the new child Setting appended to the passed element 651 static void save ( const int &integer, Setting &element, const string &name = "" ); 652 653 //! A double is stored in the new child Setting appended to the passed element 654 static void save ( const double &real, Setting &element, const string &name = "" ); 611 static void save ( const log_level_base &log_level, Setting &element, const string &name = "log_level" ); 612 655 613 //!@} 656 614 -
library/bdm/bdmroot.cpp
r769 r907 4 4 namespace bdm { 5 5 6 //! a general utility transforming a comma-separated sequence of strings into an instance of Array<strings> 7 Array<string> log_level_base::string2Array( const string &input ) 8 { 9 string result = input; 10 string::size_type loc; 11 while( loc = result.find( ',' ), loc != string::npos ) 12 result[loc] = ' '; 13 return Array<string>("{ " + result + " }" ); 14 } 15 6 16 void UI_DBG (const Setting &S, const string &spc, ostream &out =cout){ 7 17 const char *Name=S.getName(); -
library/bdm/bdmroot.h
r870 r907 37 37 //! auxiliary function for debugging 38 38 void UI_DBG (const Setting &S, const string &spc, ostream &out ); 39 40 //! This class stores a details that will be logged to a logger 41 template<class T> class log_level_template { 39 40 //forward declaration 41 class logger; 42 43 //! base class for all log_levels 44 //! 45 //! the existence of this class is forced by the necessity of passing log_levels to user_info methods, however, the main functionality 46 //! is located in \c log_level_template class 47 class log_level_base 48 { 42 49 private: 43 50 // UserInfo class have to be able to read all the internal … … 45 52 friend class UI; 46 53 54 protected: 47 55 //! boolean flags related indicating which details will be logged to a logger 48 56 bitset<32> values; 57 58 public: 59 60 //! a general utility transforming a comma-separated sequence of strings into an instance of Array<strings> 61 static Array<string> string2Array( const string &input ); 49 62 50 63 //! string equivalents of the used enumerations which are filled with a help of #LOG_LEVEL macro within class T 51 const Array<string> &names() const 52 { 53 return T::log_level_names(); 54 } 55 56 public: 57 58 //! a general utility transforming a comma-separated sequence of strings into an instance of Array<strings> 59 static Array<string> string2Array( const string &input ) 60 { 61 string result = input; 62 string::size_type loc; 63 while( loc = result.find( ',' ), loc != string::npos ) 64 result[loc] = ' '; 65 return Array<string>("{ " + result + " }" ); 66 } 67 68 //! is any field of log_level active? 69 bool any() const 70 { 71 return values.any(); 72 } 73 74 //! read only operator for testing individual fields of log_level 75 //! 76 //! it is necessary to acces it with a proper enumeration type, thus this approach is type-safe 77 bool operator [] (const enum T::log_level_enums &log_level ) const 78 { 79 return values[log_level]; 80 } 81 82 //! operator for setting an individual field of log_level 83 //! 84 //! it is necessary to acces it with a proper enumeration type, thus this approach is type-safe 85 bitset<32>::reference operator [] (const enum T::log_level_enums &log_level ) 86 { 87 return values[log_level]; 88 } 64 virtual const Array<string> &names() const = 0; 89 65 }; 90 66 91 /*!92 \def LOG_LEVEL(classname,...)93 \brief Macro for defining a log_level attribute with a specific set of enumerations related to a specific class94 95 This macro has to be called within a class declaration. Its argument \a classname has to correspond to that wrapping class.96 This macro defines a log_level instance which can be modified either directly or by the means of #UI class.97 98 One of the main purposes of this macro is to allow variability in using enumerations. By relating them to their names through99 an array of strings, we are no more dependant on their precise ordering. What is more, we can add or remove any without harming100 any applications which are using this library.101 102 \todo Write a more detailed explanation including also examples103 104 \ref ui105 */106 #define LOG_LEVEL(classname,...) public: enum log_level_enums { __VA_ARGS__ }; log_level_template<classname> log_level; private: friend class log_level_template<classname>; static const Array<string> &log_level_names() { static const Array<string> log_level_names = log_level_template<classname>::string2Array( #__VA_ARGS__ ); return log_level_names; }107 108 //forward declaration109 class logger;110 111 //! information about connection to a logger112 class log_record {113 public:114 //!remember which logger is registered115 logger &L;116 //! vector of log IDs - one element for each entry117 ivec ids;118 119 //!default constructor120 log_record ( logger &L0 ) : L ( L0 ), ids ( 0 ) {}121 };122 67 123 68 //! Root class of BDM objects … … 127 72 friend class UI; 128 73 129 //! This method is a dummy method closely related to to the #LOG_LEVEL macro, do not remove it130 static const string &log_level_names()131 {132 static const string log_level_names;133 return log_level_names;134 };135 136 74 protected: 137 //! record of connections to the logger138 log _record* logrec;75 //!remember which logger is registered 76 logger * registered_logger; 139 77 140 78 /*! … … 217 155 218 156 public: 219 //! This enumeration defines all possible options specifing the level of details logged by a logger about this specific class 220 //! 221 //! It has to be reimplemented in descendant classes using the #LOG_LEVEL macro 222 enum log_level_enums { }; 223 157 224 158 //!default constructor 225 root() : logrec( NULL ) {};159 root() : registered_logger ( NULL ) {}; 226 160 227 161 //! make sure this is a virtual object 228 162 virtual ~root() { 229 if ( logrec ) delete logrec;230 163 } 231 164 … … 242 175 //! The level of details (parameter \c level ) is individual for each class. 243 176 virtual void log_register ( logger &L, const string &prefix ) { 244 logrec = new log_record ( L );177 registered_logger = &L; 245 178 } 246 179 247 180 //! Write current information into the given logger 248 181 virtual void log_write() const { 249 } 182 } 250 183 251 184 /*! -
library/bdm/design/ctrlbase.h
r738 r907 36 36 37 37 void from_setting ( const Setting &set ) { 38 UI::get ( rv, set, "rv", UI::optional ); 39 UI::get ( rvc, set, "rvc", UI::optional ); 38 shared_ptr<RV> rv_ptr = UI::build<RV>( set, "rv", UI::optional ); 39 if( rv_ptr ) rv = *rv_ptr; 40 shared_ptr<RV> rvc_ptr = UI::build<RV>( set, "rvc", UI::optional ); 41 if( rvc_ptr ) rvc = *rvc_ptr; 40 42 } 41 43 //! access function -
library/bdm/estim/kalman.cpp
r884 r907 120 120 vec &_yp = fy._mu(); 121 121 //TODO get rid of Q in qr()! 122 // mat Q;122 // mat Q; 123 123 124 124 //R and Q are already set in set_parameters() -
library/bdm/estim/kalman.h
r896 r907 139 139 set_statistics ( mu0, P0 ); 140 140 // Initial values 141 UI::get ( yrv,set, "yrv", UI::optional );142 UI::get ( rvc, set, "urv", UI::optional);143 s et_yrv ( concat ( yrv, rvc ));144 145 validate();141 shared_ptr<RV> yrv_ptr = UI::build<RV>( set, "yrv", UI::optional ); 142 if( !yrv_ptr ) yrv_ptr = new RV(); 143 shared_ptr<RV> rvc_ptr = UI::build<RV>( set, "urv", UI::optional ); 144 if( !rvc_ptr ) rvc_ptr = new RV(); 145 set_yrv ( concat ( *yrv_ptr, *rvc_ptr ) ); 146 146 } 147 147 //! validate object -
library/bdm/estim/particles.h
r900 r907 579 579 // void log_register( logger &L, const string &prefix ){ 580 580 // BM::log_register(L,prefix); 581 // logrec->ids.set_size ( 3 );582 // logrec->ids(1)= L.add_vector(RV("Q",dimension()*dimension()), prefix+L.prefix_sep()+"Q");583 // logrec->ids(2)= L.add_vector(RV("R",dimensiony()*dimensiony()), prefix+L.prefix_sep()+"R");581 // registered_logger->ids.set_size ( 3 ); 582 // registered_logger->ids(1)= L.add_vector(RV("Q",dimension()*dimension()), prefix+L.prefix_sep()+"Q"); 583 // registered_logger->ids(2)= L.add_vector(RV("R",dimensiony()*dimensiony()), prefix+L.prefix_sep()+"R"); 584 584 // 585 585 // }; … … 599 599 // 600 600 // } 601 // logrec->L.log_vector ( logrec->ids ( 1 ), cvectorize(mQ) );602 // logrec->L.log_vector ( logrec->ids ( 2 ), cvectorize(mR) );601 // registered_logger->L.log_vector ( registered_logger->ids ( 1 ), cvectorize(mQ) ); 602 // registered_logger->L.log_vector ( registered_logger->ids ( 2 ), cvectorize(mR) ); 603 603 // 604 604 // } -
library/bdm/stat/exp_family.cpp
r889 r907 298 298 299 299 void egiw::log_register ( bdm::logger& L, const string& prefix ) { 300 if ( log_level[ tri] ) {300 if ( log_level[logmean] || log_level[logvariance] ) { 301 301 root::log_register ( L, prefix ); 302 logrec->ids.set_length ( 2 );303 302 int th_dim = dimension() - dimx * ( dimx + 1 ) / 2; 304 logrec->ids ( 0 ) = L.add_vector ( RV ( "", th_dim ), prefix, "mean" ); 305 logrec->ids ( 1 ) = L.add_vector ( RV ( "", th_dim * th_dim ), prefix, "variance" ); 303 304 if ( log_level[logmean] ) 305 registered_logger->add_vector( log_level, logmean, RV ( th_dim ), prefix ); 306 if ( log_level[logvariance] ) 307 registered_logger->add_vector( log_level, logvariance, RV ( th_dim * th_dim ), prefix ); 306 308 } else { 307 309 epdf::log_register ( L, prefix ); … … 310 312 311 313 void egiw::log_write() const { 312 if ( log_level[ tri] ) {314 if ( log_level[logmean] || log_level[logvariance] ) { 313 315 mat M; 314 316 ldmat Lam; 315 317 ldmat Vz; 316 318 factorize ( M, Vz, Lam ); 317 logrec->L.log_vector ( logrec->ids ( 0 ), est_theta() ); 318 logrec->L.log_vector ( logrec->ids ( 1 ), cvectorize ( est_theta_cov().to_mat() ) ); 319 if( log_level[logmean] ) 320 log_level.store( logmean, est_theta() ); 321 if( log_level[logvariance] ) 322 log_level.store( logvariance, cvectorize ( est_theta_cov().to_mat() ) ); 319 323 } else { 320 324 epdf::log_write(); 321 325 } 322 323 326 } 324 327 -
library/bdm/stat/exp_family.h
r900 r907 102 102 BM::to_setting( set ); 103 103 UI::save(frg, set, "frg"); 104 // TODO DOPLNIT? ALE MOMENTALNE CHYBI FROM_SETTING PRO INSPIRACI105 104 } 105 106 106 void from_setting( const Setting &set) { 107 107 BM::from_setting(set); 108 108 if ( !UI::get ( frg, set, "frg" ) ) 109 109 frg = 1.0; 110 111 110 } 112 111 … … 349 348 */ 350 349 class egiw : public eEF { 351 //! \var log_level_enums tri350 //! \var log_level_enums logvariance 352 351 //! TODO DOPLNIT 353 LOG_LEVEL(egiw,tri); 352 353 //! \var log_level_enums logmean 354 //! TODO DOPLNIT 355 LOG_LEVEL(egiw,logmean, logvariance); 354 356 355 357 protected: -
library/tests/CMakeLists.txt
r722 r907 1 1 # Make sure the compiler can find include files from our Bdm library. 2 2 include_directories (${BDM_SOURCE_DIR}/bdm) 3 include_directories ( ./unittest-cpp)3 include_directories (${BDM_SOURCE_DIR}/tests/unittest-cpp) 4 4 5 5 # Make sure the linker can find the Hello library once it is built. 6 6 link_directories (${BDM_BINARY_DIR}/bdm) 7 link_directories ( ./unittest-cpp)7 link_directories (${BDM_BINARY_DIR}/tests/unittest-cpp) 8 8 9 9 SET(testutil_src general_suite.cpp general_suite.h epdf_harness.cpp epdf_harness.h mat_checks.cpp mat_checks.h -
library/tests/testsuite/datasource_test.cpp
r795 r907 8 8 TEST ( EpdfDS_test ) { 9 9 UIFile uif ( "epdfds.cfg" ); 10 11 10 shared_ptr<EpdfDS> ds = UI::build<EpdfDS> ( uif, "ds" ); 12 11 -
library/tests/testsuite/logger_test.cpp
r737 r907 32 32 } 33 33 34 class log_tester : public root 35 { 36 LOG_LEVEL(log_tester,logr,logth,logpol); 37 public: 38 RV th, r; 39 int pol, i; 40 41 log_tester() { 42 th = RV ( "{alog blog }" ); 43 r = RV ( "{r }", "2" ); 44 pol = 11; 45 46 log_level[logr] = true; 47 log_level[logth] = true; 48 log_level[logpol] = true; 49 } 50 51 void log_register( logger &L, const string prefix ) { 52 root::log_register( L, prefix ); 53 L.add_vector( log_level, logr, r, prefix ); 54 L.add_vector( log_level, logth, th, prefix ); 55 L.add_setting( log_level, logpol, prefix ); 56 } 57 58 void log_write() const { 59 root::log_write(); 60 log_level.store( logr, vec_2 ( ( double ) i, ( double ) ( i + 1 ) ) ); 61 log_level.store( logth, vec_2 ( ( double ) ( 100 - i ), ( double ) ( i - 50 ) ) ); 62 log_level.store( logpol, pol ); 63 } 64 65 }; 66 34 67 TEST ( memlog_test ) { 35 RV th = RV ( "{alog blog }" );36 RV r = RV ( "{r }", "2" );37 38 68 string ls ( "memlog_test" ); 39 69 remove_all ( ls.c_str() ); … … 41 71 memlog logger ( 100, ls ); 42 72 43 int pol = 11;44 73 45 int rid = logger.add_vector ( r, "" ); 46 int thid = logger.add_vector ( th, "th" ); 47 int polid = logger.add_setting ( "pols" ); 48 74 log_tester tester; 75 tester.log_register( logger, "memlog" ); 76 49 77 logger.init(); 50 78 51 for ( int i = 0; i < 10; i++ ) { 52 logger.log_vector ( rid, vec_2 ( ( double ) i, ( double ) ( i + 1 ) ) ); 53 logger.log_vector ( thid, vec_2 ( ( double ) ( 100 - i ), ( double ) ( i - 50 ) ) ); 54 UI::save ( pol, logger.log_to_setting ( polid ), "polozka" ); 79 for ( tester.i = 0; tester.i < 10; tester.i++ ) { 80 tester.log_write(); 55 81 logger.step(); 56 82 } … … 63 89 64 90 TEST ( dirfilelog_test ) { 65 RV th = RV ( "{alog blog }" ); 66 RV r = RV ( "{r }", "2" ); 91 67 92 68 93 string ls ( "exp" ); … … 71 96 remove_all ( "dirfilelog_files" ); 72 97 73 dirfilelog L( "dirfilelog_files", 10 );98 dirfilelog logger ( "dirfilelog_files", 10 ); 74 99 75 int rid = L.add_vector ( r, "" );76 int thid = L.add_vector ( th, "th" );100 log_tester tester; 101 tester.log_register( logger, "dirfilelog" ); 77 102 78 L.init();103 logger.init(); 79 104 80 for ( int i = 0; i < 150; i++ ) { 81 L.log_vector ( rid, vec_2 ( ( double ) i, ( double ) ( i + 1 ) ) ); 82 L.log_vector ( thid, vec_2 ( ( double ) ( 100 - i ), ( double ) ( i - 50 ) ) ); 83 L.step(); 105 for ( tester.i = 0; tester.i < 150; tester.i++ ) { 106 tester.log_write(); 107 logger.step(); 84 108 } 85 109 86 L.finalize();110 logger.finalize(); 87 111 88 112 std::string expected ( load_test_file ( "logger_test_dirfile_format.matrix" ) );