1 #include "optimization/flow_constraints.hpp"     2 #include "mesh/meshmover_linear_elasticity.hpp"     4 #include "rol_to_dealii_vector.hpp"     6 #include "ode_solver/ode_solver_factory.h"     8 #include <Epetra_RowMatrixTransposer.h>    12 #include "global_counter.hpp"    20                   std::shared_ptr<dealii::TrilinosWrappers::SparseMatrix> precomputed_dXvdXp)
    21     : mpi_rank(dealii::Utilities::MPI::this_mpi_process(MPI_COMM_WORLD))
    22     , i_print(mpi_rank==0)
    24     , design_parameterization(_design_parameterization)
    25     , jacobian_prec(nullptr)
    26     , adjoint_jacobian_prec(nullptr)
    30     Assert(dg->high_order_grid == design_parameterization->high_order_grid, 
    31            dealii::ExcMessage(
"DG and DesignParameterization do not point to the same high order grid."));
    33     design_parameterization->initialize_design_variables(design_var);
    34     const unsigned int n_design_variables = design_parameterization->get_number_of_design_variables();
    36     if (precomputed_dXvdXp) {
    37         if (precomputed_dXvdXp->m() == dg->high_order_grid->volume_nodes.size() && precomputed_dXvdXp->n() == n_design_variables) {
    38             dXvdXp.copy_from(*precomputed_dXvdXp);
    41         design_parameterization->compute_dXv_dXp(dXvdXp);
    44     dealii::ParameterHandler parameter_handler;
    46     this->linear_solver_param.parse_parameters (parameter_handler);
    47     this->linear_solver_param.max_iterations = 1000;
    48     this->linear_solver_param.restart_number = 200;
    49     this->linear_solver_param.linear_residual = 1e-17;
    51     this->linear_solver_param.ilut_fill = 50;
    52     this->linear_solver_param.ilut_drop = 1e-8;
    55     this->linear_solver_param.ilut_atol = 1e-5;
    56     this->linear_solver_param.ilut_rtol = 1.0+1e-2;
    57     this->linear_solver_param.linear_solver_output = Parameters::OutputEnum::verbose;
    58     this->linear_solver_param.linear_solver_type = Parameters::LinearSolverParam::LinearSolverEnum::gmres;
    66     destroy_JacobianPreconditioner_1();
    67     destroy_AdjointJacobianPreconditioner_1();
    72 ::update_1( 
const ROL::Vector<double>& des_var_sim, 
bool flag, 
int iter )
    74     (void) flag; (void) iter;
    76     dg->solution.update_ghost_values();
    81 ::update_2( 
const ROL::Vector<double>& des_var_ctl, 
bool flag, 
int iter )
    83     (void) flag; (void) iter;
    85     bool mesh_updated = design_parameterization->update_mesh_from_design_variables(dXvdXp, design_var);
    88         dg->output_results_vtk(iupdate);
    89         design_parameterization->output_design_variables(iupdate);
    97     ROL::Vector<double>& constraint_values,
    98     ROL::Vector<double>& des_var_sim,
    99     const ROL::Vector<double>& des_var_ctl,
   104     update_2(des_var_ctl);
   106     dg->output_results_vtk(i_out++);
   107     design_parameterization->output_design_variables(i_out);
   109     ode_solver_1->steady_state();
   111     dg->assemble_residual();
   112     tol = dg->get_residual_l2norm();
   114     constraint = dg->right_hand_side;
   116     des_var_sim_v = dg->solution;
   122     ROL::Vector<double>& constraint_values,
   123     const ROL::Vector<double>& des_var_sim,
   124     const ROL::Vector<double>& des_var_ctl,
   129     update_1(des_var_sim);
   130     update_2(des_var_ctl);
   132     dg->assemble_residual();
   134     constraint = dg->right_hand_side;
   140     ROL::Vector<double>& output_vector,
   141     const ROL::Vector<double>& input_vector,
   142     const ROL::Vector<double>& des_var_sim,
   143     const ROL::Vector<double>& des_var_ctl,
   148     update_1(des_var_sim);
   149     update_2(des_var_ctl);
   151     const bool compute_dRdW=
true; 
const bool compute_dRdX=
false; 
const bool compute_d2R=
false;
   152     dg->assemble_residual(compute_dRdW, compute_dRdX, compute_d2R, flow_CFL_);
   156     this->dg->system_matrix.vmult(output_vector_v, input_vector_v);
   166     ROL::Vector<double>& output_vector,
   167     const ROL::Vector<double>& input_vector,
   168     const ROL::Vector<double>& des_var_sim,
   169     const ROL::Vector<double>& des_var_ctl,
   173     update_1(des_var_sim);
   174     update_2(des_var_ctl);
   176     const bool compute_dRdW=
true; 
const bool compute_dRdX=
false; 
const bool compute_d2R=
false;
   177     dg->assemble_residual(compute_dRdW, compute_dRdX, compute_d2R, flow_CFL_);
   179     if(i_print) std::cout << __PRETTY_FUNCTION__ << std::endl;
   205     solve_linear (dg->system_matrix, input_vector_v, output_vector_v, this->linear_solver_param);
   218     delete jacobian_prec;
   219     jacobian_prec = 
nullptr;
   225     delete adjoint_jacobian_prec;
   226     adjoint_jacobian_prec = 
nullptr;
   232     const ROL::Vector<double>& des_var_sim,
   233     const ROL::Vector<double>& des_var_ctl)
   235     update_1(des_var_sim);
   236     update_2(des_var_ctl);
   238     const bool compute_dRdW=
true; 
const bool compute_dRdX=
false; 
const bool compute_d2R=
false;
   239     dg->assemble_residual(compute_dRdW, compute_dRdX, compute_d2R, flow_CFL_);
   241     Epetra_CrsMatrix * jacobian = 
const_cast<Epetra_CrsMatrix *
>(&(dg->system_matrix.trilinos_matrix()));
   243     destroy_JacobianPreconditioner_1();
   246     Teuchos::ParameterList List;
   248     const std::string PrecType = 
"ILUT"; 
   249     List.set(
"fact: ilut level-of-fill", 50.0);
   250     List.set(
"fact: absolute threshold", 1e-3);
   251     List.set(
"fact: relative threshold", 1.01);
   252     List.set(
"fact: drop tolerance", 0.0);
   257     List.set(
"schwarz: reordering type", 
"rcm");
   258     const int OverlapLevel = 1; 
   259     jacobian_prec = Factory.Create(PrecType, jacobian, OverlapLevel);
   260     assert (jacobian_prec != 0);
   265     IFPACK_CHK_ERR(jacobian_prec->SetParameters(List));
   266     IFPACK_CHK_ERR(jacobian_prec->Initialize());
   267     IFPACK_CHK_ERR(jacobian_prec->Compute());
   276     const ROL::Vector<double>& des_var_sim,
   277     const ROL::Vector<double>& des_var_ctl)
   279     update_1(des_var_sim);
   280     update_2(des_var_ctl);
   282     const bool compute_dRdW=
