openGPMP
Open Source Mathematics Package
regularizers.cpp
Go to the documentation of this file.
1 /*************************************************************************
2  *
3  * Project
4  * _____ _____ __ __ _____
5  * / ____| __ \| \/ | __ \
6  * ___ _ __ ___ _ __ | | __| |__) | \ / | |__) |
7  * / _ \| '_ \ / _ \ '_ \| | |_ | ___/| |\/| | ___/
8  *| (_) | |_) | __/ | | | |__| | | | | | | |
9  * \___/| .__/ \___|_| |_|\_____|_| |_| |_|_|
10  * | |
11  * |_|
12  *
13  * Copyright (C) Akiel Aries, <akiel@akiel.org>, et al.
14  *
15  * This software is licensed as described in the file LICENSE, which
16  * you should have received as part of this distribution. The terms
17  * among other details are referenced in the official documentation
18  * seen here : https://akielaries.github.io/openGPMP/ along with
19  * important files seen in this project.
20  *
21  * You may opt to use, copy, modify, merge, publish, distribute
22  * and/or sell copies of the Software, and permit persons to whom
23  * the Software is furnished to do so, under the terms of the
24  * LICENSE file. As this is an Open Source effort, all implementations
25  * must be of the same methodology.
26  *
27  *
28  *
29  * This software is distributed on an AS IS basis, WITHOUT
30  * WARRANTY OF ANY KIND, either express or implied.
31  *
32  ************************************************************************/
33 #include <algorithm>
34 #include <cmath>
36 #include <random>
37 
38 double
39 gpmp::ml::Regularize::l1_regularization(const std::vector<double> &weights,
40  double lambda) {
41  double penalty = 0.0;
42  for (double weight : weights) {
43  penalty += std::abs(weight);
44  }
45  return lambda * penalty;
46 }
47 
48 double
49 gpmp::ml::Regularize::l2_regularization(const std::vector<double> &weights,
50  double lambda) {
51  double penalty = 0.0;
52  for (double weight : weights) {
53  penalty += weight * weight;
54  }
55  return 0.5 * lambda * penalty;
56 }
57 
59  const std::vector<double> &weights,
60  double lambda1,
61  double lambda2) {
62  double l1_penalty = l1_regularization(weights, lambda1);
63  double l2_penalty = l2_regularization(weights, lambda2);
64  return l1_penalty + l2_penalty;
65 }
66 
68  int num_neurons) {
69  return 0.5 * dropout_rate * num_neurons;
70 }
71 
72 bool gpmp::ml::Regularize::early_stopping(double current_val_loss,
73  double &best_val_loss,
74  int patience,
75  int epoch) {
76  if (current_val_loss < best_val_loss) {
77  best_val_loss = current_val_loss;
78  patience = epoch + patience; // Reset patience
79  } else {
80  if (epoch >= patience) {
81  return true; // Stop training
82  }
83  }
84  return false; // Continue training
85 }
86 
88  const std::vector<std::vector<double>> &predictions) {
89  std::vector<double> ensemble;
90  if (!predictions.empty()) {
91  ensemble.resize(predictions.front().size(), 0.0);
92  for (const auto &prediction : predictions) {
93  for (size_t i = 0; i < prediction.size(); ++i) {
94  ensemble[i] += prediction[i];
95  }
96  }
97  for (auto &val : ensemble) {
98  val /= predictions.size();
99  }
100  }
101  return ensemble;
102 }
103 
104 void gpmp::ml::Regularize::max_norm_regularization(std::vector<double> &weights,
105  double max_norm) {
106  double norm = 0.0;
107  for (double &weight : weights) {
108  norm += weight * weight;
109  }
110  norm = sqrt(norm);
111  if (norm > max_norm) {
112  double factor = max_norm / norm;
113  for (double &weight : weights) {
114  weight *= factor;
115  }
116  }
117 }
118 
120  std::vector<double> &weights,
121  double lambda) {
122  for (double &weight : weights) {
123  weight *= (1.0 - lambda);
124  }
125 }
126 
127 std::vector<std::vector<double>> gpmp::ml::Regularize::batch_normalization(
128  const std::vector<std::vector<double>> &input_data,
129  double epsilon,
130  double scale,
131  double shift) {
132  std::vector<std::vector<double>> normalized_data;
133  for (const auto &instance : input_data) {
134  double mean = 0.0;
135  for (double val : instance) {
136  mean += val;
137  }
138  mean /= instance.size();
139 
140  double variance = 0.0;
141  for (double val : instance) {
142  variance += (val - mean) * (val - mean);
143  }
144  variance /= instance.size();
145 
146  double std_dev = sqrt(variance + epsilon);
147 
148  std::vector<double> normalized_instance;
149  for (double val : instance) {
150  double normalized_val = scale * ((val - mean) / std_dev) + shift;
151  normalized_instance.push_back(normalized_val);
152  }
153  normalized_data.push_back(normalized_instance);
154  }
155  return normalized_data;
156 }
157 
158 std::vector<std::vector<double>> gpmp::ml::Regularize::data_augmentation(
159  const std::vector<std::vector<double>> &input_data,
160  int augmentation_factor) {
161  std::vector<std::vector<double>> augmented_data;
162  std::random_device rd;
163  std::mt19937 gen(rd());
164 
165  for (const auto &instance : input_data) {
166  augmented_data.push_back(instance);
167  for (int i = 1; i < augmentation_factor; ++i) {
168  std::vector<double> augmented_instance = instance;
169  std::shuffle(augmented_instance.begin(),
170  augmented_instance.end(),
171  gen);
172  augmented_data.push_back(augmented_instance);
173  }
174  }
175  return augmented_data;
176 }
static double l2_regularization(const std::vector< double > &weights, double lambda)
Computes L2 regularization penalty (Ridge regression)
static std::vector< double > ensemble_predictions(const std::vector< std::vector< double >> &predictions)
Combines predictions from multiple models using ensembling.
static void max_norm_regularization(std::vector< double > &weights, double max_norm)
Applies max norm regularization to the weights.
static std::vector< std::vector< double > > data_augmentation(const std::vector< std::vector< double >> &input_data, int augmentation_factor)
Applies data augmentation to the input data.
static std::vector< std::vector< double > > batch_normalization(const std::vector< std::vector< double >> &input_data, double epsilon=1e-5, double scale=1.0, double shift=0.0)
Applies batch normalization to the input data.
static double elastic_net_regularization(const std::vector< double > &weights, double lambda1, double lambda2)
Computes Elastic Net regularization penalty.
static double l1_regularization(const std::vector< double > &weights, double lambda)
Computes L1 regularization penalty (Lasso regression)
static double dropout_regularization(double dropout_rate, int num_neurons)
Computes Dropout regularization penalty.
static void weight_decay_regularization(std::vector< double > &weights, double lambda)
Applies weight decay regularization to the weights.
static bool early_stopping(double current_val_loss, double &best_val_loss, int patience, int epoch)
Performs early stopping based on validation loss.