14 #include "GreedySampler.h"
15 #include "utils/HDFDatabase.h"
24 GreedyErrorIndicatorPoint
26 const std::shared_ptr<Vector> & localROM)
33 getNearestPoint(
const std::vector<Vector> & param_points, Vector & point)
37 return param_points[closest_point_index];
44 double closest_dist_to_points = INT_MAX;
45 int closest_point_index = -1;
47 for (
int i = 0; i < param_points.size(); i++)
50 point.
minus(param_points[i], diff);
51 double dist = diff.
norm();
52 if (dist < closest_dist_to_points)
54 closest_dist_to_points = dist;
55 closest_point_index = i;
59 return closest_point_index;
63 getNearestPoint(std::vector<double> & param_points,
double point)
67 return param_points[closest_point_index];
74 double closest_dist_to_points = INT_MAX;
75 int closest_point_index = -1;
77 for (
int i = 0; i < param_points.size(); i++)
79 double dist = std::abs(point - param_points[i]);
80 if (dist < closest_dist_to_points)
82 closest_dist_to_points = dist;
83 closest_point_index = i;
87 return closest_point_index;
91 const std::vector<Vector> & parameter_points,
93 double relative_error_tolerance,
97 int convergence_subset_size,
98 std::string output_log_path,
99 std::string warm_start_file_name,
102 bool debug_algorithm)
109 constructObject(check_local_rom, relative_error_tolerance, alpha, max_clamp,
110 subset_size, convergence_subset_size, output_log_path, use_centroid,
111 random_seed, debug_algorithm);
115 const std::vector<double> & parameter_points,
116 bool check_local_rom,
117 double relative_error_tolerance,
121 int convergence_subset_size,
122 std::string output_log_path,
123 std::string warm_start_file_name,
126 bool debug_algorithm)
131 std::vector<Vector> parameter_points_vec;
132 for (
int i = 0; i < parameter_points.size(); i++)
135 vec.
item(0) = parameter_points[i];
136 parameter_points_vec.push_back(vec);
141 constructObject(check_local_rom, relative_error_tolerance, alpha, max_clamp,
142 subset_size, convergence_subset_size, output_log_path, use_centroid,
143 random_seed, debug_algorithm);
147 const Vector & param_space_min,
148 const Vector & param_space_max,
149 int num_parameter_points,
150 bool check_local_rom,
151 double relative_error_tolerance,
155 int convergence_subset_size,
156 std::string output_log_path,
157 std::string warm_start_file_name,
160 bool debug_algorithm)
167 constructObject(check_local_rom, relative_error_tolerance, alpha, max_clamp,
169 convergence_subset_size, output_log_path, use_centroid, random_seed,
174 double param_space_min,
175 double param_space_max,
176 int num_parameter_points,
177 bool check_local_rom,
178 double relative_error_tolerance,
182 int convergence_subset_size,
183 std::string output_log_path,
184 std::string warm_start_file_name,
187 bool debug_algorithm)
190 Vector param_space_min_vec(1,
false);
191 param_space_min_vec.
item(0) = param_space_min;
192 Vector param_space_max_vec(1,
false);
193 param_space_max_vec.
item(0) = param_space_max;
199 constructObject(check_local_rom, relative_error_tolerance, alpha, max_clamp,
201 convergence_subset_size, output_log_path, use_centroid, random_seed,
206 std::string base_file_name,
207 std::string output_log_path)
209 CAROM_ASSERT(!base_file_name.empty());
212 MPI_Initialized(&mpi_init);
214 MPI_Comm_rank(MPI_COMM_WORLD, &
d_rank);
222 load(base_file_name);
227 std::string
const& warm_start_file_name)
230 std::string full_file_name = warm_start_file_name;
232 database.
open(full_file_name,
"r");
234 sprintf(tmp,
"num_parameter_sampled_indices");
235 int num_parameter_sampled_indices;
236 database.
getInteger(tmp, num_parameter_sampled_indices);
237 if (num_parameter_sampled_indices > 0)
239 int temp_parameter_sampled_indices[num_parameter_sampled_indices];
240 sprintf(tmp,
"parameter_sampled_indices");
242 num_parameter_sampled_indices);
243 for (
int i = 0; i < num_parameter_sampled_indices; i++)
245 std::string vec_path = warm_start_file_name +
"_" + std::to_string(i);
252 double dist = diff.
norm();
265 std::string base_file_name)
268 std::string full_file_name = base_file_name;
270 database.
open(full_file_name,
"r");
272 sprintf(tmp,
"num_parameter_points");
273 int num_parameter_points;
274 database.
getInteger(tmp, num_parameter_points);
275 for (
int i = 0; i < num_parameter_points; i++)
277 std::string vec_path = base_file_name +
"_" + std::to_string(i);
283 std::string vec_path = base_file_name +
"_min_point";
286 vec_path = base_file_name +
"_max_point";
289 sprintf(tmp,
"num_parameter_sampled_indices");
290 int num_parameter_sampled_indices;
291 database.
getInteger(tmp, num_parameter_sampled_indices);
292 if (num_parameter_sampled_indices > 0)
294 int temp_parameter_sampled_indices[num_parameter_sampled_indices];
295 sprintf(tmp,
"parameter_sampled_indices");
297 num_parameter_sampled_indices);
298 for (
int i = 0; i < num_parameter_sampled_indices; i++)
305 sprintf(tmp,
"procedure_completed");
311 sprintf(tmp,
"max_error");
313 sprintf(tmp,
"curr_relative_error");
315 sprintf(tmp,
"error_indicator_tol");
317 sprintf(tmp,
"relative_error_tol");
319 sprintf(tmp,
"alpha");
321 sprintf(tmp,
"max_clamp");
323 sprintf(tmp,
"max_num_parameter_points");
325 sprintf(tmp,
"subset_size");
327 sprintf(tmp,
"convergence_subset_size");
329 sprintf(tmp,
"next_point_to_sample");
331 sprintf(tmp,
"next_point_requiring_error_indicator");
333 sprintf(tmp,
"check_local_rom");
336 sprintf(tmp,
"use_centroid");
339 sprintf(tmp,
"iteration_started");
342 sprintf(tmp,
"convergence_started");
345 sprintf(tmp,
"next_parameter_point_computed");
348 sprintf(tmp,
"point_requiring_error_indicator_computed");
351 sprintf(tmp,
"subset_created");
354 sprintf(tmp,
"debug_algorithm");
357 sprintf(tmp,
"counter");
359 sprintf(tmp,
"subset_counter");
361 sprintf(tmp,
"random_seed");
364 sprintf(tmp,
"parameter_point_random_indices");
369 sprintf(tmp,
"parameter_point_errors");
374 sprintf(tmp,
"parameter_point_local_rom");
381 std::string vec_path = base_file_name +
"_conv_" + std::to_string(i);
398 bool isGreater =
false;
418 CAROM_VERIFY(isGreater);
423 str +=
"Total number of sample points: " + std::to_string(
425 str +=
"Parameter space minimum: [ ";
431 str +=
"Parameter space maximum: [ ";
443 bool check_local_rom,
444 double relative_error_tolerance,
448 int convergence_subset_size,
449 std::string output_log_path,
452 bool debug_algorithm)
454 CAROM_VERIFY(relative_error_tolerance > 0.0);
455 CAROM_VERIFY(alpha >= 1.0);
456 CAROM_VERIFY(max_clamp >= 1.0);
457 CAROM_VERIFY(subset_size > 0);
458 CAROM_VERIFY(convergence_subset_size > 0);
459 CAROM_VERIFY(subset_size < convergence_subset_size);
460 CAROM_VERIFY(random_seed > 0);
463 MPI_Initialized(&mpi_init);
465 MPI_Comm_rank(MPI_COMM_WORLD, &
d_rank);
501 str +=
"Alpha constant: " + std::to_string(
d_alpha) +
"\n";
502 str +=
"Max clamp constant: " + std::to_string(
d_max_clamp) +
"\n";
503 str +=
"Iteration subset size: " + std::to_string(
d_subset_size) +
"\n";
530 std::shared_ptr<Vector>
535 return std::shared_ptr<Vector>(
nullptr);
539 return std::shared_ptr<Vector>(
nullptr);
544 return std::shared_ptr<Vector>(result);
569 str +=
"\nPoint sampled at [ ";
581 return std::shared_ptr<Vector>(result);
597 Vector* result2 =
nullptr;
611 std::shared_ptr<Vector>(result2));
647 std::shared_ptr<Vector>(result2));
694 str +=
"Error indicator at [ ";
698 str += std::to_string(
701 str +=
"] skipped.\n";
702 str +=
"Error indicator " + std::to_string(curr_error) +
703 " already computed at the same local ROM.\n";
718 std::shared_ptr<Vector>(result2));
726 str +=
"Error indicator at [ ";
730 str += std::to_string(
733 str +=
"] skipped.\n";
734 str +=
"Error indicator " + std::to_string(curr_error) +
735 " is less than current max error " + std::to_string(
d_max_error) +
"\n";
746 str +=
"Ran out of points to calculate error indicator for in this iteration.\n";
810 str +=
"Sampling type: " + sampling_type +
"\n";
821 str +=
"Convergence achieved.\n";
824 str =
"\nSampled Parameter Points\n";
825 std::vector<std::pair<double, int>> first_dim_of_sampled_points;
828 first_dim_of_sampled_points.push_back(std::make_pair(
831 sort(first_dim_of_sampled_points.begin(), first_dim_of_sampled_points.end());
832 for (
int i = 0; i < first_dim_of_sampled_points.size(); i++)
838 str += std::to_string(
850 CAROM_VERIFY(error >= 0);
853 if (!std::isfinite(error))
863 str +=
"Relative error computed at [ ";
869 str +=
"Relative error: " + std::to_string(error) +
"\n";
892 str +=
"The relative error was smaller than the relative error tolerance. The error indicator tolerance must increase.\n";
893 str +=
"Alpha constant * relative error tolerance: " + std::to_string(
895 str +=
"The minimum value the error indicator tolerance can take is: " +
896 std::to_string(max1) +
"\n";
897 str +=
"Max clamp constant * current max error indicator: " + std::to_string(
899 str +=
"Relative error tolerance * current max error indicator / current relative error: "
900 + std::to_string(min2) +
"\n";
901 str +=
"The maximum value the error indicator tolerance can take is the minimum of the previous two values: "
902 + std::to_string(std::min(min1, min2)) +
"\n";
915 str +=
"The relative error was larger than the relative error tolerance. The error indicator tolerance must decrease.\n";
916 str +=
"Current error indicator tolerance: " + std::to_string(
918 str +=
"Relative error tolerance * current max error indicator / current relative error: "
919 + std::to_string(min1) +
"\n";
920 str +=
"The minimum value the error indicator tolerance can take is: " +
931 str +=
"Error indicator tolerance was adaptively changed from " +
932 std::to_string(old_error_indicator_tol) +
" to " + std::to_string(
967 CAROM_VERIFY(error >= 0);
970 double proc_errors = pow(error, 2);
971 int total_vec_size = vec_size;
972 CAROM_VERIFY(MPI_Allreduce(MPI_IN_PLACE,
977 MPI_COMM_WORLD) == MPI_SUCCESS);
978 CAROM_VERIFY(MPI_Allreduce(MPI_IN_PLACE,
983 MPI_COMM_WORLD) == MPI_SUCCESS);
984 proc_errors = sqrt(proc_errors);
985 proc_errors /= total_vec_size;
987 if (!std::isfinite(proc_errors))
989 proc_errors = INT_MAX;
1009 str +=
"Error indicator computed at [ ";
1010 for (
int i = 0 ; i < errorIndicatorPoint.
dim(); i++)
1012 str += std::to_string(errorIndicatorPoint.
item(i)) +
" ";
1015 str +=
"Error indicator: " + std::to_string(proc_errors) +
"\n";
1029 std::ofstream database_history;
1031 database_history << str;
1032 database_history.close();
1069 str +=
"Local ROM error indicator computed at [ ";
1073 str += std::to_string(
1077 str +=
"Local ROM error indicator (tolerance unchecked): " + std::to_string(
1078 proc_errors) +
"\n";
1081 str +=
"Error indicator at the local ROM was higher than the previous tolerance.\n";
1082 str +=
"The error indicator tolerance should always be at least the error indicator at the local ROM.\n";
1083 str +=
"Error indicator tolerance was adaptively changed from " +
1084 std::to_string(old_error_indicator_tol) +
" to " + std::to_string(
1199 " met. Computing convergence.\n";
1212 std::vector<Vector> random_points;
1214 std::vector<std::uniform_real_distribution<double>> unif;
1221 for (
int i = 0; i < num_points; i++)
1224 for (
int j = 0; j < point.
dim(); j++)
1228 random_points.push_back(point);
1230 return random_points;
1233 std::shared_ptr<Vector>
1238 double closest_dist_to_points = INT_MAX;
1239 int closest_point_index = -1;
1245 double dist = diff.
norm();
1246 if (dist < closest_dist_to_points)
1248 closest_dist_to_points = dist;
1249 closest_point_index = *itr;
1253 if (closest_point_index == -1)
1255 return std::shared_ptr<Vector>(
nullptr);
1259 return std::shared_ptr<Vector>(result);
1265 double closest_dist_to_points = INT_MAX;
1266 int closest_point_index = -1;
1275 double dist = diff.
norm();
1276 if (dist < closest_dist_to_points)
1278 closest_dist_to_points = dist;
1279 closest_point_index = i;
1284 return closest_point_index;
1293 double closest_dist_to_points = INT_MAX;
1294 int closest_point_index = -1;
1302 double dist = diff.
norm();
1303 if (dist < closest_dist_to_points ||
1306 closest_dist_to_points = dist;
1307 closest_point_index = *itr;
1310 else if (!ignore_self)
1312 closest_dist_to_points = 0;
1313 closest_point_index = *itr;
1318 return closest_point_index;
1330 std::vector<Vector> sampled_points;
1335 return sampled_points;
1341 CAROM_ASSERT(!base_file_name.empty());
1346 std::string full_file_name = base_file_name;
1348 database.
create(full_file_name);
1350 sprintf(tmp,
"num_parameter_points");
1354 std::string vec_path = base_file_name +
"_" + std::to_string(i);
1359 std::string vec_path = base_file_name +
"_conv_" + std::to_string(i);
1363 std::string vec_path = base_file_name +
"_min_point";
1366 vec_path = base_file_name +
"_max_point";
1369 sprintf(tmp,
"num_parameter_sampled_indices");
1373 sprintf(tmp,
"parameter_sampled_indices");
1374 std::vector<int> d_parameter_sampled_indices_vec(
1380 sprintf(tmp,
"procedure_completed");
1385 sprintf(tmp,
"max_error");
1387 sprintf(tmp,
"curr_relative_error");
1389 sprintf(tmp,
"error_indicator_tol");
1391 sprintf(tmp,
"relative_error_tol");
1393 sprintf(tmp,
"alpha");
1395 sprintf(tmp,
"max_clamp");
1397 sprintf(tmp,
"max_num_parameter_points");
1399 sprintf(tmp,
"subset_size");
1401 sprintf(tmp,
"convergence_subset_size");
1403 sprintf(tmp,
"next_point_to_sample");
1405 sprintf(tmp,
"next_point_requiring_error_indicator");
1407 sprintf(tmp,
"check_local_rom");
1409 sprintf(tmp,
"use_centroid");
1411 sprintf(tmp,
"iteration_started");
1413 sprintf(tmp,
"convergence_started");
1415 sprintf(tmp,
"next_parameter_point_computed");
1417 sprintf(tmp,
"point_requiring_error_indicator_computed");
1419 sprintf(tmp,
"subset_created");
1421 sprintf(tmp,
"debug_algorithm");
1423 sprintf(tmp,
"counter");
1425 sprintf(tmp,
"subset_counter");
1427 sprintf(tmp,
"random_seed");
1430 sprintf(tmp,
"parameter_point_random_indices");
1433 sprintf(tmp,
"parameter_point_errors");
1436 sprintf(tmp,
"parameter_point_local_rom");
1442 MPI_Barrier(MPI_COMM_WORLD);
1454 str +=
"Maximum number of parameter points reached. Stopping now.\n";
void getInteger(const std::string &key, int &data)
Reads an integer associated with the supplied key from the currently open database file.
void putDouble(const std::string &key, double data)
Writes a double associated with the supplied key to currently open database file.
void putInteger(const std::string &key, int data)
Writes an integer associated with the supplied key to currently open database file.
void getDouble(const std::string &key, double &data)
Reads a double associated with the supplied key from the currently open database file.
void printErrorIndicator(const Vector &errorIndicatorPoint, double proc_errors)
Print the error indicator.
GreedySampler(const std::vector< Vector > ¶meter_points, bool check_local_rom, double relative_error_tolerance, double alpha, double max_clamp, int subset_size, int convergence_subset_size, std::string output_log_path="", std::string warm_start_file_name="", bool use_centroid=true, int random_seed=1, bool debug_algorithm=false)
Constructor.
void printConvergenceAchieved()
Print that convergence was achieved.
void setPointRelativeError(double error)
Set the relative error of the specified point.
void generateConvergenceSubset()
Generate a new set of convergence points.
GreedyErrorIndicatorPoint getNextPointRequiringRelativeError()
Returns the next parameter point for which a relative error is required.
double d_max_error
The current max error of the parameter points of the current iteration.
int getNearestNonSampledPoint(const Vector &point)
Returns the index of the nearest non-sampled parameter point to the given point.
virtual void save(std::string base_file_name)
Save the object state to a file.
bool d_subset_created
Whether the database has already created a random subset for this iteration.
int d_next_point_requiring_error_indicator
The next parameter point requiring a error indicator.
void printSamplingType(std::string sampling_type)
Print the sampling type.
void setSubsetErrorIndicator(double proc_errors)
Set the error indicator for a subset point.
int d_subset_counter
An internal subset counter.
double d_max_clamp
The max_clamp constant.
bool d_use_centroid
Whether the use the centroid heuristic for obtaining the first parameter point.
bool d_point_requiring_error_indicator_computed
Whether the database has already computed a new paramter point requiring a error indicator.
void setConvergenceErrorIndicator(double proc_errors)
Set the error indicator for a convergence point.
bool isComplete()
Check if the greedy algorithm procedure is complete.
int d_random_seed
Then random seed used to generate subsets.
int d_subset_size
The size of the subset of parameter points used per iteration.
bool d_debug_algorithm
Turn off randomness for debugging purposes.
std::vector< Vector > getParameterPointDomain()
Get the domain of the parameter points.
double d_relative_error_tol
The relative error tolerance used to terminate the greedy procedure.
std::string d_output_log_path
Output log path.
void constructObject(bool check_local_rom, double relative_error_tolerance, double alpha, double max_clamp, int subset_size, int convergence_subset_size, std::string output_log_path, bool use_centroid, int random_seed, bool debug_algorithm)
Construct the GreedySampler object.
bool d_check_local_rom
Whether the check the last sampled local ROM's error indicator after each iteration.
std::vector< int > d_parameter_point_random_indices
The parameter point indices (used to generate the random subsets).
virtual void getNextParameterPointAfterConvergenceFailure()=0
Get the next parameter point to sample after a convergence failure.
std::vector< Vector > d_convergence_points
The convergence parameter points to explore.
GreedyErrorIndicatorPoint getNextSubsetPointRequiringErrorIndicator()
Get the next subset point requiring an error indicator.
std::vector< Vector > d_parameter_points
The parameter points to explore.
int d_rank
The rank of the given processor.
double d_curr_relative_error
The current relative error of the current iteration.
std::vector< double > d_parameter_point_errors
The current errors of the parameter points.
void initializeParameterPoints()
Initialize the list of parameter point candidates to sample.
int d_counter
An internal counter.
bool d_next_parameter_point_computed
Whether the database has already computed a new parameter point to sample.
virtual ~GreedySampler()
Destructor.
void setPointErrorIndicator(double error, int vec_size)
Set the error indicator error of the specified parameter point.
std::default_random_engine rng
Random engine used to generate subsets.
GreedyErrorIndicatorPoint getNextConvergencePointRequiringErrorIndicator()
Get the next convergence point requiring an error indicator.
std::vector< int > d_parameter_point_local_rom
The local ROMs used to obtain the current errors of the parameter points.
GreedyErrorIndicatorPoint getNextPointRequiringErrorIndicator()
Returns the next parameter point for which an error indicator is required.
int d_next_point_to_sample
The next parameter point to sample.
void agnosticPrint(std::string str)
Print to output_log_file or cout.
int d_num_parameter_points
The maximum number of parameter points to sample.
std::shared_ptr< Vector > getNearestROM(const Vector &point)
Returns the nearest local ROM to the specified parameter point.
double d_error_indicator_tol
The error indicator tolerance used to terminate the greedy procedure.
virtual void load(std::string base_file_name)
Load the object state from a file.
int getNearestROMIndexToParameterPoint(int index, bool ignore_self)
Returns the index to the nearest local ROM to the specified parameter point index in the parameter po...
bool d_procedure_completed
Whether the greedy procedure has completed.
int d_convergence_subset_size
The size of the subset of parameter points used to check convergence.
bool d_convergence_started
Whether the database is in the convergence verifying phase.
void printErrorIndicatorToleranceNotMet()
Print that the error indicator was not met.
double d_alpha
The alpha constant.
std::vector< Vector > getSampledParameterPoints()
Get the sampled parameter points.
Vector d_max_param_point
The maximum value of the parameter space.
std::set< int > d_parameter_sampled_indices
The parameter points that were already sampled.
void startConvergence()
Switch to convergence mode.
Vector d_min_param_point
The minimum value of the parameter space.
void addDatabaseFromFile(std::string const &warm_start_file_name)
Do a warm start by adding the sampled parameters from the database in a file to the current database.
std::shared_ptr< Vector > getNextParameterPoint()
Returns the next parameter point for which sampling is required.
bool d_iteration_started
Whether the database has already computed a new parameter point for the current iteration.
void checkParameterPointInput()
Construct the list of parameter point candidates to sample.
std::vector< Vector > generateRandomPoints(int num_points)
Generate a vector of random points.
virtual void getDoubleArray(const std::string &key, double *data, int nelements, const bool distributed=false) override
Reads an array of doubles associated with the supplied key from the currently open HDF5 database file...
virtual void putIntegerArray(const std::string &key, const int *const data, int nelements, const bool distributed=false) override
Writes an array of integers associated with the supplied key to the currently open HDF5 database file...
virtual void getIntegerArray(const std::string &key, int *data, int nelements, const bool distributed=false) override
Reads an array of integers associated with the supplied key from the currently open HDF5 database fil...
virtual bool create(const std::string &file_name, const MPI_Comm comm=MPI_COMM_NULL) override
Creates a new HDF5 database file with the supplied name.
virtual bool open(const std::string &file_name, const std::string &type, const MPI_Comm comm=MPI_COMM_NULL) override
Opens an existing HDF5 database file with the supplied name.
virtual void putDoubleArray(const std::string &key, const double *const data, int nelements, const bool distributed=false) override
Writes an array of doubles associated with the supplied key to the currently open HDF5 database file.
virtual bool close() override
Closes the currently open HDF5 database file.
double norm() const
Form the norm of this.
std::unique_ptr< Vector > minus(const Vector &other) const
Subtracts other and this and returns the result.
void write(const std::string &base_file_name)
write Vector into (a) HDF file(s).
const double & item(int i) const
Const Vector member access.
void local_read(const std::string &base_file_name, int rank)
read read a single rank of a distributed Vector from (a) HDF file(s).
int dim() const
Returns the dimension of the Vector on this processor.
int getNearestPointIndex(const std::vector< Vector > ¶m_points, Vector &point)
Given a vector, find the nearest point in a domain.
GreedyErrorIndicatorPoint createGreedyErrorIndicatorPoint(const std::shared_ptr< Vector > &point, const std::shared_ptr< Vector > &localROM)
Create a greedy error indicator point.
int getCenterPoint(const std::vector< const Vector * > &points, bool use_centroid)
Get center point of a group of points.