solver.hpp serif/utils/serialize/model.hpp serif/utils/serialize/numerics.hpp serif/solver/nonlinear/result.hpp src/include/serif/utils/serialize/serialize.hpp serif::utils::serialize::Serializer< solver::linear::Status > serif::utils::serialize::Serializer< solver::SolveStatus > serif::utils::serialize::Serializer< solver::MetricEvaluation > serif::utils::serialize::Serializer< solver::linear::Report > serif::utils::serialize::Serializer< geometry::deformation::GeometryStepLimit > serif::utils::serialize::Serializer< solver::SolveDiagnostics > serif::utils::serialize::Serializer< solver::NewtonProgress > serif::utils::serialize::Serializer< solver::NewtonCheckpoint< State > > serif::utils::serialize::Serializer< solver::SolveResult< State, System, Model > > serif serif::utils serif::utils::serialize #pragmaonce #include"serif/utils/serialize/model.hpp" #include"serif/utils/serialize/numerics.hpp" #include"serif/solver/nonlinear/result.hpp" namespaceserif::utils::serialize{ template<> structSerializer<solver::linear::Status>:EnumSerializer<solver::linear::Status>{ staticconstexprstd::string_viewkey="linear_status"; staticconstexprautochoices=std::array{ std::pair{solver::linear::Status::converged,std::string_view{"converged"}}, std::pair{solver::linear::Status::maximum_iterations,std::string_view{"maximum_iterations"}}, std::pair{solver::linear::Status::breakdown,std::string_view{"breakdown"}}, std::pair{solver::linear::Status::non_finite,std::string_view{"non_finite"}}, std::pair{solver::linear::Status::backend_failure,std::string_view{"backend_failure"}}}; }; template<> structSerializer<solver::SolveStatus>:EnumSerializer<solver::SolveStatus>{ staticconstexprstd::string_viewkey="solve_status"; staticconstexprautochoices=std::array{ std::pair{solver::SolveStatus::converged,std::string_view{"converged"}}, std::pair{solver::SolveStatus::initial_state_rejected,std::string_view{"initial_state_rejected"}}, std::pair{solver::SolveStatus::invalid_metric,std::string_view{"invalid_metric"}}, std::pair{solver::SolveStatus::preparation_failure,std::string_view{"preparation_failure"}}, std::pair{solver::SolveStatus::linear_solve_failure,std::string_view{"linear_solve_failure"}}, std::pair{solver::SolveStatus::globalization_failure,std::string_view{"globalization_failure"}}, std::pair{solver::SolveStatus::maximum_iterations,std::string_view{"maximum_iterations"}}, std::pair{solver::SolveStatus::stopped,std::string_view{"stopped"}}}; }; template<> structSerializer<solver::MetricEvaluation>:StructSerializer<solver::MetricEvaluation>{ usingT=solver::MetricEvaluation; staticconstexprstd::string_viewkey="newton_metric"; staticconstexprautomembers=std::tuple{ member_field("residual_norm",&T::residual_norm),member_field("merit",&T::merit)}; }; template<> structSerializer<solver::linear::Report>:StructSerializer<solver::linear::Report>{ usingT=solver::linear::Report; staticconstexprstd::string_viewkey="linear_report"; staticconstexprautomembers=std::tuple{ member_field("status",&T::status),member_field("control",&T::control),member_field("iterations",&T::iterations),member_field("restarts",&T::restarts), member_field("right_hand_side_norm",&T::right_hand_side_norm),member_field("initial_residual_norm",&T::initial_residual_norm), member_field("reported_residual_norm",&T::reported_residual_norm),member_field("true_residual_norm",&T::true_residual_norm), member_field("relative_true_residual_norm",&T::relative_true_residual_norm),member_field("operator_applications",&T::operator_applications), member_field("preconditioner_applications",&T::preconditioner_applications),member_field("solve_seconds",&T::solve_seconds), member_field("operator_seconds",&T::operator_seconds),member_field("preconditioner_seconds",&T::preconditioner_seconds)}; }; template<> structSerializer<geometry::deformation::GeometryStepLimit>:StructSerializer<geometry::deformation::GeometryStepLimit>{ usingT=geometry::deformation::GeometryStepLimit; staticconstexprstd::string_viewkey="geometry_step_limit"; staticconstexprautomembers=std::tuple{ member_field("step",&T::step),member_field("boundary_step",&T::boundary_step), member_field("minimum_determinant_at_accepted",&T::minimum_determinant_at_accepted), member_field("minimum_determinant_at_maximum",&T::minimum_determinant_at_maximum), member_field("limiting_point_determinant_at_step",&T::limiting_point_determinant_at_step), member_field("sampled_point_count",&T::sampled_point_count),member_field("limited_by_geometry",&T::limited_by_geometry), member_field("limiting_element",&T::limiting_element),member_field("limiting_rule",&T::limiting_rule),member_field("limiting_point",&T::limiting_point)}; }; template<> structSerializer<solver::SolveDiagnostics>:StructSerializer<solver::SolveDiagnostics>{ usingT=solver::SolveDiagnostics; staticconstexprstd::string_viewkey="solve_diagnostics"; staticconstexprautomembers=std::tuple{ member_field("attempted_iterations",&T::attempted_iterations), member_field("accepted_iterations",&T::accepted_iterations),member_field("line_search_trials",&T::line_search_trials), member_field("rejected_trials",&T::rejected_trials),member_field("geometry_limited_iterations",&T::geometry_limited_iterations), member_field("total_linear_iterations",&T::total_linear_iterations),member_field("initial_residual_norm",&T::initial_residual_norm), member_field("final_residual_norm",&T::final_residual_norm),member_field("convergence_threshold",&T::convergence_threshold), member_field("last_linear_solve",&T::last_linear_solve),member_field("last_geometry_preflight",&T::last_geometry_preflight), member_field("last_accepted_step",&T::last_accepted_step)}; staticNodesave(constT&diagnostics){ Noderesult=StructSerializer<T>::save(diagnostics); result.children.emplace("solve_seconds",encode(0.0)); result.children.emplace("linear_solve_seconds",encode(0.0)); returnresult; } }; template<> structSerializer<solver::NewtonProgress>:StructSerializer<solver::NewtonProgress>{ usingT=solver::NewtonProgress; staticconstexprstd::string_viewkey="newton_progress"; staticconstexprautomembers=std::tuple{ member_field("accepted_metric",&T::accepted_metric),member_field("correction",&T::correction),member_field("next_step",&T::next_step), member_field("diagnostics",&T::diagnostics)}; }; template<typenameState> structSerializer<solver::NewtonCheckpoint<State>>{ staticconstexprstd::string_viewkey="checkpoint"; staticNodesave(constsolver::NewtonCheckpoint<State>&checkpoint){ returnobject("newton_checkpoint",field("strategy",std::string_view{"standard_newton"}), field("state",checkpoint.state),field("progress",checkpoint.progress)); } staticResult<solver::NewtonCheckpoint<State>>load(constNode&node){ constautostrategy=read_field<std::string>(node,"strategy"); if(!strategy){ returnstd::unexpected(strategy.error()); } if(*strategy!="standard_newton"){ returnstd::unexpected(Error{"strategy","Thischeckpointrequiresunsupportednumericalstrategyhistory."}); } autoresult=read_object(node,"newton_checkpoint",[](Statestate,solver::NewtonProgressprogress){ returnsolver::NewtonCheckpoint<State>{.state=std::move(state),.progress=std::move(progress)}; },member<State>("state"),member<solver::NewtonProgress>("progress")); if(result){ if(constautoerror=solver::validate_newton_progress(result->progress,result->state.values().size())){ returnstd::unexpected(Error{"progress",*error}); } } returnresult; } }; template<typenameState,typenameSystem,typenameModel> structSerializer<solver::SolveResult<State,System,Model>>{ staticconstexprstd::string_viewkey="solution"; staticNodesave(constsolver::SolveResult<State, System, Model>&result){ Nodenode=object("solve_result",field("status",result.status()),field("message",result.message()), field("diagnostics",result.diagnostics()),field("has_state",result.has_state())); ifconstexpr(!std::same_as<Model,solver::NoModel>){ node.children.emplace("model",encode(result.model())); } if(result.has_state()){ node.children.emplace("state",encode(result.state())); } if(result.has_checkpoint()){ node.children.emplace("checkpoint",encode(result.checkpoint())); } ifconstexpr(requires{result.system()->reference_scales();result.system()->coordinates();}){ if(result.system()){ node.children.emplace("reference_scales",encode(result.system()->reference_scales())); node.children.emplace("coordinates",encode(result.system()->coordinates())); } } returnnode; } staticResult<solver::SolveResult<State, System, Model>>load(constNode&){ returnstd::unexpected(Error{"","Asavedsolutioncontainsscientificdata,notexecutableoperators.Readitsmodel/stateorcheckpointcomponentsandrebuildtheruntimesystemwithresume_equilibrium."}); } }; }