Skip to content

Commit

Permalink
Harmonize preconditioners
Browse files Browse the repository at this point in the history
  • Loading branch information
guyer committed Nov 11, 2023
1 parent da86849 commit dd914bc
Show file tree
Hide file tree
Showing 42 changed files with 443 additions and 382 deletions.
2 changes: 1 addition & 1 deletion fipy/solvers/petsc/linearLUSolver.py
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,7 @@ def __init__(self, tolerance="default", criterion="default",
See :ref:`CONVERGENCE` for more information.
iterations : int
Maximum number of iterative steps to perform.
precon : ~fipy.solvers.petsc.preconditioners.preconditioner.Preconditioner
precon
*ignored*
"""
super(LinearLUSolver, self).__init__(tolerance=tolerance,
Expand Down
4 changes: 2 additions & 2 deletions fipy/solvers/petsc/petscKrylovSolver.py
Original file line number Diff line number Diff line change
Expand Up @@ -39,10 +39,10 @@ def __init__(self, tolerance="default",
See :ref:`CONVERGENCE` for more information.
iterations : int
Maximum number of iterative steps to perform.
precon : ~fipy.solvers.petsc.preconditioners.preconditioner.Preconditioner, optional
precon : ~fipy.solvers.petsc.preconditioners.petscPreconditioner.PETScPreconditioner, optional
Preconditioner to apply to the matrix. A value of None means
to perform an unpreconditioned solve. (default:
~fipy.solvers.petsc.preconditioners.defaultPreconditioner.DefaultPreconditioner).
:class:`~fipy.solvers.petsc.preconditioners.defaultPreconditioner.DefaultPreconditioner`).
"""
if self.__class__ is PETScKrylovSolver:
raise NotImplementedError("can't instantiate abstract base class")
Expand Down
7 changes: 3 additions & 4 deletions fipy/solvers/petsc/preconditioners/defaultPreconditioner.py
Original file line number Diff line number Diff line change
@@ -1,15 +1,14 @@
from __future__ import unicode_literals
__docformat__ = 'restructuredtext'

from .preconditioner import Preconditioner
from .petscPreconditioner import PETScPreconditioner

__all__ = ["DefaultPreconditioner"]
from future.utils import text_to_native_str
__all__ = [text_to_native_str(n) for n in __all__]

class DefaultPreconditioner(Preconditioner):
"""
Apply PETSc's default preconditioning.
class DefaultPreconditioner(PETScPreconditioner):
"""Apply PETSc's default preconditioning to :class:`~fipy.solvers.petsc.petscSolver.PETScSolver`.
"The default preconditioner for sparse matrices is PCILU or PCICC with
0 fill on one process and block Jacobi (PCBJACOBI) with PCILU or PCICC
Expand Down
8 changes: 3 additions & 5 deletions fipy/solvers/petsc/preconditioners/icPreconditioner.py
Original file line number Diff line number Diff line change
@@ -1,16 +1,14 @@
from __future__ import unicode_literals
__docformat__ = 'restructuredtext'

from .preconditioner import Preconditioner
from .petscPreconditioner import PETScPreconditioner

__all__ = ["ICPreconditioner"]
from future.utils import text_to_native_str
__all__ = [text_to_native_str(n) for n in __all__]

class ICPreconditioner(Preconditioner):
"""
Incomplete Choleski Preconditioner for PETSc solvers.
class ICPreconditioner(PETScPreconditioner):
"""Incomplete Choleski preconditioner for :class:`~fipy.solvers.petsc.petscSolver.PETScSolver`.
"""

pctype = "icc"
8 changes: 3 additions & 5 deletions fipy/solvers/petsc/preconditioners/iluPreconditioner.py
Original file line number Diff line number Diff line change
@@ -1,16 +1,14 @@
from __future__ import unicode_literals
__docformat__ = 'restructuredtext'

from .preconditioner import Preconditioner
from .petscPreconditioner import PETScPreconditioner

__all__ = ["ILUPreconditioner"]
from future.utils import text_to_native_str
__all__ = [text_to_native_str(n) for n in __all__]

class ILUPreconditioner(Preconditioner):
"""
ILU Preconditioner for PETSc solvers.
class ILUPreconditioner(PETScPreconditioner):
"""ILU preconditioner for :class:`~fipy.solvers.petsc.petscSolver.PETScSolver`.
"""

pctype = "ilu"
8 changes: 3 additions & 5 deletions fipy/solvers/petsc/preconditioners/jacobiPreconditioner.py
Original file line number Diff line number Diff line change
@@ -1,16 +1,14 @@
from __future__ import unicode_literals
__docformat__ = 'restructuredtext'

from .preconditioner import Preconditioner
from .petscPreconditioner import PETScPreconditioner

__all__ = ["JacobiPreconditioner"]
from future.utils import text_to_native_str
__all__ = [text_to_native_str(n) for n in __all__]

class JacobiPreconditioner(Preconditioner):
"""
Jacobi Preconditioner for PETSc solvers.
class JacobiPreconditioner(PETScPreconditioner):
"""Jacobi preconditioner for :class:`~fipy.solvers.petsc.petscSolver.PETScSolver`.
"""

pctype = "jacobi"
7 changes: 3 additions & 4 deletions fipy/solvers/petsc/preconditioners/luPreconditioner.py
Original file line number Diff line number Diff line change
@@ -1,15 +1,14 @@
from __future__ import unicode_literals
__docformat__ = 'restructuredtext'

from .preconditioner import Preconditioner
from .petscPreconditioner import PETScPreconditioner

__all__ = ["LUPreconditioner"]
from future.utils import text_to_native_str
__all__ = [text_to_native_str(n) for n in __all__]

class LUPreconditioner(Preconditioner):
"""
LU Preconditioner for PETSc solvers.
class LUPreconditioner(PETScPreconditioner):
"""LU preconditioner for :class:`~fipy.solvers.petsc.petscSolver.PETScSolver`.
"""

Expand Down
Original file line number Diff line number Diff line change
@@ -1,14 +1,14 @@
from __future__ import unicode_literals
from builtins import object
__docformat__ = 'restructuredtext'

__all__ = ["Preconditioner"]
from fipy.solvers.preconditioner import SolverModifyingPreconditioner

__all__ = ["PETScPreconditioner"]
from future.utils import text_to_native_str
__all__ = [text_to_native_str(n) for n in __all__]

class Preconditioner(object):
"""
The base Preconditioner class.
class PETScPreconditioner(SolverModifyingPreconditioner):
"""Base class preconditioners of for :class:`~fipy.solvers.petsc.petscSolver.PETScSolver`.
.. attention:: This class is abstract. Always create one of its subclasses.
"""
Expand Down
6 changes: 3 additions & 3 deletions fipy/solvers/petsc/preconditioners/ssorPreconditioner.py
Original file line number Diff line number Diff line change
@@ -1,15 +1,15 @@
from __future__ import unicode_literals
__docformat__ = 'restructuredtext'

from .preconditioner import Preconditioner
from .petscPreconditioner import PETScPreconditioner

__all__ = ["SSORPreconditioner"]
from future.utils import text_to_native_str
__all__ = [text_to_native_str(n) for n in __all__]

class SSORPreconditioner(Preconditioner):
class SSORPreconditioner(PETScPreconditioner):
"""
SSOR Preconditioner for PETSc solvers.
SSOR preconditioner for :class:`~fipy.solvers.petsc.petscSolver.PETScSolver`.
"""

Expand Down
57 changes: 57 additions & 0 deletions fipy/solvers/preconditioner.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,57 @@
from __future__ import unicode_literals
from builtins import object
__docformat__ = 'restructuredtext'

__all__ = ["Preconditioner",
"SolverModifyingPreconditioner",
"MatrixModifyingPreconditioner"]
from future.utils import text_to_native_str
__all__ = [text_to_native_str(n) for n in __all__]

class Preconditioner(object):
"""Base class for solver preconditioners.
.. attention:: This class is abstract. Always create one of its subclasses.
"""

pass


class SolverModifyingPreconditioner(Preconditioner):
"""Base class for preconditioners that modify a :class:`~fipy.solvers.solver.Solver`.
"""

def _applyToSolver(self, solver, matrix):
"""Modify `solver` to apply preconditioning to `matrix`.
Parameters
----------
solver
The solver to modify with preconditioner.
matrix
The matrix the preconditioner applies to.
Returns
-------
None
"""
raise NotImplementedError


class MatrixModifyingPreconditioner(Preconditioner):
"""Base class for preconditioners that modify a :class:`~fipy.matrices.sparseMatrix.SparseMatrix`.
"""

def _applyToMatrix(self, matrix):
"""Create a preconditioner for `matrix`.
Returns
-------
preconditioner : object
Preconditioning object appropriate for this solver suite.
matrix : :class:`~fipy.matrices.sparseMatrix.SparseMatrix`
Matrix, possibly restructured to facilitate applying
preconditioner.
"""
raise NotImplementedError

Original file line number Diff line number Diff line change
Expand Up @@ -3,18 +3,20 @@

from pyamg import smoothed_aggregation_solver

from ...scipy.preconditioners.preconditioner import Preconditioner
from ...scipy.preconditioners.scipyPreconditioner import ScipyPreconditioner

__all__ = ["SmoothedAggregationPreconditioner"]
from future.utils import text_to_native_str
__all__ = [text_to_native_str(n) for n in __all__]

class SmoothedAggregationPreconditioner(Preconditioner):
"""Preconditioner based on `PyAMG smoothed_aggregation_solver <https://pyamg.readthedocs.io/en/latest/generated/pyamg.aggregation.html#pyamg.aggregation.smoothed_aggregation_solver>`_
class SmoothedAggregationPreconditioner(ScipyPreconditioner):
"""Preconditioner based on `PyAMG smoothed_aggregation_solver`_ for :class:`~fipy.solvers.scipy.scipySolver.ScipySolver`.
.. _PyAMG smoothed_aggregation_solver: https://pyamg.readthedocs.io/en/latest/generated/pyamg.aggregation.html#pyamg.aggregation.smoothed_aggregation_solver
"""

def __init__(self):
pass

def _applyToMatrix(self, A):
return smoothed_aggregation_solver(A).aspreconditioner(cycle='V')
def _applyToMatrix(self, matrix):
return smoothed_aggregation_solver(matrix).aspreconditioner(cycle='V'), None
71 changes: 33 additions & 38 deletions fipy/solvers/pyamgx/preconditioners.py
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
from __future__ import unicode_literals
from builtins import object
import copy

from fipy.solvers.preconditioner import SolverModifyingPreconditioner

__all__ = ["AMGPreconditioner",
"AggregationAMGPreconditioner",
Expand All @@ -12,96 +12,91 @@
"ILUPreconditioner",
"JacobiPreconditioner",
"PolynomialPreconditioner",
"Preconditioner"]
"PyAMGXPreconditioner"]
from future.utils import text_to_native_str
__all__ = [text_to_native_str(n) for n in __all__]

