gko::LinOpFactory#
Abstract base for factories that produce a LinOp from a
system matrix. The canonical workflow is
auto factory = gko::solver::Cg<double>::build()
.with_criteria(
gko::stop::Iteration::build().with_max_iters(100u))
.on(exec); // returns a unique_ptr<Cg<double>::Factory>
auto solver = factory->generate(system_matrix); // returns a unique_ptr<Cg<double>>
solver->apply(b, x);
with_* setters configure the factory parameters; .on(exec) ties
the factory to an executor and produces the concrete factory, which is a
LinOpFactory; finally generate(matrix) binds the factory to a concrete
system and returns the operator. Solver / preconditioner / factorisation
classes all expose this pattern through the GKO_ENABLE_LIN_OP_FACTORY macro,
which builds on the EnableDefaultLinOpFactory mixin.
-
class LinOpFactory #
Inherits from
A LinOpFactory represents a higher order mapping which transforms one linear operator into another.
In Ginkgo, every linear solver is viewed as a mapping. For example, given an s.p.d linear system $Ax = b$, the solution $x = A^{-1}b$ can be computed using the CG method. This algorithm can be represented in terms of linear operators and mappings between them as follows:
A Cg::Factory is a higher order mapping which, given an input operator $A$, returns a new linear operator $A^{-1}$ stored in “CG
format”
Storing the operator $A^{-1}$ in “CG format” means that the data structure used to store the operator is just a simple pointer to the original matrix $A$. The application $x = A^{-1}b$ of such an operator can then be implemented by solving the linear system $Ax = b$ using the CG method. This is achieved in code by having a special class for each of those “formats” (e.g. the “Cg” class defines such a format for the CG solver).
Another example of a LinOpFactory is a preconditioner. A preconditioner for a linear operator $A$ is a linear operator $M^{-1}$, which approximates $A^{-1}$. In addition, it is stored in a way such that both the data of $M^{-1}$ is cheap to compute from $A$, and the operation $x = M^{-1}b$ can be computed quickly. These operators are useful to accelerate the convergence of Krylov solvers. Thus, a preconditioner also fits into the LinOpFactory framework:
The factory maps a linear operator $A$ into a preconditioner $M^{-1}$ which is stored in suitable format (e.g. as a product of two factors in case of ILU preconditioners).
The resulting linear operator implements the application operation $x = M^{-1}b$ depending on the format the preconditioner is stored in (e.g. as two triangular solves in case of ILU)
#
Example: using CG in Ginkgo#
// Suppose A is a matrix, b a rhs vector, and x an initial guess // Create a CG which runs for at most 1000 iterations, and stops after // reducing the residual norm by 6 orders of magnitude auto cg_factory = solver::Cg<>::build() .with_max_iters(1000) .with_rel_residual_goal(1e-6) .on(cuda); // create a linear operator which represents the solver auto cg = cg_factory->generate(A); // solve the system cg->apply(b, x);
Subclassed by
gko::EnableAbstractPolymorphicObject< Cholesky< ValueType
IndexType >
LinOpFactory >
gko::EnableAbstractPolymorphicObject< Lu< ValueType
IndexType >
LinOpFactory >
gko::EnableAbstractPolymorphicObject< Amd< int32 >
LinOpFactory >
gko::EnableAbstractPolymorphicObject< Mc64< default_precision
int32 >
LinOpFactory >
gko::EnableAbstractPolymorphicObject< NestedDissection< ValueType
IndexType >
LinOpFactory >
gko::EnableAbstractPolymorphicObject< Rcm< int32 >
LinOpFactory >
gko::EnableAbstractPolymorphicObject< IdentityFactory< default_precision >
LinOpFactory >
gko::EnableAbstractPolymorphicObject< GaussSeidel< default_precision
int32 >
LinOpFactory >
gko::EnableAbstractPolymorphicObject< Sor< default_precision
int32 >
LinOpFactory >