From 44ee25894419475c3017af840c820e6c3a26a971 Mon Sep 17 00:00:00 2001 From: Martin Beseda <martin.beseda@vsb.cz> Date: Sun, 6 Jan 2019 09:33:48 +0100 Subject: [PATCH] ENH: Method run_k_fold_test overloaded, so that it can output not only to STDOUT, but also to the file, either according to its name or to the open handler. --- src/CrossValidator/CrossValidator.cpp | 54 ++++++++++++++++++++++++--- src/CrossValidator/CrossValidator.h | 12 +++++- 2 files changed, 60 insertions(+), 6 deletions(-) diff --git a/src/CrossValidator/CrossValidator.cpp b/src/CrossValidator/CrossValidator.cpp index 970c7fbf..35449264 100644 --- a/src/CrossValidator/CrossValidator.cpp +++ b/src/CrossValidator/CrossValidator.cpp @@ -3,7 +3,7 @@ // #include "CrossValidator.h" -#include "../message.h" +#include "message.h" namespace lib4neuro { LIB4NEURO_API CrossValidator::CrossValidator(ILearningMethods* optimizer, ErrorFunction* ef) { @@ -11,19 +11,63 @@ namespace lib4neuro { this->ef = ef; } - LIB4NEURO_API void CrossValidator::run_k_fold_test(unsigned int k, unsigned int tests_number) { + LIB4NEURO_API void CrossValidator::run_k_fold_test(unsigned int k, unsigned int tests_number, std::ofstream* results_file_path) { + //TODO do not duplicate code - write in a more elegant way NeuralNetwork *net = this->ef->get_network_instance(); + double cv_err_sum = 0; + + for(unsigned int i = 0; i < tests_number; i++) { + COUT_INFO("Cross-validation run " << i+1 << std::endl); + *results_file_path << "Cross-validation run " << i+1 << std::endl; + + this->ef->divide_data_train_test(1.0/k); + *results_file_path << "Number of train data points: " << this->ef->get_dataset()->get_n_elements() << std::endl; + *results_file_path << "Number of test data points: " << this->ef->get_test_dataset()->get_n_elements() << std::endl; + net->randomize_parameters(); + net->scale_parameters( 1.0 / (net->get_n_weights() + net->get_n_biases())); + this->optimizer->optimize(*this->ef); + + /* Error evaluation and writing */ + double err = this->ef->eval_on_test_data(results_file_path); + cv_err_sum += err; + COUT_INFO("CV error (run " << i+1 << "): " << err << std::endl << std::endl); + + this->ef->return_full_data_set_for_training(); + } + + COUT_INFO("CV error mean: " << cv_err_sum/tests_number << std::endl); + *results_file_path << "CV error mean: " << cv_err_sum/tests_number << std::endl; + } + + LIB4NEURO_API void CrossValidator::run_k_fold_test(unsigned int k, unsigned int tests_number, std::string results_file_path) { + NeuralNetwork *net = this->ef->get_network_instance(); + + double cv_err_sum = 0; + for(unsigned int i = 0; i < tests_number; i++) { - COUT_DEBUG(<< "Cross-validation run " << i+1 << std::endl); + COUT_INFO("Cross-validation run " << i+1 << std::endl); this->ef->divide_data_train_test(1.0/k); - COUT_DEBUG(<< "number of train data points: " << this->ef->get_dataset()->get_n_elements() << std::endl); + COUT_DEBUG("Number of train data points: " << this->ef->get_dataset()->get_n_elements() << std::endl); + COUT_DEBUG("Number of test data points: " << this->ef->get_test_dataset()->get_n_elements() << std::endl); net->randomize_parameters(); net->scale_parameters( 1.0 / (net->get_n_weights() + net->get_n_biases())); - net->print_weights(); this->optimizer->optimize(*this->ef); + + /* Error evaluation and writing */ + double err; + if(results_file_path == "") { + err = this->ef->eval_on_test_data(); + } else { + err = this->ef->eval_on_test_data(results_file_path + "_cv" + std::to_string(i) + ".dat"); + } + cv_err_sum += err; + COUT_INFO("CV error (run " << i+1 << "): " << err << std::endl << std::endl); + this->ef->return_full_data_set_for_training(); } + + COUT_INFO("CV error mean: " << cv_err_sum/tests_number << std::endl); } } diff --git a/src/CrossValidator/CrossValidator.h b/src/CrossValidator/CrossValidator.h index a6db416d..8ee16286 100644 --- a/src/CrossValidator/CrossValidator.h +++ b/src/CrossValidator/CrossValidator.h @@ -36,12 +36,22 @@ namespace lib4neuro { */ LIB4NEURO_API CrossValidator(ILearningMethods* optimizer, ErrorFunction* ef); + /** + * + * @param k + * @param test_number + * @param results_file_path + */ + LIB4NEURO_API void + run_k_fold_test(unsigned int k, unsigned int test_number, std::string results_file_path = ""); + /** * * @param k * @param tests_number + * @param results_file_path */ - LIB4NEURO_API void run_k_fold_test(unsigned int k, unsigned int test_number); + LIB4NEURO_API void run_k_fold_test(unsigned int k, unsigned int tests_number, std::ofstream* results_file_path); }; } -- GitLab