Doxygen 1.9.1
Toolkit for Adaptive Stochastic Modeling and Non-Intrusive ApproximatioN: Tasmanian v8.1
Tasmanian Sparse Grids module, example 4
Collaboration diagram for Tasmanian Sparse Grids module, example 4:

Functions

void sparse_grids_example_04 ()
 Sparse Grids Example 4: basic surrogate modeling. More...
 

Detailed Description

Example 4
Build a surrogate model to an simple function, i.e., construct an interpolant that approximates the function.

Function Documentation

◆ sparse_grids_example_04()

void sparse_grids_example_04 ( )

Sparse Grids Example 4: basic surrogate modeling.

Problems associated with statistical analysis and/or optimization often require a huger number of model realizations (i.e., samples) to compute reliable results. However, when the models are computationally expensive, collecting sufficient number of samples becomes infeasible. Surrogate modeling aims at constructing a cheap to evaluate approximate model from a limited number of samples. The model function used in this example is very simple, but it serves as a demonstration on how to construct interpolatory approximations to much harder models.

#endif
cout << "\n---------------------------------------------------------------------------------------------------\n";
cout << std::scientific; cout.precision(4);
cout << "Example 4: interpolate f(x,y) = exp(-x^2) * cos(y),"
<< "using clenshaw-curtis iptotal rule\n";
const int num_inputs = 2; // just x and y as inputs
const int num_outputs = 1; // using single-value output
const int num_samples = 1; // this is a huge number in an actual application
std::vector<double> pnts = { 0.3, 0.7 }; // points of interest where the model is not known
double reference_solution = std::exp(-0.3 * 0.3) * std::cos(0.7);
std::vector<int> polynomial_order = {6, 12}; // use two grids with different polynomial order
for(auto prec : polynomial_order){
// the first 3 inputs to make grid are always: inputs, outputs, depth
// TasGrid::type_iptotal means interpret the precision as "total degree polynomial space"
auto grid = TasGrid::makeGlobalGrid(num_inputs, num_outputs, prec,
// having constructed the initial grid
// to complete the interpolant, Tasmanian needs the model values at the needed points
auto points = grid.getNeededPoints();
// allocate a vector for the associated model values
std::vector<double> model_values(grid.getNumNeeded() * num_outputs);
for(int i=0; i<grid.getNumNeeded(); i++){
double x = points[i*num_inputs];
double y = points[i*num_inputs+1];
model_values[i] = std::exp(-x*x) * std::cos(y);
}
// feed the data to the grid
grid.loadNeededValues(model_values);
// interpolation can be performed after loadNeededPoints() is called
// note that we don't need to set the size, Tasmanian will automatically set the right size
std::vector<double> result(num_samples * num_outputs);
// evaluate() deals with a single point
// if num_samples is large, evaluateBatch() is much more efficient
grid.evaluate(pnts, result);
cout << "\n using polynomials of total degree up to: " << prec << "\n"
<< " the grid has: " << grid.getNumPoints() << " poitns\n"
<< " interpolant at (0.3,0.7): " << result[0] << "\n"
<< " error: "
<< std::abs(result[0] - reference_solution) << "\n";
}
#ifndef __TASMANIAN_DOXYGEN_SKIP
@ rule_clenshawcurtis
Classic nested rule using Chebyshev nodes with very low Lebesgue constant.
Definition: tsgEnumerates.hpp:289
@ type_iptotal
Total degree polynomial space for interpolation, i.e., the span of .
Definition: tsgEnumerates.hpp:221
TasmanianSparseGrid makeGlobalGrid(int dimensions, int outputs, int depth, TypeDepth type, TypeOneDRule rule, std::vector< int > const &anisotropic_weights=std::vector< int >(), double alpha=0.0, double beta=0.0, const char *custom_filename=nullptr, std::vector< int > const &level_limits=std::vector< int >())
Factory method, creates a new grid and calls TasmanianSparseGrid::makeGlobalGrid().
Definition: TasmanianSparseGrid.hpp:2272