Example of solving the wave equation using finite difference and RODASP formula.
#include <exception>
#include <iostream>
#include <optional>
#include <string>
#include <string_view>
#include <vector>
#include <Eigen/Core>
#include <fmt/format.h>
#include <plotly_plotter/eigen.h>
#include <plotly_plotter/figure.h>
#include <plotly_plotter/write_html.h>
#include <plotly_plotter/write_png.h>
#include <toml++/toml.h>
template <typename T>
static auto get_config_value(
const toml::parse_result& config, std::string_view key) {
const std::optional<T> res = config.as_table()
->at("fd_rodasp_wave1d")
.as_table()
->at(key)
.value<T>();
if (!res) {
"Failed to load configuration {}.", key);
}
return res.value();
}
auto main(int argc, char** argv) -> int {
std::string_view config_filepath = "examples/pde/fd_rodasp_wave1d.toml";
if (argc == 2) {
config_filepath = argv[1];
}
std::string(config_filepath));
using solver_type =
const auto config = toml::parse_file(config_filepath);
const double speed = get_config_value<double>(config, "speed");
get_config_value<num_collect::index_type>(config, "num_points");
const double length = get_config_value<double>(config, "length");
.speed = speed, .num_points = num_points, .length = length};
problem_type problem{params};
solver_type solver{problem};
constexpr double init_time = 0.0;
solver.init(init_time, solution.
solution());
plotly_plotter::figure figure;
auto trace = figure.add_scatter();
trace.x(problem.points());
trace.y(solver.variable().tail(problem.points().size()));
trace.name(fmt::format(
"t = {:.1f}", init_time));
const auto time_list = std::vector<double>{0.2, 0.4, 0.6, 0.8, 1.0};
for (const double time : time_list) {
solver.solve_till(time);
auto trace = figure.add_scatter();
trace.x(problem.points());
trace.y(solver.variable().tail(problem.points().size()));
trace.name(fmt::format(
"t = {:.1f}", init_time));
const auto error_norm =
(solver.variable() - solution.
solution()).norm();
logger.
info()(
"Error norm at time {:.3f}: {:.3e}", time, error_norm);
}
figure.title(
"Solution of 1D wave equation using finite difference and "
"Rosenbrock method (RODASP formula)");
figure.layout().xaxis().title().text("x");
figure.layout().yaxis().title().text("Displacement");
plotly_plotter::write_html("fd_rodasp_wave1d.html", figure);
if (plotly_plotter::is_png_supported()) {
plotly_plotter::write_png("fd_rodasp_wave1d.png", figure);
}
return 0;
}
Class of exception on invalid arguments.
auto info(util::source_info_view source=util::source_info_view()) const noexcept -> logging_proxy
Write a information log.
Class of ODE problem to solve 1D wave equation of strings discretized using finite difference.
Class to calculate exact solution of string_wave_1d_problem.
void evaluate_on(double time)
Evaluate solution.
auto solution() -> const Eigen::VectorXd &
Get the solution.
Definition of exceptions.
Definition of index_type type.
Definition of load_logging_config function.
Definition of logger class.
Definition of macros for logging.
#define NUM_COLLECT_LOG_TRACE(LOGGER,...)
Write a trace log.
#define NUM_COLLECT_LOG_AND_THROW(EXCEPTION_TYPE,...)
Write an error log and throw an exception for an error.
std::ptrdiff_t index_type
Type of indices in this library.
NUM_COLLECT_EXPORT void load_logging_config_file(std::string_view filepath)
Parse and apply configurations of logging from a file.
embedded_solver< rodasp_formula< Problem > > rodasp_solver
Class of solver using RODASP formula.
Definition of string_wave_1d_problem class.
Struct of parameters in string_wave_1d_problem.