true; 
const bool compute_dRdX=
false; 
const bool compute_d2R=
false;
   283     dg->assemble_residual(compute_dRdW, compute_dRdX, compute_d2R, flow_CFL_);
   285     Epetra_CrsMatrix * adjoint_jacobian = 
const_cast<Epetra_CrsMatrix *
>(&(dg->system_matrix_transpose.trilinos_matrix()));
   287     destroy_AdjointJacobianPreconditioner_1();
   290     Teuchos::ParameterList List;
   292     const std::string PrecType = 
"ILUT"; 
   293     List.set(
"fact: ilut level-of-fill", 50.0);
   294     List.set(
"fact: absolute threshold", 1e-3);
   295     List.set(
"fact: relative threshold", 1.01);
   296     List.set(
"fact: drop tolerance", 0.0);
   301     List.set(
"schwarz: reordering type", 
"rcm");
   302     const int OverlapLevel = 1; 
   303     adjoint_jacobian_prec = Factory.Create(PrecType, adjoint_jacobian, OverlapLevel);
   304     assert (adjoint_jacobian_prec != 0);
   306     IFPACK_CHK_ERR(adjoint_jacobian_prec->SetParameters(List));
   307     IFPACK_CHK_ERR(adjoint_jacobian_prec->Initialize());
   308     IFPACK_CHK_ERR(adjoint_jacobian_prec->Compute());
   317     ROL::Vector<double>& output_vector,
   318     const ROL::Vector<double>& input_vector,
   319     const ROL::Vector<double>& des_var_sim,
   320     const ROL::Vector<double>& des_var_ctl,
   325     if(i_print) std::cout << __PRETTY_FUNCTION__ << std::endl;
   331     Epetra_Vector input_trilinos(View,
   332                     dg->system_matrix.trilinos_matrix().DomainMap(),
   333                     input_vector_v.begin());
   334     Epetra_Vector output_trilinos(View,
   335                     dg->system_matrix.trilinos_matrix().RangeMap(),
   336                     output_vector_v.begin());
   337     jacobian_prec->ApplyInverse (input_trilinos, output_trilinos);
   349     ROL::Vector<double>& output_vector,
   350     const ROL::Vector<double>& input_vector,
   351     const ROL::Vector<double>& des_var_sim,
   352     const ROL::Vector<double>& des_var_ctl,
   357     if(i_print) std::cout << __PRETTY_FUNCTION__ << std::endl;
   363     Epetra_Vector input_trilinos(View,
   364                     dg->system_matrix_transpose.trilinos_matrix().DomainMap(),
   365                     input_vector_v.begin());
   366     Epetra_Vector output_trilinos(View,
   367                     dg->system_matrix_transpose.trilinos_matrix().RangeMap(),
   368                     output_vector_v.begin());
   369     adjoint_jacobian_prec->ApplyInverse (input_trilinos, output_trilinos);
   380 const ROL::Vector<double>& input_vector,
   381 const ROL::Vector<double>& des_var_sim,
   382 const ROL::Vector<double>& des_var_ctl,
   386     if(i_print) std::cout << __PRETTY_FUNCTION__ << std::endl;
   387     update_1(des_var_sim);
   388     update_2(des_var_ctl);
   390     const bool compute_dRdW=