class Preconditioner(object):
"""Interface to pyamgx_ `preconditioner configuration`_.
class PyAMGXPreconditioner(SolverModifyingPreconditioner):
"""Interface to pyamgx_ `preconditioner configuration`_ for :class:`~fipy.solvers.pyamgx.pyAMGXSolver.PyAMGXSolver`.
.. _pyamgx: https://pyamgx.readthedocs.io
.. _preconditioner configuration: https://pyamgx.readthedocs.io/en/latest/basic.html#config-objects
"""

def __init__(self, **kwargs):
"""
Parameters
----------
**kwargs : dict, optional
Extra arguments to preconditioner: refer to `preconditioner
configuration`_ for information about possible arguments.
"""
self.config_dict = {
"solver": self.pctype,
"max_iters": 1
}
self.config_dict.update(kwargs)

def __call__(self, **kwargs):
config_dict = self.config_dict.copy()
config_dict.update(kwargs)
return config_dict
def _applyToSolver(self, solver, matrix=None):
solver["preconditioner"] = self.config_dict.copy()

class AMGPreconditioner(Preconditioner):
class AMGPreconditioner(PyAMGXPreconditioner):
"""Adaptive Multigrid preconditioner for :class:`~fipy.solvers.pyamgx.pyAMGXSolver.PyAMGXSolver`.
"""
Adaptive Multigrid Preconditioner for pyamgx solvers.

"""
pctype = "AMG"

