Coverage for pySDC/implementations/datatype_classes/fenics_mesh.py: 100%
42 statements
« prev ^ index » next coverage.py v7.17.0, created at 2026-11-02 12:30 +0000
« prev ^ index » next coverage.py v7.17.0, created at 2026-11-02 12:30 +0000
1import dolfin as df
3from pySDC.core.errors import DataError
4from pySDC.implementations.datatype_classes.container import MultiComponentContainer
7class fenics_mesh(object):
8 """
9 FEniCS Function data type with arbitrary dimensions
11 Attributes:
12 values (np.ndarray): contains the ndarray of the values
13 """
15 def __init__(self, init=None, val=0.0):
16 """
17 Initialization routine
19 Args:
20 init: can either be a FunctionSpace or another fenics_mesh object
21 val: initial value (default: 0.0)
22 Raises:
23 DataError: if init is none of the types above
24 """
25 # if init is another fenic_mesh, do a deepcopy (init by copy)
26 if isinstance(init, type(self)):
27 self.values = init.values.copy(deepcopy=True)
28 # if init is FunctionSpace, create mesh object with val as initial value
29 elif isinstance(init, df.Function):
30 self.values = init.copy(deepcopy=True)
31 elif isinstance(init, df.FunctionSpace):
32 self.values = df.Function(init)
33 self.values.vector()[:] = val
34 else:
35 raise DataError('something went wrong during %s initialization' % type(init))
37 def __add__(self, other):
38 """
39 Overloading the addition operator for mesh types
41 Args:
42 other (fenics_mesh): mesh object to be added
43 Raises:
44 DataError: if other is not a mesh object
45 Returns:
46 fenics_mesh: sum of caller and other values (self+other)
47 """
49 if isinstance(other, type(self)):
50 # always create new mesh, since otherwise c = a + b changes a as well!
51 me = fenics_mesh(self)
52 me += other
53 return me
54 else:
55 raise DataError("Type error: cannot add %s to %s" % (type(other), type(self)))
57 def __sub__(self, other):
58 """
59 Overloading the subtraction operator for mesh types
61 Args:
62 other (fenics_mesh): mesh object to be subtracted
63 Raises:
64 DataError: if other is not a mesh object
65 Returns:
66 fenics_mesh: differences between caller and other values (self-other)
67 """
69 if isinstance(other, type(self)):
70 # always create new mesh, since otherwise c = a - b changes a as well!
71 me = fenics_mesh(self)
72 me -= other
73 return me
74 else:
75 raise DataError("Type error: cannot subtract %s from %s" % (type(other), type(self)))
77 def __iadd__(self, other):
78 """
79 Add another mesh in place, on the vector underneath, without copying through NumPy
81 Args:
82 other (fenics_mesh): mesh object to be added
83 Raises:
84 DataError: if other is not a mesh object
85 Returns:
86 fenics_mesh: the caller, now holding self+other
87 """
89 if isinstance(other, type(self)):
90 self.values.vector().axpy(1.0, other.values.vector())
91 return self
92 else:
93 raise DataError("Type error: cannot add %s to %s" % (type(other), type(self)))
95 def __isub__(self, other):
96 """
97 Subtract another mesh in place, on the vector underneath, without copying through NumPy
99 Args:
100 other (fenics_mesh): mesh object to be subtracted
101 Raises:
102 DataError: if other is not a mesh object
103 Returns:
104 fenics_mesh: the caller, now holding self-other
105 """
107 if isinstance(other, type(self)):
108 self.values.vector().axpy(-1.0, other.values.vector())
109 return self
110 else:
111 raise DataError("Type error: cannot subtract %s from %s" % (type(other), type(self)))
113 def __rmul__(self, other):
114 """
115 Overloading the right multiply by factor operator for mesh types
117 Args:
118 other (float): factor
119 Raises:
120 DataError: if other is not a float
121 Returns:
122 fenics_mesh: copy of original values scaled by factor
123 """
125 if isinstance(other, float):
126 # always create new mesh, since otherwise c = f*a changes a as well!
127 me = fenics_mesh(self)
128 vector = me.values.vector()
129 vector *= other
130 return me
131 else:
132 raise DataError("Type error: cannot multiply %s to %s" % (type(other), type(self)))
134 def __abs__(self):
135 """
136 Overloading the abs operator for mesh types
138 Returns:
139 float: absolute maximum of all mesh values
140 """
142 # take absolute values of the mesh values
144 absval = df.norm(self.values, 'L2')
146 # return maximum
147 return absval
150class rhs_fenics_mesh(MultiComponentContainer):
151 """
152 RHS data type for fenics_meshes with implicit and explicit components
154 Attributes:
155 impl (fenics_mesh): implicit part
156 expl (fenics_mesh): explicit part
157 """
159 components = ['impl', 'expl']
160 component_type = fenics_mesh