true; 
const bool compute_dRdX=
false; 
const bool compute_d2R=
false;
   391     dg->assemble_residual(compute_dRdW, compute_dRdX, compute_d2R, flow_CFL_);
   397     solve_linear (dg->system_matrix_transpose, input_vector_v, output_vector_v, this->linear_solver_param);
   404 const ROL::Vector<double>& input_vector,
   405 const ROL::Vector<double>& des_var_sim,
   406 const ROL::Vector<double>& des_var_ctl,
   410     if(i_print) std::cout << __PRETTY_FUNCTION__ << std::endl;
   411     update_1(des_var_sim);
   412     update_2(des_var_ctl);
   436     auto dXvdXp_input = dg->high_order_grid->volume_nodes;
   437     dXvdXp.vmult(dXvdXp_input, input_vector_v);
   442         const bool compute_dRdW=
false; 
const bool compute_dRdX=
true; 
const bool compute_d2R=
false;
   443         dg->assemble_residual(compute_dRdW, compute_dRdX, compute_d2R, flow_CFL_);
   444         dg->dRdXv.vmult(output_vector_v, dXvdXp_input);
   454 const ROL::Vector<double>& input_vector,
   455 const ROL::Vector<double>& des_var_sim,
   456 const ROL::Vector<double>& des_var_ctl,
   460     if(i_print) std::cout << __PRETTY_FUNCTION__ << std::endl;
   461     update_1(des_var_sim);
   462     update_2(des_var_ctl);
   464     const bool compute_dRdW=