class AggregationAMGPreconditioner(AMGPreconditioner):
"""Aggregation Adaptive Multigrid preconditioner for :class:`~fipy.solvers.pyamgx.pyAMGXSolver.PyAMGXSolver`.
"""
Aggregation Adaptive Multigrid Preconditioner for pyamgx solvers.

"""
def __init__(self):
super(ClassicalAMGPreconditioner, self).__init__(algorithm="AGGREGATION",
selector="SIZE_2")
class BiCGStabPreconditioner(Preconditioner):
class BiCGStabPreconditioner(PyAMGXPreconditioner):
"""Biconjugate Gradient Stabilized preconditioner for :class:`~fipy.solvers.pyamgx.pyAMGXSolver.PyAMGXSolver`.
"""
Biconjugate Gradient Stabilized Preconditioner for pyamgx solvers.

"""
pctype = "PCIBCGSTAB"

class CGPreconditioner(Preconditioner):
class CGPreconditioner(PyAMGXPreconditioner):
"""Conjugate Gradient preconditioner for :class:`~fipy.solvers.pyamgx.pyAMGXSolver.PyAMGXSolver`.
"""
Conjugate Gradient Preconditioner for pyamgx solvers.

"""
pctype = "PCG"

class DILUPreconditioner(Preconditioner):
class DILUPreconditioner(PyAMGXPreconditioner):
"""DILU preconditioner for :class:`~fipy.solvers.pyamgx.pyAMGXSolver.PyAMGXSolver`.
"""
DILU Preconditioner for pyamgx solvers.

"""
pctype = "MULTICOLOR_DILU"

