Commit 90ab7937 authored by Thomas Purcell's avatar Thomas Purcell
Browse files

Add const keywords to the FeatureSpace, Models and Regressors

parent eaf62009
#include <descriptor_identifier/Model/Model.hpp>
Model::Model(
std::string prop_label,
Unit prop_unit,
std::vector<double> prop_train,
std::vector<double> prop_test,
std::vector<model_node_ptr> feats,
std::vector<int> task_sizes_train,
std::vector<int> task_sizes_test,
bool fix_intercept
const std::string prop_label,
const Unit prop_unit,
const std::vector<double> prop_train,
const std::vector<double> prop_test,
const std::vector<model_node_ptr> feats,
const std::vector<int> task_sizes_train,
const std::vector<int> task_sizes_test,
const bool fix_intercept
) :
_n_samp_train(feats[0]->n_samp()),
_n_samp_test(feats[0]->n_test_samp()),
......@@ -30,7 +30,7 @@ Model::Model() :
_task_eval(0)
{}
double Model::eval(std::vector<double> x_in)
double Model::eval(std::vector<double> x_in) const
{
int n_leaves_tot = std::accumulate(_feats.begin(), _feats.end(), 0, [](int tot, model_node_ptr feat){return tot + feat->n_leaves();});
if(x_in.size() != n_leaves_tot)
......@@ -45,7 +45,7 @@ double Model::eval(std::vector<double> x_in)
return eval(x_in.data());
}
double Model::eval(std::map<std::string, double> x_in_dct)
double Model::eval(std::map<std::string, double> x_in_dct) const
{
std::vector<double> x_in;
for(auto& feat : _feats)
......@@ -68,7 +68,7 @@ double Model::eval(std::map<std::string, double> x_in_dct)
}
std::vector<double> Model::eval(std::vector<std::vector<double>> x_in)
std::vector<double> Model::eval(std::vector<std::vector<double>> x_in) const
{
int n_leaves_tot = std::accumulate(_feats.begin(), _feats.end(), 0, [](int tot, model_node_ptr feat){return tot + feat->n_leaves();});
if(x_in.size() != n_leaves_tot)
......@@ -91,7 +91,7 @@ std::vector<double> Model::eval(std::vector<std::vector<double>> x_in)
return eval(x_in.data());
}
std::vector<double> Model::eval(std::map<std::string, std::vector<double>> x_in_dct)
std::vector<double> Model::eval(std::map<std::string, std::vector<double>> x_in_dct) const
{
std::vector<std::vector<double>> x_in;
for(auto& feat :_feats)
......
......@@ -77,14 +77,14 @@ public:
* @param fix_intercept If true the intercept of the model is 0
*/
Model(
std::string prop_label,
Unit prop_unit,
std::vector<double> prop_train,
std::vector<double> prop_test,
std::vector<model_node_ptr> feats,
std::vector<int> task_sizes_train,
std::vector<int> task_sizes_test,
bool fix_intercept
const std::string prop_label,
const Unit prop_unit,
const std::vector<double> prop_train,
const std::vector<double> prop_test,
const std::vector<model_node_ptr> feats,
const std::vector<int> task_sizes_train,
const std::vector<int> task_sizes_test,
const bool fix_intercept
);
/**
......@@ -121,7 +121,7 @@ public:
* @param x_in pointer to the new data point (order the same as appending the results of _feats[nn]->get_x_in_expr_list() for all feature)
* @return The prediction of the model for a given data point
*/
virtual double eval(double* x_in) = 0;
virtual double eval(double* x_in) const = 0;
/**
* @brief Evaluate the model for a new point
......@@ -129,7 +129,7 @@ public:
* @param x_in The data point to evaluate the model (order the same as appending the results of _feats[nn]->get_x_in_expr_list() for all feature)
* @return The prediction of the model for a given data point
*/
double eval(std::vector<double> x_in);
double eval(std::vector<double> x_in) const;
/**
* @brief Evaluate the model for a new point
......@@ -137,7 +137,7 @@ public:
* @param x_in_dct Dictionary describing the new point ("feature expr": value)
* @return The prediction of the model for a given data point
*/
double eval(std::map<std::string, double> x_in_dct);
double eval(std::map<std::string, double> x_in_dct) const;
/**
* @brief Evaluate the model for a new set of new points
......@@ -145,7 +145,7 @@ public:
* @param x_in a vector of pointers to the set of values for new data points (one pointer per each feature and order the same as appending the results of _feats[nn]->get_x_in_expr_list() for all feature)
* @return The prediction of the model for a given set of data points
*/
virtual std::vector<double> eval(std::vector<double>* x_in) = 0;
virtual std::vector<double> eval(std::vector<double>* x_in) const = 0;
/**
* @brief Evaluate the model for a set of new points
......@@ -153,7 +153,7 @@ public:
* @param x_in The set data for a set of new data points (size of n_feature x n_points, and order the same as appending the results of _feats[nn]->get_x_in_expr_list() for all feature)
* @return The prediction of the model for a given data point
*/
std::vector<double> eval(std::vector<std::vector<double>> x_in);
std::vector<double> eval(std::vector<std::vector<double>> x_in) const;
/**
* @brief Evaluate the model for a set of new points
......@@ -161,7 +161,7 @@ public:
* @param x_in_dct The set of data points to evaluate the model. Keys must be strings representing feature expressions and vectors must be the same length
* @return The prediction of the model for a given data point
*/
std::vector<double> eval(std::map<std::string, std::vector<double>> x_in_dct);
std::vector<double> eval(std::map<std::string, std::vector<double>> x_in_dct) const;
// DocString: model_set_task_eval
/**
......@@ -177,25 +177,25 @@ public:
*
* @returns _task_eval Task to evaluate
*/
inline int get_task_eval(){return _task_eval;}
inline int get_task_eval() const {return _task_eval;}
// DocString: model_n_samp_train
/**
* @brief Total number of samples being trained on
*/
inline int n_samp_train(){return _n_samp_train;}
inline int n_samp_train() const {return _n_samp_train;}
// DocString: model_n_samp_test
/**
* @brief Total number of samples being tested
*/
inline int n_samp_test(){return _n_samp_test;}
inline int n_samp_test() const {return _n_samp_test;}
// DocString: model_n_dim
/**
* @brief The dimensionality of the data
*/
inline int n_dim(){return _n_dim;}
inline int n_dim() const {return _n_dim;}
// DocString: model_prop_unit
/**
......@@ -209,7 +209,7 @@ public:
* @brief The label for the property
* @return The label for the property
*/
inline std::string prop_label(){return _prop_label;}
inline std::string prop_label() const {return _prop_label;}
/**
* @brief Convert the Model into an output file
......@@ -218,19 +218,19 @@ public:
* @param train If true output the training data
* @param test_inds The indexes of the test set
*/
virtual void to_file(std::string filename, bool train=true, std::vector<int> test_inds={}) = 0;
virtual void to_file(const std::string filename, const bool train=true, const std::vector<int> test_inds={}) const = 0;
// DocString: model_fix_intercept
/**
* @brief Access whether the intercept is fixed at 0 or not
*/
inline bool fix_intercept(){return _fix_intercept;}
inline bool fix_intercept() const {return _fix_intercept;}
/**
* @brief Accessor to the coefficients for the model
* @return The coefficients for the model for each task
*/
inline std::vector<std::vector<double>> coefs(){return _coefs;}
inline std::vector<std::vector<double>> coefs() const {return _coefs;}
#ifdef PY_BINDINGS
// DocString: model_coefs
......@@ -291,7 +291,7 @@ public:
* @param x_in The data point to evaluate the model (order the same as appending the results of _feats[nn]->get_x_in_expr_list() for all feature)
* @return The prediction of the model for a given data point
*/
inline double eval_py(np::ndarray x_in){return eval(python_conv_utils::from_ndarray<double>(x_in));}
inline double eval_py(np::ndarray x_in) const {return eval(python_conv_utils::from_ndarray<double>(x_in));}
/**
* @brief Evaluate the model for a new point
......@@ -299,7 +299,7 @@ public:
* @param x_in The data point to evaluate the model (order the same as appending the results of _feats[nn]->get_x_in_expr_list() for all feature)
* @return The prediction of the model for a given data point
*/
inline double eval_py(py::list x_in){return eval(python_conv_utils::from_list<double>(x_in));}
inline double eval_py(py::list x_in) const {return eval(python_conv_utils::from_list<double>(x_in));}
/**
* @brief Evaluate the model for a new point
......@@ -307,7 +307,7 @@ public:
* @param x_in_dct Dictionary describing the new point ("feature expr": value)
* @return The prediction of the model for a given data point
*/
inline double eval_py(py::dict x_in){return eval(python_conv_utils::from_dict<std::string, double>(x_in));}
inline double eval_py(py::dict x_in) const {return eval(python_conv_utils::from_dict<std::string, double>(x_in));}
/**
* @brief Evaluate the model for a set of new points
......@@ -315,7 +315,7 @@ public:
* @param x_in The set data for a set of new data points (size of n_feature x n_points, and order the same as appending the results of _feats[nn]->get_x_in_expr_list() for all feature)
* @return The prediction of the model for a given data point
*/
np::ndarray eval_many_py(np::ndarray x_in);
np::ndarray eval_many_py(np::ndarray x_in) const ;
/**
* @brief Evaluate the model for a set of new points
......@@ -323,7 +323,7 @@ public:
* @param x_in_dct The set of data points to evaluate the model. Keys must be strings representing feature expressions and vectors must be the same length
* @return The prediction of the model for a given data point
*/
np::ndarray eval_many_py(py::dict x_in);
np::ndarray eval_many_py(py::dict x_in) const ;
#endif
};
......
#include <descriptor_identifier/Model/ModelClassifier.hpp>
ModelClassifier::ModelClassifier(
std::string prop_label,
Unit prop_unit,
std::vector<double> prop_train,
std::vector<double> prop_test,
std::vector<model_node_ptr> feats,
std::vector<int> task_sizes_train,
std::vector<int> task_sizes_test,
bool fix_intercept
const std::string prop_label,
const Unit prop_unit,
const std::vector<double> prop_train,
const std::vector<double> prop_test,
const std::vector<model_node_ptr> feats,
const std::vector<int> task_sizes_train,
const std::vector<int> task_sizes_test,
const bool fix_intercept
) :
Model(prop_label, prop_unit, prop_train, prop_test, feats, task_sizes_train, task_sizes_test, fix_intercept),
_prop_train_est(_prop_train),
......@@ -72,7 +72,7 @@ ModelClassifier::ModelClassifier(
_test_n_svm_misclassified = std::accumulate(test_misclassified.begin(), test_misclassified.end(), 0);
}
ModelClassifier::ModelClassifier(std::string train_file)
ModelClassifier::ModelClassifier(const std::string train_file)
{
_n_samp_test = 0;
......@@ -128,7 +128,7 @@ ModelClassifier::ModelClassifier(std::string train_file)
throw std::logic_error("The file does not have the same convex overlap (" + std::to_string(file_train_n_convex_overlap) + ") as calculated here (" + std::to_string(_train_n_convex_overlap) + ").");
}
ModelClassifier::ModelClassifier(std::string train_file, std::string test_file)
ModelClassifier::ModelClassifier(const std::string train_file, const std::string test_file)
{
std::vector<std::string> split_str;
std::vector<std::string> feature_expr_train = populate_model(train_file, true);
......@@ -203,21 +203,21 @@ ModelClassifier::ModelClassifier(std::string train_file, std::string test_file)
}
}
double ModelClassifier::eval(double* x_in)
double ModelClassifier::eval(double* x_in) const
{
double result = 0.0;
throw std::logic_error("Eval not defined for classifier.");
return result;
}
std::vector<double> ModelClassifier::eval(std::vector<double>* x_in)
std::vector<double> ModelClassifier::eval(std::vector<double>* x_in) const
{
std::vector<double> result(0, 0.0);
throw std::logic_error("Eval not defined for classifier.");
return result;
}
std::vector<std::string> ModelClassifier::populate_model(std::string filename, bool train)
std::vector<std::string> ModelClassifier::populate_model(const std::string filename, const bool train)
{
std::ifstream file_stream;
file_stream.open(filename, std::ios::in);
......@@ -578,7 +578,7 @@ std::ostream& operator<< (std::ostream& outStream, const ModelClassifier& model)
return outStream;
}
void ModelClassifier::to_file(std::string filename, bool train, std::vector<int> test_inds)
void ModelClassifier::to_file(std::string filename, bool train, std::vector<int> test_inds) const
{
boost::filesystem::path p(filename.c_str());
boost::filesystem::path parent = p.remove_filename();
......
......@@ -66,14 +66,14 @@ public:
* @param fix_intercept if True then the intercept is 0.0
*/
ModelClassifier(
std::string prop_label,
Unit prop_unit,
std::vector<double> prop_train,
std::vector<double> prop_test,
std::vector<model_node_ptr> feats,
std::vector<int> task_sizes_train,
std::vector<int> task_sizes_test,
bool fix_intercept
const std::string prop_label,
const Unit prop_unit,
const std::vector<double> prop_train,
const std::vector<double> prop_test,
const std::vector<model_node_ptr> feats,
const std::vector<int> task_sizes_train,
const std::vector<int> task_sizes_test,
const bool fix_intercept
);
// DocString: model_class_init_str
......@@ -83,7 +83,7 @@ public:
*
* @param train_file Previously generated model file
*/
ModelClassifier(std::string train_file);
ModelClassifier(const std::string train_file);
// DocString: model_class_init_str_str
/**
......@@ -93,7 +93,7 @@ public:
* @param train_file Previously generated training model output file
* @param train_file Previously generated testing model output file
*/
ModelClassifier(std::string train_file, std::string test_file);
ModelClassifier(const std::string train_file, const std::string test_file);
/**
* @brief Copy Constructor
......@@ -129,7 +129,7 @@ public:
* @param x_in pointer to the new data point (order the same as appending the results of _feats[nn]->get_x_in_expr_list() for all feature)
* @return The prediction of the model for a given data point
*/
double eval(double* x_in);
double eval(double* x_in) const;
/**
* @brief Evaluate the model for a new set of new points
......@@ -137,7 +137,7 @@ public:
* @param x_in a vector of pointers to the set of values for new data points (one pointer per each feature and order the same as appending the results of _feats[nn]->get_x_in_expr_list() for all feature)
* @return The prediction of the model for a given set of data points
*/
std::vector<double> eval(std::vector<double>* x_in);
std::vector<double> eval(std::vector<double>* x_in) const;
/**
* @brief Read an output file and extract all relevant information
......@@ -171,7 +171,7 @@ public:
*
* @param res pointer to the beginning of the vector to store the residual
*/
inline void copy_error(double* res){std::copy_n(_train_error.data(), _n_samp_train, res);}
inline void copy_error(double* res) const {std::copy_n(_train_error.data(), _n_samp_train, res);}
/**
* @brief Convert the ModelClassifier into an output file
......@@ -180,7 +180,7 @@ public:
* @param train If true output the training data
* @param test_inds The indexes of the test set
*/
void to_file(std::string filename, bool train=true, std::vector<int> test_inds={});
void to_file(const std::string filename, const bool train=true, const std::vector<int> test_inds={}) const;
/**
* @brief Set the train/test error of the model using linear programming
......@@ -191,31 +191,31 @@ public:
/**
* @brief The number of samples in overlapping convex hull regions (training data)
*/
inline int n_convex_overlap_train(){return _train_n_convex_overlap;}
inline int n_convex_overlap_train() const {return _train_n_convex_overlap;}
// DocString: model_classn_convex_overlap_test
/**
* @brief The number of samples in overlapping convex hull regions (test data)
*/
inline int n_convex_overlap_test(){return _test_n_convex_overlap;}
inline int n_convex_overlap_test() const {return _test_n_convex_overlap;}
// DocString: model_classn_svm_misclassified_train
/**
* @brief The number of samples misclassified by SVM (training data)
*/
inline int n_svm_misclassified_train(){return _train_n_svm_misclassified;}
inline int n_svm_misclassified_train() const {return _train_n_svm_misclassified;}
// DocString: model_classn_svm_misclassified_test
/**
* @brief The number of samples misclassified by SVM (training data)
*/
inline int n_svm_misclassified_test(){return _test_n_svm_misclassified;}
inline int n_svm_misclassified_test() const {return _test_n_svm_misclassified;}
// DocString: model_class_precent_train_error
/**
* @brief Percent of all training samples misclassified
*/
inline double percent_train_error()
inline double percent_train_error() const
{
return 100.0 * static_cast<double>(_train_n_convex_overlap) / static_cast<double>(_n_samp_train);
}
......@@ -224,7 +224,7 @@ public:
/**
* @brief Percent of all tset samples misclassified
*/
inline double percent_test_error()
inline double percent_test_error() const
{
return 100.0 * static_cast<double>(_test_n_convex_overlap) / static_cast<double>(_n_samp_test);
}
......
......@@ -4,14 +4,14 @@ ModelLogRegressor::ModelLogRegressor()
{}
ModelLogRegressor::ModelLogRegressor(
std::string prop_label,
Unit prop_unit,
std::vector<double> prop_train,
std::vector<double> prop_test,
std::vector<model_node_ptr> feats,
std::vector<int> task_sizes_train,
std::vector<int> task_sizes_test,
bool fix_intercept
const std::string prop_label,
const Unit prop_unit,
const std::vector<double> prop_train,
const std::vector<double> prop_test,
const std::vector<model_node_ptr> feats,
const std::vector<int> task_sizes_train,
const std::vector<int> task_sizes_test,
const bool fix_intercept
) :
ModelRegressor(prop_label, prop_unit, prop_train, prop_test, feats, task_sizes_train, task_sizes_test, fix_intercept, false),
_log_prop_train(_n_samp_train, 0.0),
......@@ -119,7 +119,7 @@ ModelLogRegressor::ModelLogRegressor(
std::transform(_prop_test.begin(), _prop_test.end(), _prop_test_est.begin(), _test_error.begin(), [](double pt, double pt_est){return pt - pt_est;});
}
ModelLogRegressor::ModelLogRegressor(std::string train_file) :
ModelLogRegressor::ModelLogRegressor(const std::string train_file) :
ModelRegressor(train_file),
_log_prop_train(_n_samp_train, 0.0),
_log_prop_test(_n_samp_test, 0.0),
......@@ -141,7 +141,7 @@ ModelLogRegressor::ModelLogRegressor(std::string train_file) :
);
}
ModelLogRegressor::ModelLogRegressor(std::string train_file, std::string test_file) :
ModelLogRegressor::ModelLogRegressor(const std::string train_file, const std::string test_file) :
ModelRegressor(train_file, test_file),
_log_prop_train(_n_samp_train, 0.0),
_log_prop_test(_n_samp_test, 0.0),
......@@ -178,7 +178,7 @@ ModelLogRegressor::ModelLogRegressor(std::string train_file, std::string test_fi
);
}
double ModelLogRegressor::eval(double* x_in)
double ModelLogRegressor::eval(double* x_in) const
{
double result = _coefs[_task_eval].back();
int ff = 0;
......@@ -191,7 +191,7 @@ double ModelLogRegressor::eval(double* x_in)
return result;
}
std::vector<double> ModelLogRegressor::eval(std::vector<double>* x_in)
std::vector<double> ModelLogRegressor::eval(std::vector<double>* x_in) const
{
std::vector<double> result(x_in->size(), _coefs[_task_eval].back());
int ff = 0;
......
......@@ -56,14 +56,14 @@ public:
* @param fix_intercept if True then the intercept is 0.0
*/
ModelLogRegressor(
std::string prop_label,
Unit prop_unit,
std::vector<double> prop_train,
std::vector<double> prop_test,
std::vector<model_node_ptr> feats,
std::vector<int> task_sizes_train,
std::vector<int> task_sizes_test,
bool fix_intercept
const std::string prop_label,
const Unit prop_unit,
const std::vector<double> prop_train,
const std::vector<double> prop_test,
const std::vector<model_node_ptr> feats,
const std::vector<int> task_sizes_train,
const std::vector<int> task_sizes_test,
const bool fix_intercept
);
// DocString: model_log_reg_init_str
......@@ -119,7 +119,7 @@ public:
* @param x_in pointer to the new data point (order the same as appending the results of _feats[nn]->get_x_in_expr_list() for all feature)
* @return The prediction of the model for a given data point
*/
double eval(double* x_in);
double eval(double* x_in) const;
/**
* @brief Evaluate the model for a new set of new points
......@@ -127,7 +127,7 @@ public:
* @param x_in a vector of pointers to the set of values for new data points (one pointer per each feature and order the same as appending the results of _feats[nn]->get_x_in_expr_list() for all feature)
* @return The prediction of the model for a given set of data points
*/
std::vector<double> eval(std::vector<double>* x_in);
std::vector<double> eval(std::vector<double>* x_in) const;
// DocString: model_log_reg_str
/**
......@@ -150,7 +150,7 @@ public:
*
* @param res pointer to the beginning of the vector to store the residual
*/
virtual inline void copy_error(double* res){std::copy_n(_log_train_error.data(), _n_samp_train, res);}
virtual inline void copy_error(double* res) const {std::copy_n(_log_train_error.data(), _n_samp_train, res);}
};
/**
......
......@@ -4,15 +4,15 @@ ModelRegressor::ModelRegressor()
{}
ModelRegressor::ModelRegressor(
std::string prop_label,
Unit prop_unit,
std::vector<double> prop_train,
std::vector<double> prop_test,
std::vector<model_node_ptr> feats,
std::vector<int> task_sizes_train,
std::vector<int> task_sizes_test,
bool fix_intercept,
bool fill_vecs
const std::string prop_label,
const Unit prop_unit,
const std::vector<double> prop_train,
const std::vector<double> prop_test,
const std::vector<model_node_ptr> feats,
const std::vector<int> task_sizes_train,
const std::vector<int> task_sizes_test,
const bool fix_intercept,
const bool fill_vecs
) :
Model(prop_label, prop_unit, prop_train, prop_test, feats, task_sizes_train, task_sizes_test, fix_intercept),
_prop_train_est(_n_samp_train, 0.0),
......@@ -85,7 +85,7 @@ ModelRegressor::ModelRegressor(
}
}
ModelRegressor::ModelRegressor(std::string train_file)
ModelRegressor::ModelRegressor(const std::string train_file)
{
_n_samp_test = 0;
......@@ -132,7 +132,7 @@ ModelRegressor::ModelRegressor(std::string train_file)
}
}
ModelRegressor::ModelRegressor(std::string train_file, std::string test_file)
ModelRegressor::ModelRegressor(const std::string train_file, std::string test_file)
{
std::vector<std::string> split_str;
std::vector<std::string> feature_expr_train = populate_model(train_file, true);
......@@ -185,7 +185,7 @@ ModelRegressor::ModelRegressor(std::string train_file, std::string test_file)
}
}
double ModelRegressor::eval(double* x_in)
double ModelRegressor::eval(double* x_in) const
{
double result = _coefs[_task_eval].back();
int ff = 0;
......@@ -198,7 +198,7 @@ double ModelRegressor::eval(double* x_in)
return result;
}
std::vector<double> ModelRegressor::eval(std::vector<double>* x_in)
std::vector<double> ModelRegressor::eval(std::vector<double>* x_in) const
{
std::vector<double> result(x_in->size(), _coefs[_task_eval].back());