true; 
const bool compute_dRdX=
false; 
const bool compute_d2R=
false;
   465     dg->assemble_residual(compute_dRdW, compute_dRdX, compute_d2R, flow_CFL_);
   469     this->dg->system_matrix.Tvmult(output_vector_v, input_vector_v);
   478 const ROL::Vector<double>& input_vector,
   479 const ROL::Vector<double>& des_var_sim,
   480 const ROL::Vector<double>& des_var_ctl,
   484     if(i_print) std::cout << __PRETTY_FUNCTION__ << std::endl;
   485     update_1(des_var_sim);
   486     update_2(des_var_ctl);
   491     auto input_dRdXv = dg->high_order_grid->volume_nodes;
   493         const bool compute_dRdW=
false; 
const bool compute_dRdX=
true; 
const bool compute_d2R=
false;
   494         dg->assemble_residual(compute_dRdW, compute_dRdX, compute_d2R, flow_CFL_);
   495         dg->dRdXv.Tvmult(input_dRdXv, input_vector_v);
   518     dXvdXp.Tvmult(output_vector_v, input_dRdXv);
   527                                   const ROL::Vector<double> &dual,
   528                                   const ROL::Vector<double> &input_vector,
   529                                   const ROL::Vector<double> &des_var_sim,
   530                                   const ROL::Vector<double> &des_var_ctl,
   536     if(i_print) std::cout << __PRETTY_FUNCTION__ << std::endl;
   539     dg->dual.update_ghost_values();
   540     update_1(des_var_sim);
   541     update_2(des_var_ctl);
   543     const bool compute_dRdW=
false; 
const bool compute_dRdX=
false; 
const bool compute_d2R=
true;
   544     dg->assemble_residual(compute_dRdW, compute_dRdX, compute_d2R, flow_CFL_);
   554                                   const ROL::Vector<double> &dual,
   555                                   const ROL::Vector<double> &input_vector,
   556                                   const ROL::Vector<double> &des_var_sim,
   557                                   const ROL::Vector<double> &des_var_ctl,
   563     if(i_print) std::cout << __PRETTY_FUNCTION__ << std::endl;
   565     update_1(des_var_sim);
   566     update_2(des_var_ctl);
   569     dg->dual.update_ghost_values();
   573     auto input_d2RdWdX = dg->high_order_grid->volume_nodes;
   575         const bool compute_dRdW=
false; 
const bool compute_dRdX=
false; 
const bool compute_d2R=
true;
   576         dg->assemble_residual(compute_dRdW, compute_dRdX, compute_d2R, flow_CFL_);
   577         dg->d2RdWdX.Tvmult(input_d2RdWdX, input_vector_v);
   600     dXvdXp.Tvmult(output_vector_v, input_d2RdWdX);
   609     ROL::Vector<double> &output_vector,
   610     const ROL::Vector<double> &dual,
   611     const ROL::Vector<double> &input_vector,
   612     const ROL::Vector<double> &des_var_sim,
   613     const ROL::Vector<double> &des_var_ctl,
   620     if(i_print) std::cout << __PRETTY_FUNCTION__ << std::endl;
   622     update_1(des_var_sim);
   623     update_2(des_var_ctl);
   626     dg->dual.update_ghost_values();
   650     auto dXvdXp_input = dg->high_order_grid->volume_nodes;
   651     dXvdXp.vmult(dXvdXp_input, input_vector_v);
   655         const bool compute_dRdW=
