00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018 #include <string>
00019 #include <sstream>
00020 #include <iostream>
00021 #include <fstream>
00022 #include <algorithm>
00023 #include <functional>
00024 #include <limits>
00025 #include <cmath>
00026 #include <ctime>
00027
00028
00029
00030 #include "QuasiNewtonMethod.h"
00031
00032 namespace Flood
00033 {
00034
00035
00036
00041
00042 QuasiNewtonMethod::QuasiNewtonMethod(ObjectiveFunctional* new_objective_functional_pointer)
00043 : TrainingAlgorithm(new_objective_functional_pointer)
00044 {
00045
00046
00047 inverse_Hessian_approximation_method = BFGS;
00048 }
00049
00050
00051
00052
00056
00057 QuasiNewtonMethod::QuasiNewtonMethod(void) : TrainingAlgorithm()
00058 {
00059
00060
00061 inverse_Hessian_approximation_method = BFGS;
00062 }
00063
00064
00065
00066
00068
00069 QuasiNewtonMethod::~QuasiNewtonMethod(void)
00070 {
00071 }
00072
00073
00074
00075
00076
00077
00078
00080
00081 QuasiNewtonMethod::InverseHessianApproximationMethod QuasiNewtonMethod::get_inverse_Hessian_approximation_method(void)
00082 {
00083 return(inverse_Hessian_approximation_method);
00084 }
00085
00086
00087
00088
00090
00091 std::string QuasiNewtonMethod::get_inverse_Hessian_approximation_method_name(void)
00092 {
00093 switch(inverse_Hessian_approximation_method)
00094 {
00095 case DFP:
00096 {
00097 return("DFP");
00098 }
00099 break;
00100
00101 case BFGS:
00102 {
00103 return("BFGS");
00104 }
00105 break;
00106
00107 default:
00108 {
00109 std::cerr << "Flood Error: QuasiNewtonMethod class." << std::endl
00110 << "std::string get_inverse_Hessian_approximation_method_name(void) method." << std::endl
00111 << "Unknown inverse Hessian approximation method." << std::endl;
00112
00113 exit(1);
00114 }
00115 break;
00116 }
00117 }
00118
00119
00120
00121
00124
00125 void QuasiNewtonMethod::set_inverse_Hessian_approximation_method(const QuasiNewtonMethod::InverseHessianApproximationMethod&
00126 new_inverse_Hessian_approximation_method)
00127 {
00128 inverse_Hessian_approximation_method = new_inverse_Hessian_approximation_method;
00129 }
00130
00131
00132
00133
00141
00142 void QuasiNewtonMethod::set_inverse_Hessian_approximation_method(const std::string& new_inverse_Hessian_approximation_method_name)
00143 {
00144 if(new_inverse_Hessian_approximation_method_name == "DFP")
00145 {
00146 inverse_Hessian_approximation_method = DFP;
00147 }
00148 else if(new_inverse_Hessian_approximation_method_name == "BFGS")
00149 {
00150 inverse_Hessian_approximation_method = BFGS;
00151 }
00152 else
00153 {
00154 std::cerr << "Flood Error: QuasiNewtonMethod class." << std::endl
00155 << "void set_inverse_Hessian_approximation_method(const std::string&) method." << std::endl
00156 << "Unknown inverse Hessian approximation method: " << new_inverse_Hessian_approximation_method_name << "." <<std::endl;
00157
00158 exit(1);
00159 }
00160 }
00161
00162
00163
00164
00168
00169 void QuasiNewtonMethod::set_reserve_all_training_history(bool new_reserve_all_training_history)
00170 {
00171 reserve_elapsed_time_history = new_reserve_all_training_history;
00172 reserve_parameters_history = new_reserve_all_training_history;
00173 reserve_parameters_norm_history = new_reserve_all_training_history;
00174 reserve_evaluation_history = new_reserve_all_training_history;
00175 reserve_gradient_history = new_reserve_all_training_history;
00176 reserve_gradient_norm_history = new_reserve_all_training_history;
00177 reserve_training_direction_history = new_reserve_all_training_history;
00178 reserve_training_rate_history = new_reserve_all_training_history;
00179 }
00180
00181
00182
00183
00186
00187 void QuasiNewtonMethod::resize_training_history(int new_size)
00188 {
00189
00190
00191 if(reserve_parameters_history)
00192 {
00193 parameters_history.resize(new_size);
00194 }
00195
00196 if(reserve_parameters_norm_history)
00197 {
00198 parameters_norm_history.resize(new_size);
00199 }
00200
00201
00202
00203 if(reserve_evaluation_history)
00204 {
00205 evaluation_history.resize(new_size);
00206 }
00207
00208 if(reserve_gradient_history)
00209 {
00210 gradient_history.resize(new_size);
00211 }
00212
00213 if(reserve_gradient_norm_history)
00214 {
00215 gradient_norm_history.resize(new_size);
00216 }
00217
00218 if(reserve_inverse_Hessian_history)
00219 {
00220 inverse_Hessian_history.resize(new_size);
00221 }
00222
00223 if(reserve_validation_error_history)
00224 {
00225 validation_error_history.resize(new_size);
00226 }
00227
00228
00229
00230 if(reserve_training_direction_history)
00231 {
00232 training_direction_history.resize(new_size);
00233 }
00234
00235 if(reserve_training_rate_history)
00236 {
00237 training_rate_history.resize(new_size);
00238 }
00239
00240 if(reserve_elapsed_time_history)
00241 {
00242 elapsed_time_history.resize(new_size);
00243 }
00244 }
00245
00246
00247
00248
00252
00253 std::string QuasiNewtonMethod::get_training_history_XML(bool show_declaration)
00254 {
00255 std::stringstream buffer;
00256
00257
00258
00259 if(show_declaration)
00260 {
00261 buffer << "<Flood version='3.0' class='QuasiNewtonMethod' content='TrainingHistory'>" << std::endl;
00262 }
00263
00264
00265
00266 if(reserve_parameters_history)
00267 {
00268 buffer << "<ParametersHistory>" << std::endl;
00269
00270 for(int i = 0; i < parameters_history.get_size(); i++)
00271 {
00272 buffer << parameters_history[i] << std::endl;
00273 }
00274
00275 buffer << "</ParametersHistory>" << std::endl;
00276 }
00277
00278 if(reserve_parameters_norm_history)
00279 {
00280 buffer << "<ParametersNormHistory>" << std::endl
00281 << parameters_norm_history << std::endl
00282 << "</ParametersNormHistory>" << std::endl;
00283 }
00284
00285
00286
00287 if(reserve_evaluation_history)
00288 {
00289 buffer << "<EvaluationHistory>" << std::endl
00290 << evaluation_history << std::endl
00291 << "</EvaluationHistory>" << std::endl;
00292 }
00293
00294 if(reserve_gradient_history)
00295 {
00296 buffer << "<GradientHistory>" << std::endl;
00297
00298 for(int i = 0; i < gradient_history.get_size(); i++)
00299 {
00300 buffer << gradient_history[i] << std::endl;
00301 }
00302
00303 buffer << "</GradientHistory>" << std::endl;
00304 }
00305
00306 if(reserve_gradient_norm_history)
00307 {
00308 buffer << "<GradientNormHistory>" << std::endl
00309 << gradient_norm_history << std::endl
00310 << "</GradientNormHistory>" << std::endl;
00311 }
00312
00313 if(reserve_inverse_Hessian_history)
00314 {
00315 buffer << "<InverseHessianHistory>" << std::endl;
00316
00317 int size = inverse_Hessian_history.get_size();
00318
00319 for(int i = 0; i < size; i++)
00320 {
00321 buffer << "<InverseHessian>" << std::endl
00322 << inverse_Hessian_history[i] << std::endl
00323 << "</InverseHessian>" << std::endl;
00324 }
00325
00326 buffer << "</InverseHessianHistory>" << std::endl;
00327 }
00328
00329
00330
00331 if(reserve_training_direction_history)
00332 {
00333 buffer << "<TrainingDirectionHistory>" << std::endl;
00334
00335 for(int i = 0; i < training_direction_history.get_size(); i++)
00336 {
00337 buffer << training_direction_history[i] << std::endl;
00338 }
00339
00340 buffer << "</TrainingDirectionHistory>" << std::endl;
00341 }
00342
00343 if(reserve_training_rate_history)
00344 {
00345 buffer << "<TrainingRateHistory>" << std::endl
00346 << training_rate_history << std::endl
00347 << "</TrainingRateHistory>" << std::endl;
00348 }
00349
00350 if(reserve_elapsed_time_history)
00351 {
00352 buffer << "<ElapsedTimeHistory>" << std::endl
00353 << elapsed_time_history << std::endl
00354 << "</ElapsedTimeHistory>" << std::endl;
00355 }
00356
00357 if(reserve_validation_error_history)
00358 {
00359 buffer << "<ValidationErrorHistory>" << std::endl
00360 << validation_error_history << std::endl
00361 << "</ValidationErrorHistory>" << std::endl;
00362 }
00363
00364 return(buffer.str());
00365 }
00366
00367
00368
00369
00370
00371
00372
00379
00380 Matrix<double> QuasiNewtonMethod::calculate_inverse_Hessian_approximation(
00381 const Vector<double>& old_parameters, const Vector<double>& parameters,
00382 const Vector<double>& old_gradient, const Vector<double>& gradient,
00383 const Matrix<double>& old_inverse_Hessian)
00384 {
00385 switch(inverse_Hessian_approximation_method)
00386 {
00387 case DFP:
00388 {
00389 return(objective_functional_pointer->calculate_DFP_inverse_Hessian(old_parameters, parameters, old_gradient, gradient, old_inverse_Hessian));
00390 }
00391 break;
00392
00393 case BFGS:
00394 {
00395 return(objective_functional_pointer->calculate_BFGS_inverse_Hessian(old_parameters, parameters, old_gradient, gradient, old_inverse_Hessian));
00396 }
00397 break;
00398
00399 default:
00400 {
00401 std::cerr << "Flood Error: QuasiNewtonMethod class." << std::endl
00402 << "Vector<double> calculate_inverse_Hessian_approximation(const Vector<double>&, const Vector<double>&, const Vector<double>&, const Vector<double>&, const Matrix<double>&) method." << std::endl
00403 << "Unknown inverse Hessian approximation method." << std::endl;
00404
00405 exit(1);
00406 }
00407 break;
00408 }
00409 }
00410
00411
00412
00413
00414 Vector<double> QuasiNewtonMethod::calculate_training_direction(const Vector<double>& gradient, const Matrix<double>& inverse_Hessian)
00415 {
00416 Vector<double> training_direction = inverse_Hessian.dot(gradient)*(-1.0);
00417
00418 double training_direction_norm = training_direction.calculate_norm();
00419
00420 return(training_direction/training_direction_norm);
00421 }
00422
00423
00424
00425
00426 Vector<double> QuasiNewtonMethod::calculate_gradient_descent_training_direction(const Vector<double>& gradient)
00427 {
00428 double gradient_norm = gradient.calculate_norm();
00429
00430 return(gradient/(-1.0*gradient_norm));
00431 }
00432
00433
00434
00435
00439
00440 void QuasiNewtonMethod::train(void)
00441 {
00442
00443
00444 #ifdef _DEBUG
00445
00446 if(objective_functional_pointer == NULL)
00447 {
00448 std::cerr << "Flood Error: QuasiNewtonMethod class." << std::endl
00449 << "void train(void) method." << std::endl
00450 << "Pointer to objective functional object cannot be NULL." << std::endl;
00451
00452 exit(1);
00453 }
00454
00455 #endif
00456
00457
00458
00459 if(display)
00460 {
00461 std::cout << "Training with quasi-Newton method..." << std::endl;
00462 }
00463
00464
00465
00466 MultilayerPerceptron* multilayer_perceptron_pointer = objective_functional_pointer->get_multilayer_perceptron_pointer();
00467
00468 int parameters_number = multilayer_perceptron_pointer->get_parameters_number();
00469
00470 Vector<double> parameters(parameters_number);
00471 Vector<double> old_parameters(parameters_number);
00472 double parameters_norm;
00473
00474 Vector<double> parameters_increment(parameters_number);
00475 double parameters_increment_norm;
00476
00477
00478
00479 double validation_error = 0.0;
00480 double old_validation_error = 0.0;
00481 double validation_error_increment = 0.0;
00482
00483 double evaluation = 0.0;
00484 double old_evaluation = 0.0;
00485 double evaluation_improvement = 0.0;
00486
00487 Vector<double> gradient(parameters_number);
00488 Vector<double> old_gradient(parameters_number);
00489 double gradient_norm;
00490
00491 Matrix<double> inverse_Hessian(parameters_number, parameters_number);
00492 Matrix<double> old_inverse_Hessian(parameters_number, parameters_number);
00493
00494
00495
00496 Vector<double> training_direction(parameters_number);
00497
00498 double training_slope;
00499
00500 double initial_training_rate = 0.0;
00501 double training_rate = 0.0;
00502 double old_training_rate = 0.0;
00503
00504 Vector<double> training_rate_evaluation(2);
00505
00506 bool stop_training = false;
00507
00508 time_t beginning_time, current_time;
00509 time(&beginning_time);
00510 double elapsed_time;
00511
00512 resize_training_history(maximum_epochs_number+1);
00513
00514
00515
00516 for(int epoch = 0; epoch <= maximum_epochs_number; epoch++)
00517 {
00518
00519
00520 parameters = multilayer_perceptron_pointer->get_parameters();
00521
00522 parameters_norm = parameters.calculate_norm();
00523
00524 if(display && parameters_norm >= warning_parameters_norm)
00525 {
00526 std::cout << "Flood Warning: Parameters norm is " << parameters_norm << "." << std::endl;
00527 }
00528
00529
00530
00531 if(epoch == 0)
00532 {
00533 evaluation = objective_functional_pointer->calculate_evaluation();
00534 evaluation_improvement = 0.0;
00535 }
00536 else
00537 {
00538 evaluation = training_rate_evaluation[1];
00539 evaluation_improvement = old_evaluation - evaluation;
00540 }
00541
00542 validation_error = objective_functional_pointer->calculate_validation_error();
00543
00544 if(epoch == 0)
00545 {
00546 validation_error_increment = 0.0;
00547 }
00548 else
00549 {
00550 validation_error_increment = validation_error - old_validation_error;
00551 }
00552
00553 gradient = objective_functional_pointer->calculate_gradient();
00554
00555 gradient_norm = gradient.calculate_norm();
00556
00557 if(display && gradient_norm >= warning_gradient_norm)
00558 {
00559 std::cout << "Flood Warning: Gradient norm is " << gradient_norm << "." << std::endl;
00560 }
00561
00562 if(epoch == 0)
00563 {
00564 inverse_Hessian.set_to_identity();
00565 }
00566 else
00567 {
00568 inverse_Hessian = calculate_inverse_Hessian_approximation(old_parameters, parameters, old_gradient, gradient, old_inverse_Hessian);
00569 }
00570
00571
00572
00573 training_direction = calculate_training_direction(gradient, inverse_Hessian);
00574
00575
00576
00577 training_slope = (gradient/gradient_norm).dot(training_direction);
00578
00579
00580
00581 if(training_slope >= 0.0)
00582 {
00583
00584
00585 training_direction = calculate_gradient_descent_training_direction(gradient);
00586 }
00587
00588
00589
00590 if(epoch == 0)
00591 {
00592 initial_training_rate = first_training_rate;
00593 }
00594 else
00595 {
00596 initial_training_rate = old_training_rate;
00597 }
00598
00599 training_rate_evaluation = calculate_training_rate_evaluation(evaluation, training_direction, initial_training_rate);
00600
00601 training_rate = training_rate_evaluation[0];
00602
00603 if(epoch != 0 && training_rate < 1.0e-99)
00604 {
00605
00606
00607 training_direction = calculate_gradient_descent_training_direction(gradient);
00608
00609 training_rate_evaluation = calculate_training_rate_evaluation(evaluation, training_direction, first_training_rate);
00610
00611 training_rate = training_rate_evaluation[0];
00612 }
00613
00614 parameters_increment = training_direction*training_rate;
00615 parameters_increment_norm = parameters_increment.calculate_norm();
00616
00617
00618
00619 time(¤t_time);
00620 elapsed_time = difftime(current_time, beginning_time);
00621
00622
00623
00624 if(reserve_parameters_history)
00625 {
00626 parameters_history[epoch] = parameters;
00627 }
00628
00629 if(reserve_parameters_norm_history)
00630 {
00631 parameters_norm_history[epoch] = parameters_norm;
00632 }
00633
00634
00635
00636 if(reserve_evaluation_history)
00637 {
00638 evaluation_history[epoch] = evaluation;
00639 }
00640
00641 if(reserve_validation_error_history)
00642 {
00643 validation_error_history[epoch] = validation_error;
00644 }
00645
00646 if(reserve_gradient_history)
00647 {
00648 gradient_history[epoch] = gradient;
00649 }
00650
00651 if(reserve_gradient_norm_history)
00652 {
00653 gradient_norm_history[epoch] = gradient_norm;
00654 }
00655
00656 if(reserve_inverse_Hessian_history)
00657 {
00658 inverse_Hessian_history[epoch] = inverse_Hessian;
00659 }
00660
00661
00662
00663 if(reserve_training_direction_history)
00664 {
00665 training_direction_history[epoch] = training_direction;
00666 }
00667
00668 if(reserve_training_rate_history)
00669 {
00670 training_rate_history[epoch] = training_rate;
00671 }
00672
00673 if(reserve_elapsed_time_history)
00674 {
00675 elapsed_time_history[epoch] = elapsed_time;
00676 }
00677
00678
00679
00680 if(parameters_increment_norm <= minimum_parameters_increment_norm)
00681 {
00682 if(display)
00683 {
00684 std::cout << "Epoch " << epoch << ": Minimum parameters increment norm reached." << std::endl
00685 << "Parameters increment norm: " << parameters_increment_norm << std::endl;
00686 }
00687
00688 stop_training = true;
00689 }
00690
00691 if(epoch != 0 && evaluation_improvement <= minimum_evaluation_improvement)
00692 {
00693 if(display)
00694 {
00695 std::cout << "Epoch " << epoch << ": Minimum evaluation improvement reached." << std::endl;
00696 std::cout << "Evaluation improvement: " << evaluation_improvement << std::endl;
00697 }
00698
00699 stop_training = true;
00700 }
00701
00702 else if(evaluation <= evaluation_goal)
00703 {
00704 if(display)
00705 {
00706 std::cout << "Epoch " << epoch << ": Evaluation goal reached." << std::endl;
00707 }
00708
00709 stop_training = true;
00710 }
00711
00712 else if(early_stopping && epoch != 0 && validation_error_increment > 0.0)
00713 {
00714 if(display)
00715 {
00716 std::cout << "Epoch " << epoch << ": Validation error stopped improving." << std::endl;
00717 std::cout << "Validation error increment: "<< validation_error_increment << std::endl;
00718 }
00719
00720 stop_training = true;
00721 }
00722
00723 else if(gradient_norm <= gradient_norm_goal)
00724 {
00725 if(display)
00726 {
00727 std::cout << "Epoch " << epoch << ": Gradient norm goal reached." << std::endl;
00728 }
00729
00730 stop_training = true;
00731 }
00732
00733 else if(epoch == maximum_epochs_number)
00734 {
00735 if(display)
00736 {
00737 std::cout << "Epoch " << epoch << ": Maximum number of epochs reached." << std::endl;
00738 }
00739
00740 stop_training = true;
00741 }
00742
00743 else if(elapsed_time >= maximum_time)
00744 {
00745 if(display)
00746 {
00747 std::cout << "Epoch " << epoch << ": Maximum training time reached." << std::endl;
00748 }
00749
00750 stop_training = true;
00751 }
00752
00753 if(stop_training)
00754 {
00755 if(display)
00756 {
00757 std::cout << "Parameters norm: " << parameters_norm << std::endl;
00758
00759 std::cout << "Evaluation: " << evaluation << std::endl;
00760
00761 if(validation_error != 0)
00762 {
00763 std::cout << "Validation error: " << validation_error << std::endl;
00764 }
00765
00766 std::cout << "Gradient norm: " << gradient_norm << std::endl;
00767
00768 objective_functional_pointer->print_information();
00769
00770 std::cout << "Training rate: " << training_rate << std::endl
00771 << "Elapsed time: " << elapsed_time << std::endl;
00772 }
00773
00774 resize_training_history(1+epoch);
00775
00776 break;
00777 }
00778 else if(display && epoch % display_period == 0)
00779 {
00780 std::cout << "Epoch " << epoch << ";" << std::endl;
00781
00782 std::cout << "Parameters norm: " << parameters_norm << std::endl;
00783
00784 std::cout << "Evaluation: " << evaluation << std::endl;
00785
00786 if(validation_error != 0)
00787 {
00788 std::cout << "Validation error: " << validation_error << std::endl;
00789 }
00790
00791 std::cout << "Gradient norm: " << gradient_norm << std::endl;
00792
00793 objective_functional_pointer->print_information();
00794
00795 std::cout << "Training rate: " << training_rate << std::endl
00796 << "Elapsed time: " << elapsed_time << std::endl;
00797 }
00798
00799
00800
00801 old_parameters = parameters;
00802
00803 old_evaluation = evaluation;
00804
00805 old_gradient = gradient;
00806
00807 old_inverse_Hessian = inverse_Hessian;
00808
00809 old_training_rate = training_rate;
00810
00811 if(early_stopping)
00812 {
00813 old_validation_error = validation_error;
00814 }
00815
00816
00817
00818 parameters += parameters_increment;
00819
00820 multilayer_perceptron_pointer->set_parameters(parameters);
00821
00822 }
00823 }
00824
00825
00826
00827
00832
00833 std::string QuasiNewtonMethod::to_XML(bool show_declaration)
00834 {
00835 std::stringstream buffer;
00836
00837 if(show_declaration)
00838 {
00839 buffer << "<Flood version='3.0' class='QuasiNewtonMethod'>" << std::endl;
00840 }
00841
00842
00843
00844 buffer << "<InverseHessianApproximationMethod>" << std::endl
00845 << get_inverse_Hessian_approximation_method_name() << std::endl
00846 << "</InverseHessianApproximationMethod>" << std::endl;
00847
00848 buffer << "<TrainingRateMethod>" << std::endl
00849 << get_training_rate_method_name() << std::endl
00850 << "</TrainingRateMethod>" << std::endl;
00851
00852
00853
00854 buffer << "<FirstTrainingRate> " << std::endl
00855 << first_training_rate << std::endl
00856 << "</FirstTrainingRate> " << std::endl;
00857
00858 buffer << "<TrainingRateTolerance>" << std::endl
00859 << training_rate_tolerance << std::endl
00860 << "</TrainingRateTolerance>" << std::endl;
00861
00862 buffer << "<WarningParametersNorm>" << std::endl
00863 << warning_parameters_norm << std::endl
00864 << "</WarningParametersNorm>" << std::endl;
00865
00866 buffer << "<WarningGradientNorm>" << std::endl
00867 << warning_gradient_norm << std::endl
00868 << "</WarningGradientNorm>" << std::endl;
00869
00870 buffer << "<WarningTrainingRate>" << std::endl
00871 << warning_training_rate << std::endl
00872 << "</WarningTrainingRate>" << std::endl;
00873
00874 buffer << "<ErrorParametersNorm>" << std::endl
00875 << error_parameters_norm << std::endl
00876 << "</ErrorParametersNorm>" << std::endl;
00877
00878 buffer << "<ErrorGradientNorm>" << std::endl
00879 << error_gradient_norm << std::endl
00880 << "</ErrorGradientNorm>" << std::endl;
00881
00882 buffer << "<ErrorTrainingRate>" << std::endl
00883 << error_training_rate << std::endl
00884 << "</ErrorTrainingRate>" << std::endl;
00885
00886
00887
00888 buffer << "<EvaluationGoal>" << std::endl
00889 << evaluation_goal << std::endl
00890 << "</EvaluationGoal>" << std::endl;
00891
00892 buffer << "<EarlyStopping>" << std::endl
00893 << early_stopping << std::endl
00894 << "</EarlyStopping>" << std::endl;
00895
00896 buffer << "<GradientNormGoal>" << std::endl
00897 << gradient_norm_goal << std::endl
00898 << "</GradientNormGoal>" << std::endl;
00899
00900 buffer << "<MaximumEpochsNumber>" << std::endl
00901 << maximum_epochs_number << std::endl
00902 << "</MaximumEpochsNumber>" << std::endl;
00903
00904 buffer << "<MaximumTime>" << std::endl
00905 << maximum_time << std::endl
00906 << "</MaximumTime>" << std::endl;
00907
00908
00909
00910 buffer << "<ReserveParametersHistory>" << std::endl
00911 << reserve_parameters_history << std::endl
00912 << "</ReserveParametersHistory>" << std::endl;
00913
00914 buffer << "<ReserveParametersNormHistory>" << std::endl
00915 << reserve_parameters_norm_history << std::endl
00916 << "</ReserveParametersNormHistory>" << std::endl;
00917
00918 buffer << "<ReserveEvaluationHistory>" << std::endl
00919 << reserve_evaluation_history << std::endl
00920 << "</ReserveEvaluationHistory>" << std::endl;
00921
00922 buffer << "<ReserveValidationErrorHistory>" << std::endl
00923 << reserve_validation_error_history << std::endl
00924 << "</ReserveValidationErrorHistory>" << std::endl;
00925
00926 buffer << "<ReserveGradientHistory>" << std::endl
00927 << reserve_gradient_history << std::endl
00928 << "</ReserveGradientHistory>" << std::endl;
00929
00930 buffer << "<ReserveGradientNormHistory>" << std::endl
00931 << reserve_gradient_norm_history << std::endl
00932 << "</ReserveGradientNormHistory>" << std::endl;
00933
00934 buffer << "<ReserveInverseHessianHistory>" << std::endl
00935 << reserve_inverse_Hessian_history << std::endl
00936 << "</ReserveInverseHessianHistory>" << std::endl;
00937
00938 buffer << "<ReserveTrainingDirectionHistory>" << std::endl
00939 << reserve_training_direction_history << std::endl
00940 << "</ReserveTrainingDirectionHistory>" << std::endl;
00941
00942 buffer << "<ReserveTrainingRateHistory>" << std::endl
00943 << reserve_training_rate_history << std::endl
00944 << "</ReserveTrainingRateHistory>" << std::endl;
00945
00946 buffer << "<ReserveElapsedTimeHistory>" << std::endl
00947 << reserve_elapsed_time_history << std::endl
00948 << "</ReserveElapsedTimeHistory>" << std::endl;
00949
00950 buffer << "<Display>" << std::endl
00951 << display << std::endl
00952 << "</Display>" << std::endl;
00953
00954 buffer << "<DisplayPeriod>" << std::endl
00955 << display_period << std::endl
00956 << "</DisplayPeriod>" << std::endl;
00957
00958 return(buffer.str());
00959 }
00960
00961
00962
00963
00967
00968 void QuasiNewtonMethod::load(const char* filename)
00969 {
00970
00971
00972 std::fstream file;
00973
00974 file.open(filename, std::ios::in);
00975
00976 if(!file.is_open())
00977 {
00978 std::cerr << "Flood Error: QuasiNewtonMethod class." << std::endl
00979 << "void load(const char*) method." << std::endl
00980 << "Cannot open quasi-Newton method object XML-type file." << std::endl;
00981
00982 exit(1);
00983 }
00984
00985 std::string word;
00986 std::string line;
00987
00988
00989
00990 getline(file, line);
00991
00992 if(line != "<Flood version='3.0' class='QuasiNewtonMethod'>")
00993 {
00994
00995
00996
00997
00998
00999 }
01000
01001 while(!file.eof())
01002 {
01003 file >> word;
01004
01005
01006
01007 if(word == "<InverseHessianApproximationMethod>")
01008 {
01009 std::string new_inverse_Hessian_approximation_method_name;
01010
01011 file >> new_inverse_Hessian_approximation_method_name;
01012
01013 file >> word;
01014
01015 if(word != "</InverseHessianApproximationMethod>")
01016 {
01017 std::cerr << "Flood Error: QuasiNewtonMethod class." << std::endl
01018 << "void load(const char*) method." << std::endl
01019 << "Unknown inverse Hessian approximation method end tag: " << word << std::endl;
01020
01021 exit(1);
01022 }
01023
01024 set_inverse_Hessian_approximation_method(new_inverse_Hessian_approximation_method_name);
01025 }
01026
01027 if(word == "<TrainingRateMethod>")
01028 {
01029 std::string new_training_rate_method;
01030
01031 file >> new_training_rate_method;
01032
01033 file >> word;
01034
01035 if(word != "</TrainingRateMethod>")
01036 {
01037 std::cerr << "Flood Error: QuasiNewtonMethod class." << std::endl
01038 << "void load(const char*) method." << std::endl
01039 << "Unknown training rate method end tag: " << word << std::endl;
01040
01041 exit(1);
01042 }
01043
01044 set_training_rate_method(new_training_rate_method);
01045 }
01046
01047
01048
01049 else if(word == "<BracketingFactor>")
01050 {
01051 double new_backeting_factor;
01052
01053 file >> new_backeting_factor;
01054
01055 file >> word;
01056
01057 if(word != "</BracketingFactor>")
01058 {
01059 std::cerr << "Flood Error: QuasiNewtonMethod class." << std::endl
01060 << "void load(const char*) method." << std::endl
01061 << "Unknown bracketing factor end tag: " << word << std::endl;
01062
01063 exit(1);
01064 }
01065
01066 set_bracketing_factor(new_backeting_factor);
01067 }
01068 else if(word == "<FirstTrainingRate>")
01069 {
01070 double new_first_training_rate;
01071
01072 file >> new_first_training_rate;
01073
01074 file >> word;
01075
01076 if(word != "</FirstTrainingRate>")
01077 {
01078 std::cerr << "Flood Error: QuasiNewtonMethod class." << std::endl
01079 << "void load(const char*) method." << std::endl
01080 << "Unknown first training rate end tag: " << word << std::endl;
01081
01082 exit(1);
01083 }
01084
01085 set_first_training_rate(new_first_training_rate);
01086 }
01087 else if(word == "<TrainingRateTolerance>")
01088 {
01089 double new_training_rate_tolerance;
01090
01091 file >> new_training_rate_tolerance;
01092
01093 file >> word;
01094
01095 if(word != "</TrainingRateTolerance>")
01096 {
01097 std::cerr << "Flood Error: QuasiNewtonMethod class." << std::endl
01098 << "void load(const char*) method." << std::endl
01099 << "Unknown training rate tolerance end tag: " << word << std::endl;
01100
01101 exit(1);
01102 }
01103
01104 set_training_rate_tolerance(new_training_rate_tolerance);
01105 }
01106
01107 else if(word == "<WarningParametersNorm>")
01108 {
01109 double new_warning_parameters_norm;
01110
01111 file >> new_warning_parameters_norm;
01112
01113 file >> word;
01114
01115 if(word != "</WarningParametersNorm>")
01116 {
01117 std::cerr << "Flood Error: QuasiNewtonMethod class." << std::endl
01118 << "void load(const char*) method." << std::endl
01119 << "Unknown warning parameters norm end tag: " << word << std::endl;
01120
01121 exit(1);
01122 }
01123
01124 set_warning_parameters_norm(new_warning_parameters_norm);
01125 }
01126
01127 else if(word == "<WarningGradientNorm>")
01128 {
01129 double new_warning_gradient_norm;
01130
01131 file >> new_warning_gradient_norm;
01132
01133 file >> word;
01134
01135 if(word != "</WarningGradientNorm>")
01136 {
01137 std::cerr << "Flood Error: QuasiNewtonMethod class." << std::endl
01138 << "void load(const char*) method." << std::endl
01139 << "Unknown warning gradient norm end tag: " << word << std::endl;
01140
01141 exit(1);
01142 }
01143
01144 set_warning_gradient_norm(new_warning_gradient_norm);
01145 }
01146
01147 else if(word == "<WarningTrainingRate>")
01148 {
01149 double new_warning_training_rate;
01150
01151 file >> new_warning_training_rate;
01152
01153 file >> word;
01154
01155 if(word != "</WarningTrainingRate>")
01156 {
01157 std::cerr << "Flood Error: QuasiNewtonMethod class." << std::endl
01158 << "void load(const char*) method." << std::endl
01159 << "Unknown warning training rate end tag: " << word << std::endl;
01160
01161 exit(1);
01162 }
01163
01164 set_warning_training_rate(new_warning_training_rate);
01165 }
01166
01167 else if(word == "<ErrorParametersNorm>")
01168 {
01169 double new_error_parameters_norm;
01170
01171 file >> new_error_parameters_norm;
01172
01173 file >> word;
01174
01175 if(word != "</ErrorParametersNorm>")
01176 {
01177 std::cerr << "Flood Error: QuasiNewtonMethod class." << std::endl
01178 << "void load(const char*) method." << std::endl
01179 << "Unknown error parameters norm end tag: " << word << std::endl;
01180
01181 exit(1);
01182 }
01183
01184 set_error_parameters_norm(new_error_parameters_norm);
01185 }
01186
01187 else if(word == "<ErrorGradientNorm>")
01188 {
01189 double new_error_gradient_norm;
01190
01191 file >> new_error_gradient_norm;
01192
01193 file >> word;
01194
01195 if(word != "</ErrorGradientNorm>")
01196 {
01197 std::cerr << "Flood Error: QuasiNewtonMethod class." << std::endl
01198 << "void load(const char*) method." << std::endl
01199 << "Unknown error gradient norm end tag: " << word << std::endl;
01200
01201 exit(1);
01202 }
01203
01204 set_error_gradient_norm(new_error_gradient_norm);
01205 }
01206
01207 else if(word == "<ErrorTrainingRate>")
01208 {
01209 double new_error_training_rate;
01210
01211 file >> new_error_training_rate;
01212
01213 set_error_training_rate(new_error_training_rate);
01214
01215 file >> word;
01216
01217 if(word != "</ErrorTrainingRate>")
01218 {
01219 std::cerr << "Flood Error: QuasiNewtonMethod class." << std::endl
01220 << "void load(const char*) method." << std::endl
01221 << "Unknown error training rate end tag: " << word << std::endl;
01222
01223 exit(1);
01224 }
01225 }
01226
01227
01228
01229 else if(word == "<MinimumParametersIncrementNorm>")
01230 {
01231 double new_minimum_parameters_increment_norm;
01232
01233 file >> new_minimum_parameters_increment_norm;
01234
01235 file >> word;
01236
01237 if(word != "</MinimumParametersIncrementNorm>")
01238 {
01239 std::cerr << "Flood Error: QuasiNewtonMethod class." << std::endl
01240 << "void load(const char*) method." << std::endl
01241 << "Unknown minimum parameters increment norm end tag: " << word << std::endl;
01242
01243 exit(1);
01244 }
01245
01246 set_minimum_parameters_increment_norm(new_minimum_parameters_increment_norm);
01247 }
01248
01249 else if(word == "<MinimumEvaluationImprovement>")
01250 {
01251 double new_minimum_evaluation_improvement;
01252
01253 file >> new_minimum_evaluation_improvement;
01254
01255 file >> word;
01256
01257 if(word != "</MinimumEvaluationImprovement>")
01258 {
01259 std::cerr << "Flood Error: QuasiNewtonMethod class." << std::endl
01260 << "void load(const char*) method." << std::endl
01261 << "Unknown minimum evaluation improvement end tag: " << word << std::endl;
01262
01263 exit(1);
01264 }
01265
01266 set_minimum_evaluation_improvement(new_minimum_evaluation_improvement);
01267 }
01268
01269 else if(word == "<EvaluationGoal>")
01270 {
01271 double new_evaluation_goal;
01272
01273 file >> new_evaluation_goal;
01274
01275 file >> word;
01276
01277 if(word != "</EvaluationGoal>")
01278 {
01279 std::cerr << "Flood Error: QuasiNewtonMethod class." << std::endl
01280 << "void load(const char*) method." << std::endl
01281 << "Unknown evaluation goal end tag: " << word << std::endl;
01282
01283 exit(1);
01284 }
01285
01286 set_evaluation_goal(new_evaluation_goal);
01287 }
01288
01289 else if(word == "<EarlyStopping>")
01290 {
01291 bool new_early_stopping;
01292
01293 file >> new_early_stopping;
01294
01295 file >> word;
01296
01297 if(word != "</EarlyStopping>")
01298 {
01299 std::cerr << "Flood Error: QuasiNewtonMethod class." << std::endl
01300 << "void load(const char*) method." << std::endl
01301 << "Unknown early stopping end tag: " << word << std::endl;
01302
01303 exit(1);
01304 }
01305
01306 set_early_stopping(new_early_stopping);
01307 }
01308
01309 else if(word == "<GradientNormGoal>")
01310 {
01311 double new_gradient_norm_goal;
01312
01313 file >> new_gradient_norm_goal;
01314
01315 file >> word;
01316
01317 if(word != "</GradientNormGoal>")
01318 {
01319 std::cerr << "Flood Error: QuasiNewtonMethod class." << std::endl
01320 << "void load(const char*) method." << std::endl
01321 << "Unknown gradient norm goal end tag: " << word << std::endl;
01322
01323 exit(1);
01324 }
01325
01326 set_gradient_norm_goal(new_gradient_norm_goal);
01327 }
01328
01329 else if(word == "<MaximumEpochsNumber>")
01330 {
01331 int new_maximum_epochs_number;
01332
01333 file >> new_maximum_epochs_number;
01334
01335 file >> word;
01336
01337 if(word != "</MaximumEpochsNumber>")
01338 {
01339 std::cerr << "Flood Error: QuasiNewtonMethod class." << std::endl
01340 << "void load(const char*) method." << std::endl
01341 << "Unknown maximum epochs number end tag: " << word << std::endl;
01342
01343 exit(1);
01344 }
01345
01346 set_maximum_epochs_number(new_maximum_epochs_number);
01347 }
01348
01349 else if(word == "<MaximumTime>")
01350 {
01351 double new_maximum_time;
01352
01353 file >> new_maximum_time;
01354
01355 file >> word;
01356
01357 if(word != "</MaximumTime>")
01358 {
01359 std::cerr << "Flood Error: QuasiNewtonMethod class." << std::endl
01360 << "void load(const char*) method." << std::endl
01361 << "Unknown maximum time end tag: " << word << std::endl;
01362
01363 exit(1);
01364 }
01365
01366 set_maximum_time(new_maximum_time);
01367 }
01368
01369
01370
01371 else if(word == "<ReserveParametersHistory>")
01372 {
01373 bool new_reserve_parameters_history;
01374
01375 file >> new_reserve_parameters_history;
01376
01377 file >> word;
01378
01379 if(word != "</ReserveParametersHistory>")
01380 {
01381 std::cerr << "Flood Error: QuasiNewtonMethod class." << std::endl
01382 << "void load(const char*) method." << std::endl
01383 << "Unknown reserve parameters history end tag: " << word << std::endl;
01384
01385 exit(1);
01386 }
01387
01388 set_reserve_parameters_history(new_reserve_parameters_history);
01389 }
01390
01391 else if(word == "<ReserveParametersNormHistory>")
01392 {
01393 bool new_reserve_parameters_norm_history;
01394
01395 file >> new_reserve_parameters_norm_history;
01396
01397 file >> word;
01398
01399 if(word != "</ReserveParametersNormHistory>")
01400 {
01401 std::cerr << "Flood Error: QuasiNewtonMethod class." << std::endl
01402 << "void load(const char*) method." << std::endl
01403 << "Unknown reserve parameters norm history end tag: " << word << std::endl;
01404
01405 exit(1);
01406 }
01407
01408 set_reserve_parameters_norm_history(new_reserve_parameters_norm_history);
01409 }
01410 else if(word == "<ReserveEvaluationHistory>")
01411 {
01412 bool new_reserve_evaluation_history;
01413
01414 file >> new_reserve_evaluation_history;
01415
01416 file >> word;
01417
01418 if(word != "</ReserveEvaluationHistory>")
01419 {
01420 std::cerr << "Flood Error: QuasiNewtonMethod class." << std::endl
01421 << "void load(const char*) method." << std::endl
01422 << "Unknown reserve evaluation history end tag: " << word << std::endl;
01423
01424 exit(1);
01425 }
01426
01427 set_reserve_evaluation_history(new_reserve_evaluation_history);
01428 }
01429
01430 else if(word == "<ReserveGradientHistory>")
01431 {
01432 bool new_reserve_gradient_history;
01433
01434 file >> new_reserve_gradient_history;
01435
01436 file >> word;
01437
01438 if(word != "</ReserveGradientHistory>")
01439 {
01440 std::cerr << "Flood Error: QuasiNewtonMethod class." << std::endl
01441 << "void load(const char*) method." << std::endl
01442 << "Unknown reserve gradient history end tag: " << word << std::endl;
01443
01444 exit(1);
01445 }
01446
01447 set_reserve_gradient_history(new_reserve_gradient_history);
01448 }
01449
01450 else if(word == "<ReserveGradientNormHistory>")
01451 {
01452 bool new_reserve_gradient_norm_history;
01453
01454 file >> new_reserve_gradient_norm_history;
01455
01456 file >> word;
01457
01458 if(word != "</ReserveGradientNormHistory>")
01459 {
01460 std::cerr << "Flood Error: QuasiNewtonMethod class." << std::endl
01461 << "void load(const char*) method." << std::endl
01462 << "Unknown reserve gradient norm history end tag: " << word << std::endl;
01463
01464 exit(1);
01465 }
01466
01467 set_reserve_gradient_norm_history(new_reserve_gradient_norm_history);
01468 }
01469
01470 else if(word == "<ReserveInverseHessianHistory>")
01471 {
01472 bool new_reserve_inverse_Hessian_history;
01473
01474 file >> new_reserve_inverse_Hessian_history;
01475
01476 file >> word;
01477
01478 if(word != "</ReserveInverseHessianHistory>")
01479 {
01480 std::cerr << "Flood Error: QuasiNewtonMethod class." << std::endl
01481 << "void load(const char*) method." << std::endl
01482 << "Unknown reserve inverse Hessian history end tag: " << word << std::endl;
01483
01484 exit(1);
01485 }
01486
01487 set_reserve_inverse_Hessian_history(new_reserve_inverse_Hessian_history);
01488 }
01489
01490 else if(word == "<ReserveTrainingDirectionHistory>")
01491 {
01492 bool new_reserve_training_direction_history;
01493
01494 file >> new_reserve_training_direction_history;
01495
01496 file >> word;
01497
01498 if(word != "</ReserveTrainingDirectionHistory>")
01499 {
01500 std::cerr << "Flood Error: QuasiNewtonMethod class." << std::endl
01501 << "void load(const char*) method." << std::endl
01502 << "Unknown reserve training direction history end tag: " << word << std::endl;
01503
01504 exit(1);
01505 }
01506
01507 set_reserve_training_direction_history(new_reserve_training_direction_history);
01508 }
01509
01510 else if(word == "<ReserveTrainingRateHistory>")
01511 {
01512 bool new_reserve_training_rate_history;
01513
01514 file >> new_reserve_training_rate_history;
01515
01516 file >> word;
01517
01518 if(word != "</ReserveTrainingRateHistory>")
01519 {
01520 std::cerr << "Flood Error: QuasiNewtonMethod class." << std::endl
01521 << "void load(const char*) method." << std::endl
01522 << "Unknown reserve training rate history end tag: " << word << std::endl;
01523
01524 exit(1);
01525 }
01526
01527 set_reserve_training_rate_history(new_reserve_training_rate_history);
01528 }
01529
01530 else if(word == "<ReserveElapsedTimeHistory>")
01531 {
01532 bool new_reserve_elapsed_time_history;
01533
01534 file >> new_reserve_elapsed_time_history;
01535
01536 file >> word;
01537
01538 if(word != "</ReserveElapsedTimeHistory>")
01539 {
01540 std::cerr << "Flood Error: QuasiNewtonMethod class." << std::endl
01541 << "void load(const char*) method." << std::endl
01542 << "Unknown reserve elapsed time history end tag: " << word << std::endl;
01543
01544 exit(1);
01545 }
01546
01547 set_reserve_elapsed_time_history(new_reserve_elapsed_time_history);
01548 }
01549
01550 else if(word == "<ReserveValidationErrorHistory>")
01551 {
01552 bool new_reserve_validation_error_history;
01553
01554 file >> new_reserve_validation_error_history;
01555
01556 file >> word;
01557
01558 if(word != "</ReserveValidationErrorHistory>")
01559 {
01560 std::cerr << "Flood Error: QuasiNewtonMethod class." << std::endl
01561 << "void load(const char*) method." << std::endl
01562 << "Unknown reserve validation error history end tag: " << word << std::endl;
01563
01564 exit(1);
01565 }
01566
01567 set_reserve_validation_error_history(new_reserve_validation_error_history);
01568 }
01569
01570
01571
01572 else if(word == "<Display>")
01573 {
01574 bool new_display;
01575
01576 file >> new_display;
01577
01578 file >> word;
01579
01580 if(word != "</Display>")
01581 {
01582 std::cerr << "Flood Error: QuasiNewtonMethod class." << std::endl
01583 << "void load(const char*) method." << std::endl
01584 << "Unknown display end tag: " << word << std::endl;
01585
01586 exit(1);
01587 }
01588
01589 set_display(new_display);
01590 }
01591
01592 else if(word == "<DisplayPeriod>")
01593 {
01594 int new_display_period;
01595
01596 file >> new_display_period;
01597
01598 file >> word;
01599
01600 if(word != "</DisplayPeriod>")
01601 {
01602 std::cerr << "Flood Error: QuasiNewtonMethod class." << std::endl
01603 << "void load(const char*) method." << std::endl
01604 << "Unknown display period end tag: " << word << std::endl;
01605
01606 exit(1);
01607 }
01608
01609 set_display_period(new_display_period);
01610 }
01611 }
01612
01613
01614
01615 file.close();
01616 }
01617
01618 }
01619
01620
01621
01622
01623
01624
01625
01626
01627
01628
01629
01630
01631
01632
01633
01634
01635
01636
01637