Note
Go to the end to download the full example code.
2.4.8 Solver comparison
This example shows how to set up solvers explicitly and how to extract diagnostic information.
Diagnostic information from first run:
{'controller': {'mpi_run': False, 't_start': 0, 't_end': 1.0, 'profiler': {'solver': 0.011511110000000713, 'tracker': 4.8149999997804116e-05, 'compilation': 4.375287499000002}, 'jit_count': {'make_stepper': 10, 'simulation': 0}, 'solver_start': '2024-12-02 18:42:24.299644', 'successful': True, 'stop_reason': 'Reached final time', 'solver_duration': '0:00:00.011555', 't_final': 1.0}, 'package_version': 'unknown', 'solver': {'class': 'ExplicitSolver', 'pde_class': 'DiffusionPDE', 'scheme': 'euler', 'backend': 'numba', 'dt': 0.001, 'steps': 1000, 'post_step_data': None, 'stochastic': np.False_}}
Diagnostic information from second run:
{'controller': {'mpi_run': False, 't_start': 0, 't_end': 1.0, 'profiler': {'solver': 0.13954576199999735, 'tracker': 4.681100000425431e-05, 'compilation': 1.1197609419999992}, 'jit_count': {'make_stepper': 1, 'simulation': 0}, 'solver_start': '2024-12-02 18:42:25.431630', 'successful': True, 'stop_reason': 'Reached final time', 'solver_duration': '0:00:00.139600', 't_final': np.float64(1.0)}, 'package_version': 'unknown', 'solver': {'class': 'ExplicitSolver', 'pde_class': 'DiffusionPDE', 'dt_statistics': {'min': 0.001, 'max': 0.16857283231251302, 'mean': 0.08333333333333333, 'std': 0.051719779502089516, 'count': 12.0}, 'scheme': 'runge-kutta', 'backend': 'numba', 'dt': 0.001, 'dt_adaptive': True, 'steps': 12, 'stochastic': np.False_, 'post_step_data': None}}
Diagnostic information from third run:
{'controller': {'mpi_run': False, 't_start': 0, 't_end': 1.0, 'profiler': {'solver': 0.0035646819999968216, 'tracker': 4.4733000002850076e-05, 'compilation': 0.6370209379999991}, 'jit_count': {'make_stepper': 1, 'simulation': 0}, 'solver_start': '2024-12-02 18:42:27.751894', 'successful': True, 'stop_reason': 'Reached final time', 'solver_duration': '0:00:00.003605', 't_final': np.float64(1.0)}, 'package_version': 'unknown', 'solver': {'class': 'ScipySolver', 'pde_class': 'DiffusionPDE', 'dt': None, 'steps': 56, 'stochastic': False, 'backend': 'numba'}}
import pde
# initialize the grid, an initial condition, and the PDE
grid = pde.UnitGrid([32, 32])
field = pde.ScalarField.random_uniform(grid, -1, 1)
eq = pde.DiffusionPDE()
# try the explicit solver
solver1 = pde.ExplicitSolver(eq)
controller1 = pde.Controller(solver1, t_range=1, tracker=None)
sol1 = controller1.run(field, dt=1e-3)
sol1.label = "explicit solver"
print("Diagnostic information from first run:")
print(controller1.diagnostics)
print()
# try an explicit solver with adaptive time steps
solver2 = pde.ExplicitSolver(eq, scheme="runge-kutta", adaptive=True)
controller2 = pde.Controller(solver2, t_range=1, tracker=None)
sol2 = controller2.run(field, dt=1e-3)
sol2.label = "explicit, adaptive solver"
print("Diagnostic information from second run:")
print(controller2.diagnostics)
print()
# try the standard scipy solver
solver3 = pde.ScipySolver(eq)
controller3 = pde.Controller(solver3, t_range=1, tracker=None)
sol3 = controller3.run(field)
sol3.label = "scipy solver"
print("Diagnostic information from third run:")
print(controller3.diagnostics)
print()
# plot both fields and give the deviation as the title
title = f"Deviation: {((sol1 - sol2)**2).average:.2g}, {((sol1 - sol3)**2).average:.2g}"
pde.FieldCollection([sol1, sol2, sol3]).plot(title=title)
Total running time of the script: (0 minutes 8.238 seconds)