false; 
const bool compute_dRdX=
false; 
const bool compute_d2R=
true;
   656         dg->assemble_residual(compute_dRdW, compute_dRdX, compute_d2R, flow_CFL_);
   657         dg->d2RdWdX.vmult(output_vector_v, dXvdXp_input);
   668     ROL::Vector<double> &output_vector,
   669     const ROL::Vector<double> &dual,
   670     const ROL::Vector<double> &input_vector,
   671     const ROL::Vector<double> &des_var_sim,
   672     const ROL::Vector<double> &des_var_ctl,
   679     if(i_print) std::cout << __PRETTY_FUNCTION__ << std::endl;
   682     update_1(des_var_sim);
   683     update_2(des_var_ctl);
   686     dg->dual.update_ghost_values();
   710     auto dXvdXp_input = dg->high_order_grid->volume_nodes;
   711     dXvdXp.vmult(dXvdXp_input, input_vector_v);
   713     auto d2RdXdX_dXvdXp_input = dg->high_order_grid->volume_nodes;
   715         const bool compute_dRdW=
false; 
const bool compute_dRdX=
false; 
const bool compute_d2R=
true;
   716         dg->assemble_residual(compute_dRdW, compute_dRdX, compute_d2R, flow_CFL_);
   717         dg->d2RdXdX.vmult(d2RdXdX_dXvdXp_input, dXvdXp_input);
   740     dXvdXp.Tvmult(output_vector_v, d2RdXdX_dXvdXp_input);
 void applyAdjointJacobian_1(ROL::Vector< double > &output_vector, const ROL::Vector< double > &input_vector, const ROL::Vector< double > &des_var_sim, const ROL::Vector< double > &des_var_ctl, double &) override
