Source code for firedrake.mg.adaptive_transfer_manager

"""
This module contains the AdaptiveTransferManager used to perform
transfer operations on AdaptiveMeshHierarchies
"""
from firedrake.mg.embedded import TransferManager
from firedrake.ufl_expr import action, TrialFunction
from firedrake.interpolation import interpolate


__all__ = ("AdaptiveTransferManager",)


[docs] class AdaptiveTransferManager(TransferManager): """ TransferManager for adaptively refined mesh hierarchies """ def __init__(self, *, native_transfers=None, use_averaging=True): if native_transfers is not None: raise NotImplementedError("Custom transfers not implemented.") super().__init__(native_transfers=native_transfers, use_averaging=use_averaging) self.cache = {}
[docs] def get_interpolator(self, Vc, Vf): from firedrake.assemble import assemble key = (Vc, Vf) try: return self.cache[key] except KeyError: Iexpr = interpolate(TrialFunction(Vc), Vf) # TODO reusable matfree Interpolator I = assemble(Iexpr, mat_type="aij") return self.cache.setdefault(key, I)
[docs] def forward(self, uc, uf): from firedrake.assemble import assemble Vc = uc.function_space() Vf = uf.function_space() I = self.get_interpolator(Vc, Vf) return assemble(action(I, uc), tensor=uf)
[docs] def adjoint(self, uf, uc): from firedrake.assemble import assemble Vc = uc.function_space().dual() Vf = uf.function_space().dual() I = self.get_interpolator(Vc, Vf) return assemble(action(uf, I), tensor=uc)
[docs] def prolong(self, uf, uc): return self.forward(uf, uc)
[docs] def inject(self, uc, uf): return self.forward(uc, uf)
[docs] def restrict(self, uc, uf): return self.adjoint(uc, uf)