class FGMRESPreconditioner(Preconditioner):
class FGMRESPreconditioner(PyAMGXPreconditioner):
"""Flexible Generalized Mimumal Residual preconditioner for :class:`~fipy.solvers.pyamgx.pyAMGXSolver.PyAMGXSolver`.
"""
Flexible Generalized Mimumal Residual Preconditioner for pyamgx solvers.

"""
pctype = "FGMRES"

class GaussSeidelPreconditioner(Preconditioner):
class GaussSeidelPreconditioner(PyAMGXPreconditioner):
"""Gauss-Seidel preconditioner for :class:`~fipy.solvers.pyamgx.pyAMGXSolver.PyAMGXSolver`.
"""
Gauss-Seidel Preconditioner for pyamgx solvers.

"""
pctype = "MULTICOLOR_GS"

class ILUPreconditioner(Preconditioner):
class ILUPreconditioner(PyAMGXPreconditioner):
"""ILU preconditioner for :class:`~fipy.solvers.pyamgx.pyAMGXSolver.PyAMGXSolver`.
"""
ILU Preconditioner for pyamgx solvers.

"""
pctype = "MULTICOLOR_GS"

class JacobiPreconditioner(Preconditioner):
class JacobiPreconditioner(PyAMGXPreconditioner):
"""Block Jacobi preconditioner for :class:`~fipy.solvers.pyamgx.pyAMGXSolver.PyAMGXSolver`.
"""
Block Jacobi Preconditioner for pyamgx solvers.

"""
pctype = "BLOCK_JACOBI"

class PolynomialPreconditioner(Preconditioner):
class PolynomialPreconditioner(PyAMGXPreconditioner):
"""Polynomial preconditioner for :class:`~fipy.solvers.pyamgx.pyAMGXSolver.PyAMGXSolver`.
"""
Polynomial Preconditioner for pyamgx solvers.

"""
pctype = "POLYNOMIAL"
Loading

0 comments on commit dd914bc

Please sign in to comment.