68 #include "libmesh/equation_systems.h"
69 #include "libmesh/auto_ptr.h"
70 #include "libmesh/twostep_time_solver.h"
71 #include "libmesh/euler_solver.h"
72 #include "libmesh/euler2_solver.h"
73 #include "libmesh/steady_solver.h"
74 #include "libmesh/newton_solver.h"
75 #include "libmesh/numeric_vector.h"
76 #include "libmesh/petsc_diff_solver.h"
77 #include "libmesh/mesh.h"
78 #include "libmesh/mesh_tools.h"
79 #include "libmesh/mesh_base.h"
80 #include "libmesh/mesh_refinement.h"
81 #include "libmesh/system.h"
82 #include "libmesh/system_norm.h"
83 #include "libmesh/adjoint_residual_error_estimator.h"
84 #include "libmesh/const_fem_function.h"
85 #include "libmesh/error_vector.h"
86 #include "libmesh/fem_function_base.h"
87 #include "libmesh/getpot.h"
88 #include "libmesh/gmv_io.h"
89 #include "libmesh/exodusII_io.h"
90 #include "libmesh/kelly_error_estimator.h"
91 #include "libmesh/parameter_vector.h"
92 #include "libmesh/patch_recovery_error_estimator.h"
93 #include "libmesh/petsc_vector.h"
94 #include "libmesh/sensitivity_data.h"
95 #include "libmesh/tecplot_io.h"
96 #include "libmesh/uniform_refinement_estimator.h"
97 #include "libmesh/qoi_set.h"
98 #include "libmesh/weighted_patch_recovery_error_estimator.h"
99 #include "libmesh/enum_solver_package.h"
100 #include "libmesh/enum_xdr_mode.h"
106 #include "femparameters.h"
119 std::string solution_type,
121 std::string extension,
124 std::ostringstream file_name;
125 file_name << solution_type
145 return file_name.str();
152 std::string solution_type,
157 #ifdef LIBMESH_HAVE_GMV
160 std::ostringstream file_name_gmv;
161 file_name_gmv << solution_type
174 (file_name_gmv.str(), es);
178 #ifdef LIBMESH_HAVE_TECPLOT_API
181 std::ostringstream file_name_tecplot;
182 file_name_tecplot << solution_type
196 (file_name_tecplot.str(), es);
217 #ifdef LIBMESH_HAVE_EXODUS_API
228 std::ostringstream file_name_exodus;
230 file_name_exodus << solution_type <<
".e";
232 file_name_exodus <<
"-s"
273 unsigned int newton_steps,
274 unsigned int krylov_steps,
276 unsigned int tv_usec)
287 std::ofstream activemesh (
"out_activemesh.m",
289 activemesh.precision(17);
290 activemesh << (a_step + 1) <<
' '
291 << n_active_elem <<
' '
292 << n_active_dofs << std::endl;
295 std::ofstream solvesteps (
"out_solvesteps.m",
297 solvesteps.precision(17);
298 solvesteps << newton_steps <<
' '
299 << krylov_steps << std::endl;
302 std::ofstream clocktime (
"out_clocktime.m",
304 clocktime.precision(17);
305 clocktime << tv_sec <<
'.' << tv_usec << std::endl;
314 std::ofstream clocktime (
"out_clocktime.m",
316 clocktime <<
"];" << std::endl;
320 std::ofstream activemesh (
"out_activemesh.m",
322 activemesh <<
"];" << std::endl;
324 std::ofstream solvesteps (
"out_solvesteps.m",
326 solvesteps <<
"];" << std::endl;
330 std::ofstream times (
"out_time.m",
332 times <<
"];" << std::endl;
333 std::ofstream timesteps (
"out_timesteps.m",
335 timesteps <<
"];" << std::endl;
339 std::ofstream changerate (
"out_changerate.m",
341 changerate <<
"];" << std::endl;
346 std::ofstream complete (
"complete");
347 complete <<
"complete" << std::endl;
351 #if defined(LIBMESH_HAVE_GMV) || defined(LIBMESH_HAVE_TECPLOT_API)
354 unsigned int t_number,
355 unsigned int a_number,
357 std::string error_type)
367 #ifdef LIBMESH_HAVE_GMV
370 std::ostringstream error_gmv;
371 error_gmv <<
"error.gmv."
387 #ifdef LIBMESH_HAVE_TECPLOT_API
390 std::ostringstream error_tecplot;
391 error_tecplot <<
"error.plt."
411 std::string solution_type,
416 std::string file_name_mesh, file_name_soln;
420 file_name_mesh =
numbered_filename(t_step, a_step, solution_type,
"mesh",
"xda", param);
421 file_name_soln =
numbered_filename(t_step, a_step, solution_type,
"soln",
"xda", param);
425 file_name_mesh =
numbered_filename(t_step, a_step, solution_type,
"mesh",
"xdr", param);
426 file_name_soln =
numbered_filename(t_step, a_step, solution_type,
"soln",
"xdr", param);
439 for (
unsigned int i = 0; i != es.
n_systems(); ++i)
443 Real current_time = 0., current_timestep = 0.;
447 std::ifstream times (
"out_time.m");
448 std::ifstream timesteps (
"out_timesteps.m");
449 if (times.is_open() && timesteps.is_open())
452 const unsigned int headersize = 25;
453 char header[headersize];
454 timesteps.getline (header, headersize);
455 if (strcmp(header,
"vector_timesteps = [") != 0)
456 libmesh_error_msg(
"Bad header in out_timesteps.m:\n" << header);
458 times.getline (header, headersize);
459 if (strcmp(header,
"vector_time = [") != 0)
460 libmesh_error_msg(
"Bad header in out_time.m:\n" << header);
463 for (
unsigned int i = 0; i != t_step; ++i)
466 libmesh_error_msg(
"Error: File out_time.m is in non-good state.");
467 times >> current_time;
468 timesteps >> current_timestep;
472 current_time += current_timestep;
475 libmesh_error_msg(
"Error opening out_time.m or out_timesteps.m");
478 current_time = t_step * param.
deltat;
480 for (
unsigned int i = 0; i != es.
n_systems(); ++i)
511 innersolver = euler2solver;
519 innersolver = eulersolver;
522 libmesh_error_msg(
"Don't recognize core TimeSolver type: " << param.
timesolver_core);
541 system.
time_solver = libmesh_make_unique<SteadySolver>(system);
543 system.
time_solver->reduce_deltat_on_diffsolver_failure =
556 #ifdef LIBMESH_HAVE_PETSC
560 libmesh_error_msg(
"This example requires libMesh to be compiled with PETSc support.");
577 if (system.
time_solver->reduce_deltat_on_diffsolver_failure)
590 #ifdef LIBMESH_ENABLE_AMR
603 return std::unique_ptr<MeshRefinement>(mesh_refinement);
606 #endif // LIBMESH_ENABLE_AMR
612 return libmesh_make_unique<KellyErrorEstimator>();
618 std::unique_ptr<ErrorEstimator>
620 std::vector<std::vector<Real>> & term_weights,
621 std::vector<FEMNormType> & primal_error_norm_type,
622 std::vector<FEMNormType> & dual_error_norm_type)
640 std::size_t size = primal_error_norm_type.size();
642 libmesh_assert_equal_to (size, dual_error_norm_type.size());
643 for (
unsigned int i = 0; i != size; ++i)
646 adjoint_residual_estimator->
dual_error_estimator()->error_norm.set_type(i, dual_error_norm_type[i]);
651 libmesh_assert_equal_to (size, term_weights.size());
652 for (
unsigned int i = 0; i != size; ++i)
654 libmesh_assert_equal_to (size, term_weights[i].size());
656 for (
unsigned int j = 0; j != size; ++j)
661 return std::unique_ptr<ErrorEstimator>(adjoint_residual_estimator);
666 std::unique_ptr<ErrorEstimator>
667 build_weighted_error_estimator_component_wise (
FEMParameters & param,
668 std::vector<std::vector<Real>> & term_weights,
669 std::vector<FEMNormType> & primal_error_norm_type,
670 std::vector<FEMNormType> & dual_error_norm_type,
693 std::size_t size = primal_error_norm_type.size();
698 for (
unsigned int i = 0; i != size; ++i)
702 adjoint_residual_estimator->
dual_error_estimator()->error_norm.set_type(i, dual_error_norm_type[i]);
707 libmesh_assert_equal_to (size, term_weights.size());
708 for (
unsigned int i = 0; i != size; ++i)
710 libmesh_assert_equal_to (size, term_weights[i].size());
712 for (
unsigned int j = 0; j != size; ++j)
717 return std::unique_ptr<ErrorEstimator>(adjoint_residual_estimator);
721 int main (
int argc,
char ** argv)
727 #ifndef LIBMESH_ENABLE_AMR
728 libmesh_example_requires(
false,
"--enable-amr");
732 #ifndef LIBMESH_ENABLE_DIRICHLET
733 libmesh_example_requires(
false,
"--enable-dirichlet");
743 std::ifstream i(
"general.in");
745 libmesh_error_msg(
'[' <<
init.comm().rank() <<
"] Can't find general.in; exiting early.");
748 GetPot infile(
"general.in");
755 libmesh_example_requires(2 <= LIBMESH_DIM,
"2D support");
762 std::unique_ptr<MeshRefinement> mesh_refinement =
789 equation_systems.init ();
793 equation_systems.print_info();
795 libMesh::out <<
"Starting adaptive loop" << std::endl << std::endl;
798 unsigned int a_step = 0;
812 libMesh::out<<
"We cant refine to both a non-zero tolerance and a target number of elements, EXITING adaptive loop. "<<std::endl<<std::endl;
819 libMesh::out <<
"Adaptive step " << a_step << std::endl;
821 libMesh::out <<
"Solving the forward problem" << std::endl;
825 <<
" active elements and "
826 << equation_systems.n_active_dofs()
835 write_output(equation_systems, 0, a_step,
"primal", param);
844 Number QoI_0_computed = (dynamic_cast<CoupledSystem &>(system)).get_QoI_value();
847 << std::setprecision(17)
854 libmesh_assert_less(
std::abs(QoI_0_computed - 0.0833), 2.5e-4);
871 libMesh::out<<
"Solving the adjoint problem" <<std::endl;
880 primal_solution.
swap(dual_solution);
882 write_output(equation_systems, 0, a_step,
"adjoint", param);
885 primal_solution.
swap(dual_solution);
889 Real Pe = (dynamic_cast<CoupledSystem &>(system)).get_Pe();
903 std::vector<FEMNormType> primal_norm_type_vector_non_pressure;
904 primal_norm_type_vector_non_pressure.push_back(
H1_SEMINORM);
905 primal_norm_type_vector_non_pressure.push_back(
H1_SEMINORM);
906 primal_norm_type_vector_non_pressure.push_back(
L2);
907 primal_norm_type_vector_non_pressure.push_back(
H1_SEMINORM);
909 std::vector<FEMNormType> dual_norm_type_vector_non_pressure;
910 dual_norm_type_vector_non_pressure.push_back(
H1_SEMINORM);
911 dual_norm_type_vector_non_pressure.push_back(
H1_SEMINORM);
912 dual_norm_type_vector_non_pressure.push_back(
L2);
913 dual_norm_type_vector_non_pressure.push_back(
H1_SEMINORM);
915 std::vector<std::vector<Real>>
916 weights_matrix_non_pressure(system.
n_vars(),
917 std::vector<Real>(system.
n_vars(), 0.0));
918 weights_matrix_non_pressure[0][0] = 1.;
919 weights_matrix_non_pressure[1][1] = 1.;
920 weights_matrix_non_pressure[3][3] = 1./Pe;
924 std::unique_ptr<ErrorEstimator> error_estimator_non_pressure =
925 build_error_estimator_component_wise (param,
926 weights_matrix_non_pressure,
927 primal_norm_type_vector_non_pressure,
928 dual_norm_type_vector_non_pressure);
932 error_estimator_non_pressure->estimate_error(system, error_non_pressure);
935 write_error(equation_systems, error_non_pressure, 0, a_step, param,
"_non_pressure");
943 std::vector<FEMNormType> primal_norm_type_vector_with_pressure;
944 primal_norm_type_vector_with_pressure.push_back(
H1_X_SEMINORM);
945 primal_norm_type_vector_with_pressure.push_back(
H1_Y_SEMINORM);
946 primal_norm_type_vector_with_pressure.push_back(
L2);
947 primal_norm_type_vector_with_pressure.push_back(
L2);
949 std::vector<FEMNormType> dual_norm_type_vector_with_pressure;
950 dual_norm_type_vector_with_pressure.push_back(
H1_X_SEMINORM);
951 dual_norm_type_vector_with_pressure.push_back(
H1_Y_SEMINORM);
952 dual_norm_type_vector_with_pressure.push_back(
L2);
953 dual_norm_type_vector_with_pressure.push_back(
L2);
955 std::vector<std::vector<Real>>
956 weights_matrix_with_pressure (system.
n_vars(),
957 std::vector<Real>(system.
n_vars(), 0.0));
958 weights_matrix_with_pressure[0][2] = 1.;
959 weights_matrix_with_pressure[1][2] = 1.;
960 weights_matrix_with_pressure[2][0] = 1.;
961 weights_matrix_with_pressure[2][1] = 1.;
965 std::unique_ptr<ErrorEstimator> error_estimator_with_pressure =
966 build_error_estimator_component_wise (param,
967 weights_matrix_with_pressure,
968 primal_norm_type_vector_with_pressure,
969 dual_norm_type_vector_with_pressure);
972 error_estimator_with_pressure->estimate_error(system, error_with_pressure);
975 write_error(equation_systems, error_with_pressure, 0, a_step, param,
"_with_pressure");
982 std::vector<FEMNormType> primal_norm_type_vector_convection_diffusion_x;
983 primal_norm_type_vector_convection_diffusion_x.push_back(
L2);
984 primal_norm_type_vector_convection_diffusion_x.push_back(
L2);
985 primal_norm_type_vector_convection_diffusion_x.push_back(
L2);
986 primal_norm_type_vector_convection_diffusion_x.push_back(
H1_X_SEMINORM);
988 std::vector<FEMNormType> dual_norm_type_vector_convection_diffusion_x;
989 dual_norm_type_vector_convection_diffusion_x.push_back(
L2);
990 dual_norm_type_vector_convection_diffusion_x.push_back(
L2);
991 dual_norm_type_vector_convection_diffusion_x.push_back(
L2);
993 dual_norm_type_vector_convection_diffusion_x.push_back(
L2);
995 std::vector<std::vector<Real>>
996 weights_matrix_convection_diffusion_x (system.
n_vars(),
997 std::vector<Real>(system.
n_vars(), 0.0));
998 weights_matrix_convection_diffusion_x[0][3] = 1.;
999 weights_matrix_convection_diffusion_x[3][3] = 1.;
1014 std::vector<FEMFunctionBase<Number> *> coupled_system_weight_functions_x;
1015 coupled_system_weight_functions_x.push_back(&convdiffx0);
1016 coupled_system_weight_functions_x.push_back(&identity);
1017 coupled_system_weight_functions_x.push_back(&identity);
1018 coupled_system_weight_functions_x.push_back(&convdiffx3);
1022 std::unique_ptr<ErrorEstimator> error_estimator_convection_diffusion_x =
1023 build_weighted_error_estimator_component_wise (param,
1024 weights_matrix_convection_diffusion_x,
1025 primal_norm_type_vector_convection_diffusion_x,
1026 dual_norm_type_vector_convection_diffusion_x,
1027 coupled_system_weight_functions_x);
1031 error_estimator_convection_diffusion_x->estimate_error(system, error_convection_diffusion_x);
1035 error_convection_diffusion_x,
1039 "_convection_diffusion_x");
1045 std::vector<FEMNormType> primal_norm_type_vector_convection_diffusion_y;
1046 primal_norm_type_vector_convection_diffusion_y.push_back(
L2);
1047 primal_norm_type_vector_convection_diffusion_y.push_back(
L2);
1048 primal_norm_type_vector_convection_diffusion_y.push_back(
L2);
1049 primal_norm_type_vector_convection_diffusion_y.push_back(
H1_Y_SEMINORM);
1051 std::vector<FEMNormType> dual_norm_type_vector_convection_diffusion_y;
1052 dual_norm_type_vector_convection_diffusion_y.push_back(
L2);
1053 dual_norm_type_vector_convection_diffusion_y.push_back(
L2);
1054 dual_norm_type_vector_convection_diffusion_y.push_back(
L2);
1056 dual_norm_type_vector_convection_diffusion_y.push_back(
L2);
1058 std::vector<std::vector<Real>>
1059 weights_matrix_convection_diffusion_y (system.
n_vars(),
1060 std::vector<Real>(system.
n_vars(), 0.0));
1061 weights_matrix_convection_diffusion_y[1][3] = 1.;
1062 weights_matrix_convection_diffusion_y[3][3] = 1.;
1070 std::vector<FEMFunctionBase<Number> *> coupled_system_weight_functions_y;
1071 coupled_system_weight_functions_y.push_back(&identity);
1072 coupled_system_weight_functions_y.push_back(&convdiffy1);
1073 coupled_system_weight_functions_y.push_back(&identity);
1074 coupled_system_weight_functions_y.push_back(&convdiffy3);
1078 std::unique_ptr<ErrorEstimator> error_estimator_convection_diffusion_y =
1079 build_weighted_error_estimator_component_wise (param,
1080 weights_matrix_convection_diffusion_y,
1081 primal_norm_type_vector_convection_diffusion_y,
1082 dual_norm_type_vector_convection_diffusion_y,
1083 coupled_system_weight_functions_y);
1087 error_estimator_convection_diffusion_y->estimate_error(system, error_convection_diffusion_y);
1090 write_error(equation_systems, error_convection_diffusion_y, 0, a_step, param,
"_convection_diffusion_y");
1094 error.resize(error_non_pressure.size());
1098 for (std::size_t i = 0; i < error.size(); i++)
1099 error[i] = error_non_pressure[i] + error_with_pressure[i] + error_convection_diffusion_x[i] + error_convection_diffusion_y[i];
1109 error_estimator->estimate_error(system, error);
1112 write_error(equation_systems, error, 0, a_step, param,
"_total");
1123 mesh_refinement->uniformly_refine(1);
1127 mesh_refinement->flag_elements_by_error_tolerance (error);
1130 mesh_refinement->refine_and_coarsen_elements();
1138 libMesh::out <<
"We reached the target number of elements." << std::endl <<std::endl;
1142 mesh_refinement->flag_elements_by_nelem_target (error);
1145 mesh_refinement->refine_and_coarsen_elements();
1148 equation_systems.reinit();
1154 #endif // #ifndef LIBMESH_ENABLE_AMR