Applies the Jacobian of the Constraints w. r. t. the simulation variables onto a vector. 
void update_1(const ROL::Vector< double > &des_var_sim, bool flag=true, int iter=-1)
Update the simulation variables. 
void applyAdjointJacobian_2(ROL::Vector< double > &output_vector, const ROL::Vector< double > &input_vector, const ROL::Vector< double > &des_var_sim, const ROL::Vector< double > &des_var_ctl, double &) override
Applies the Jacobian of the Constraints w. r. t. the control variables onto a vector. 
static void declare_parameters(dealii::ParameterHandler &prm)
Declares the possible variables and sets the defaults. 
void applyAdjointHessian_12(ROL::Vector< double > &output_vector, const ROL::Vector< double > &dual, const ROL::Vector< double > &input_vector, const ROL::Vector< double > &des_var_sim, const ROL::Vector< double > &des_var_ctl, double &tol) override
Applies the adjoint of the Hessian of the constraints w. r. t. the simulation variables onto a vector...
std::pair< unsigned int, double > solve_linear(const dealii::TrilinosWrappers::SparseMatrix &system_matrix, dealii::LinearAlgebra::distributed::Vector< double > &right_hand_side, dealii::LinearAlgebra::distributed::Vector< double > &solution, const Parameters::LinearSolverParam ¶m)
void applyInverseAdjointJacobianPreconditioner_1(ROL::Vector< double > &output_vector, const ROL::Vector< double > &input_vector, const ROL::Vector< double > &des_var_sim, const ROL::Vector< double > &des_var_ctl, double &)
Applies the inverse Adjoint Jacobian preconditioner. 
void destroy_JacobianPreconditioner_1()
Frees Jacobian preconditioner from memory;. 
void destroy_AdjointJacobianPreconditioner_1()
Frees adjoint Jacobian preconditioner from memory;. 
Files for the baseline physics. 
void applyJacobian_2(ROL::Vector< double > &output_vector, const ROL::Vector< double > &input_vector, const ROL::Vector< double > &des_var_sim, const ROL::Vector< double > &des_var_ctl, double &) override
Applies the Jacobian of the Constraints w. r. t. the control variables onto a vector. 
void applyInverseJacobian_1(ROL::Vector< double > &output_vector, const ROL::Vector< double > &input_vector, const ROL::Vector< double > &des_var_sim, const ROL::Vector< double > &des_var_ctl, double &) override
Applies the inverse Jacobian of the Constraints w. r. t. the simulation variables onto a vector...
void applyAdjointHessian_11(ROL::Vector< double > &output_vector, const ROL::Vector< double > &dual, const ROL::Vector< double > &input_vector, const ROL::Vector< double > &des_var_sim, const ROL::Vector< double > &des_var_ctl, double &tol) override
Applies the adjoint of the Hessian of the constraints w. r. t. the simulation variables onto a vector...
void applyJacobian_1(ROL::Vector< double > &output_vector, const ROL::Vector< double > &input_vector, const ROL::Vector< double > &des_var_sim, const ROL::Vector< double > &des_var_ctl, double &) override
Applies the Jacobian of the Constraints w. r. t. the simulation variables onto a vector. 
void value(ROL::Vector< double > &constraint_values, const ROL::Vector< double > &des_var_sim, const ROL::Vector< double > &des_var_ctl, double &) override
Returns the current constraint residual given a set of control and simulation variables. 
void solve(ROL::Vector< double > &constraint_values, ROL::Vector< double > &des_var_sim, const ROL::Vector< double > &des_var_ctl, double &) override
Solve the Simulation Constraint and returns the constraints values. 
Abstract class for design parameterization. Objective function and the constraints take this class's ...
Use DGBase as a Simulation Constraint ROL::Constraint_SimOpt. 
~FlowConstraints()
Destructor. 
int construct_AdjointJacobianPreconditioner_1(const ROL::Vector< double > &des_var_sim, const ROL::Vector< double > &des_var_ctl)
Constructs the Adjoint Jacobian preconditioner. 
void applyInverseAdjointJacobian_1(ROL::Vector< double > &output_vector, const ROL::Vector< double > &input_vector, const ROL::Vector< double > &des_var_sim, const ROL::Vector< double > &des_var_ctl, double &) override
Applies the adjoint Jacobian of the Constraints w. r. t. the simulation variables onto a vector...
void applyInverseJacobianPreconditioner_1(ROL::Vector< double > &output_vector, const ROL::Vector< double > &input_vector, const ROL::Vector< double > &des_var_sim, const ROL::Vector< double > &des_var_ctl, double &)
Applies the inverse Jacobian preconditioner. 
void applyAdjointHessian_22(ROL::Vector< double > &output_vector, const ROL::Vector< double > &dual, const ROL::Vector< double > &input_vector, const ROL::Vector< double > &des_var_sim, const ROL::Vector< double > &des_var_ctl, double &tol) override
Applies the adjoint of the Hessian of the constraints w. r. t. the simulation variables onto a vector...
void update_2(const ROL::Vector< double > &des_var_ctl, bool flag=true, int iter=-1)
Update the control variables. 
FlowConstraints(std::shared_ptr< DGBase< dim, double >> &_dg, std::shared_ptr< BaseParameterization< dim >> _design_parameterization, std::shared_ptr< dealii::TrilinosWrappers::SparseMatrix > precomputed_dXvdXp=nullptr)
Constructor. 
void applyAdjointHessian_21(ROL::Vector< double > &output_vector, const ROL::Vector< double > &dual, const ROL::Vector< double > &input_vector, const ROL::Vector< double > &des_var_sim, const ROL::Vector< double > &des_var_ctl, double &tol) override
Applies the adjoint of the Hessian of the constraints w. r. t. the simulation variables onto a vector...
DGBase is independent of the number of state variables. 
static std::shared_ptr< ODESolverBase< dim, real, MeshType > > create_ODESolver(std::shared_ptr< DGBase< dim, real, MeshType > > dg_input)
Creates either implicit or explicit ODE solver based on parameter value(no POD basis given) ...
const dealii::LinearAlgebra::distributed::Vector< double > & ROL_vector_to_dealii_vector_reference(const ROL::Vector< double > &x)
Access the read-write deali.II Vector stored within the ROL::Vector. 
int construct_JacobianPreconditioner_1(const ROL::Vector< double > &des_var_sim, const ROL::Vector< double > &des_var_ctl)
Constructs the Jacobian preconditioner.