Stationary Solvers
This section describes how to solve stationary (time-independent) PDEs using the high-level API provided by this package. Both monolithic (single system) and block-iterative (subproblem) approaches are supported. For time-dependent problems, there is an extra section.
Meshes and FESpaces
To solve a ProblemDescription
, you must provide discretization information:
Mesh: The computational domain, represented as an
ExtendableGrid
. See ExtendableGrids.jl for details and grid constructors. For simplex grids, see SimplexGridFactory.jl. Gmsh mesh import is also supported.Finite Element Spaces: For each unknown, specify a finite element space (FESpace) that defines the ansatz functions. Construct with:
julia FESpace{FEType}(grid::ExtendableGrid)
whereFEType
is the finite element type. See the list of available FETypes in the ExtendableFEMBase.jl documentation.
Monolithic Solve
To solve a problem, call solve
with a ProblemDescription
and an array of FESpaces (one per unknown). The solver automatically detects whether the problem is linear or nonlinear and chooses the appropriate algorithm (direct solve or fixed-point iteration/Newton's method). The nonlinear residual is reduced to the prescribed tolerance.
CommonSolve.solve
— Functionsolve(
PD::ProblemDescription,
FES::Dict{<:Unknown};
...
) -> Any
solve(
PD::ProblemDescription,
FES::Dict{<:Unknown},
SC;
unknowns,
kwargs...
) -> Any
Solve a PDE problem described by a ProblemDescription
using the provided finite element spaces and solver configuration.
Arguments
PD::ProblemDescription
: The problem description, including operators, unknowns, and boundary conditions.FES::Union{<:FESpace, Vector{<:FESpace}, Dict{<:Unknown}}
: The finite element space(s) for discretizing the unknowns. Can be a single space, a vector of spaces (one per unknown), or a dictionary mapping unknowns to spaces.SC
: (optional) Solver configuration. If not provided, a new configuration is created.unknowns
: (optional) Vector of unknowns to solve for (default:PD.unknowns
).kwargs...
: Additional keyword arguments for solver configuration and algorithmic options (see below).
Keyword Arguments
abstol
: abstol for linear solver (if iterative). Default: 1.0e-11check_matrix
: check matrix for symmetry and positive definiteness and largest/smallest eigenvalues. Default: falseconstant_matrix
: matrix is constant (skips reassembly and refactorization in solver). Default: falseconstant_rhs
: right-hand side is constant (skips reassembly). Default: falsedamping
: amount of damping, value should be between in (0,1). Default: 0inactive
: inactive unknowns (are made available in assembly, but not updated in solve). Default: ExtendableFEM.Unknown[]init
: initial solution (also used to save the new solution). Default: nothinginitialized
: linear system in solver configuration is already assembled (turns true after first solve). Default: falseis_linear
: linear problem (avoid reassembly of nonlinear operators to check residual). Default: ''auto''maxiterations
: maximal number of nonlinear iterations/linear solves. Default: 10method_linear
: any solver or custom LinearSolveFunction compatible with LinearSolve.jl (default = UMFPACKFactorization()). Default: LinearSolve.UMFPACKFactorization(true, true)plot
: plot all solved unknowns with a (very rough but fast) unicode plot. Default: falseprecon_linear
: function that computes preconditioner for method_linear in case an iterative solver is chosen. Default: nothingreltol
: reltol for linear solver (if iterative). Default: 1.0e-11restrict_dofs
: array of dofs for each unknown that should be solved (default: all dofs). Default: Any[]return_config
: solver returns solver configuration (including A and b of last iteration). Default: falseshow_config
: show configuration at the beginning of solve. Default: falseshow_matrix
: show system matrix after assembly. Default: falsespy
: show unicode spy plot of system matrix during solve. Default: falsesymmetrize
: make system matrix symmetric (replace by (A+A')/2). Default: falsesymmetrize_structure
: make the system sparse matrix structurally symmetric (e.g. if [j,k] is also [k,j] must be set, all diagonal entries must be set). Default: falsetarget_residual
: stop if the absolute (nonlinear) residual is smaller than this number. Default: 1.0e-10time
: current time to be used in all time-dependent operators. Default: 0.0timeroutputs
: configures show of timeroutputs (choose between :hide, :full, :compact). Default: fullverbosity
: verbosity level. Default: 0
Returns
- The solution as an
FEVector
(or a tuple(sol, SC)
ifreturn_config=true
).
Notes
- The function automatically detects and handles linear and nonlinear problems depending on the operator definitions and runs a fixed-point iteration if necessary.
- See the
iterate_until_stationarity
function for non-monolithic problems. - This method extends the
CommonSolve.solve
interface, whereProblemDescription
acts as the problem type andFES
as the solver type.
ExtendableFEM.residual
— Functionresidual(S::SolverConfiguration)
returns the residual of the last solve
The type of fixed-point algorithm depends on how nonlinearities are assembled. If all are assembled as NonlinearOperator
, a Newton scheme is used (customizable via keyword arguments like damping
). If nonlinearities are linearized by LinearOperator
and BilinearOperator
, other fixed-point iterations are used.
Block-Iterative Solve (Subproblem Iteration)
For problems that can be solved by iterating over subproblems, configure each subproblem separately with a ProblemDescription
/SolverConfiguration
. This allows different tolerances and keyword arguments for each subproblem.
Construct a SolverConfiguration
with:
ExtendableFEM.SolverConfiguration
— TypeSolverConfiguration(
Problem::ProblemDescription;
init,
unknowns,
kwargs...
)
Construct a SolverConfiguration
for a given problem and set of finite element spaces.
A SolverConfiguration
bundles all data and options needed to assemble and solve a finite element system for a given ProblemDescription
. It stores the system matrix, right-hand side, solution vector, solver parameters, and bookkeeping for unknowns and degrees of freedom.
Arguments
Problem::ProblemDescription
: The problem to be solved, including operators, unknowns, and boundary conditions.FES::Union{<:FESpace, Vector{<:FESpace}}
: The finite element space(s) for the unknowns. Can be a single space or a vector of spaces (one per unknown).unknowns::Vector{Unknown}
: (optional) The unknowns to be solved for (default:Problem.unknowns
).init
: (optional) InitialFEVector
for the solution. If provided, the finite element spaces are inferred from it.kwargs...
: Additional keyword arguments to set solver parameters (see below).
Keyword Arguments
abstol
: abstol for linear solver (if iterative). Default: 1.0e-11check_matrix
: check matrix for symmetry and positive definiteness and largest/smallest eigenvalues. Default: falseconstant_matrix
: matrix is constant (skips reassembly and refactorization in solver). Default: falseconstant_rhs
: right-hand side is constant (skips reassembly). Default: falsedamping
: amount of damping, value should be between in (0,1). Default: 0inactive
: inactive unknowns (are made available in assembly, but not updated in solve). Default: ExtendableFEM.Unknown[]init
: initial solution (also used to save the new solution). Default: nothinginitialized
: linear system in solver configuration is already assembled (turns true after first solve). Default: falseis_linear
: linear problem (avoid reassembly of nonlinear operators to check residual). Default: ''auto''maxiterations
: maximal number of nonlinear iterations/linear solves. Default: 10method_linear
: any solver or custom LinearSolveFunction compatible with LinearSolve.jl (default = UMFPACKFactorization()). Default: LinearSolve.UMFPACKFactorization(true, true)plot
: plot all solved unknowns with a (very rough but fast) unicode plot. Default: falseprecon_linear
: function that computes preconditioner for method_linear in case an iterative solver is chosen. Default: nothingreltol
: reltol for linear solver (if iterative). Default: 1.0e-11restrict_dofs
: array of dofs for each unknown that should be solved (default: all dofs). Default: Any[]return_config
: solver returns solver configuration (including A and b of last iteration). Default: falseshow_config
: show configuration at the beginning of solve. Default: falseshow_matrix
: show system matrix after assembly. Default: falsespy
: show unicode spy plot of system matrix during solve. Default: falsesymmetrize
: make system matrix symmetric (replace by (A+A')/2). Default: falsesymmetrize_structure
: make the system sparse matrix structurally symmetric (e.g. if [j,k] is also [k,j] must be set, all diagonal entries must be set). Default: falsetarget_residual
: stop if the absolute (nonlinear) residual is smaller than this number. Default: 1.0e-10time
: current time to be used in all time-dependent operators. Default: 0.0timeroutputs
: configures show of timeroutputs (choose between :hide, :full, :compact). Default: fullverbosity
: verbosity level. Default: 0
Returns
- A
SolverConfiguration
instance, ready to be passed to thesolve
function.
Notes
- If
init
is provided, the finite element spaces are inferred from it and the solution vector is initialized accordingly. - The constructor checks that the number of unknowns matches the number of finite element spaces and that all unknowns are present in the problem description.
- The configuration includes storage for the system matrix, right-hand side, solution, temporary solution, residual, and solver statistics.
Trigger the fixed-point iteration over subproblems with:
ExtendableFEM.iterate_until_stationarity
— Functioniterate_until_stationarity(
SCs::Vector{<:SolverConfiguration};
...
)
iterate_until_stationarity(
SCs::Vector{<:SolverConfiguration},
FES;
maxsteps,
energy_integrator,
init,
unknowns,
kwargs...
) -> Tuple{FEVector{Float64, _A, _B, Vector{Float64}} where {_A, _B}, Int64}
Iteratively solve coupled problems (i.e. an array of SolverConfigurations/ProblemDescriptions with intersecting unknowns) by iterating between them. Iteration continues until the residuals of all subproblems fall below their specified tolerances, or until maxsteps
is reached.
Arguments
SCs::Vector{<:SolverConfiguration}
: Array of solver configurations, one for each subproblem. Each must contain its ownProblemDescription
.FES
: (optional) Nested vector of finite element spaces for all subproblems and unknowns. If not provided, must be inferred frominit
.maxsteps::Int
: Maximum number of outer iterations (default: 1000).energy_integrator
: (optional) Function or object to evaluate an energy or error after each iteration (for diagnostics).init
: (optional) InitialFEVector
containing all unknowns for all subproblems. Required ifFES
is not provided.unknowns
: (optional) List of unknowns for each subproblem (default:[SC.PD.unknowns for SC in SCs]
).kwargs...
: Additional keyword arguments passed to each subproblem's solver.
Returns
sol
: The final solution vector containing all unknowns.it
: The number of outer iterations performed.
Notes
- Each subproblem is solved in sequence within each outer iteration, using its own configuration and options.´
- If
energy_integrator
is provided, its value is printed after each iteration for monitoring convergence. - This function is intended for non-monolithic (partitioned) solution strategies; for monolithic problems with a single ProblemDescription, see
solve
.