def get_projection_basis(mesh0, mesh_refinements=None, maxh=None, degree=1, sub_spaces=None, family='CG'): if mesh_refinements is not None: mesh = mesh0 for _ in range(mesh_refinements): mesh = refine(mesh) if sub_spaces is None or sub_spaces == 0: V = FunctionSpace(mesh, family, degree) else: V = VectorFunctionSpace(mesh, family, degree) assert V.num_sub_spaces() == sub_spaces return FEniCSBasis(V) else: assert maxh is not None if sub_spaces is None or sub_spaces == 0: V = FunctionSpace(mesh0, family, degree) else: V = VectorFunctionSpace(mesh0, family, degree) assert V.num_sub_spaces() == sub_spaces B = FEniCSBasis(V) return B.refine_maxh(maxh, True)[0]
def _prepare_solution_fcns(self): # Extract parameters needed to create finite elements N = self.parameters["N"] gdim = self._mesh.geometry().dim() # Group elements for phi, chi, v elements_ch = (N - 1) * [ self._FE["phi"], ] + (N - 1) * [ self._FE["chi"], ] elements_ns = [ VectorElement(self._FE["v"], dim=gdim), ] # Append elements for p and th elements_ns.append(self._FE["p"]) if self._FE["th"] is not None: elements_ns.append(self._FE["th"]) # Build function spaces W_ch = FunctionSpace(self._mesh, MixedElement(elements_ch), constrained_domain=self._constrained_domain) W_ns = FunctionSpace(self._mesh, MixedElement(elements_ns), constrained_domain=self._constrained_domain) self._ndofs["CH"] = W_ch.dim() self._ndofs["NS"] = W_ns.dim() self._ndofs["total"] = W_ch.dim() + W_ns.dim() self._subspace["phi"] = [W_ch.sub(i) for i in range(N - 1)] self._subspace["chi"] = [ W_ch.sub(i) for i in range(N - 1, 2 * (N - 1)) ] self._ndofs["phi"] = W_ch.sub(0).dim() self._ndofs["chi"] = W_ch.sub(N - 1).dim() if gdim == 1: self._subspace["v"] = [ W_ns.sub(0), ] self._ndofs["v"] = W_ns.sub(0).dim() else: self._subspace["v"] = [W_ns.sub(0).sub(i) for i in range(gdim)] self._ndofs["v"] = W_ns.sub(0).sub(0).dim() self._subspace["p"] = W_ns.sub(1) self._ndofs["p"] = W_ns.sub(1).dim() self._ndofs["th"] = 0 if W_ns.num_sub_spaces() == 3: self._subspace["th"] = W_ns.sub(2) self._ndofs["th"] = W_ns.sub(2).dim() # ndofs = ( # (N-1)*(self._ndofs["phi"] + self._ndofs["chi"]) # + gdim*self._ndofs["v"] # + self._ndofs["p"] # + self._ndofs["th"] # ) # assert self._ndofs["total"] == ndofs # Create solution variables at ctl w_ctl = (Function(W_ch), Function(W_ns)) w_ctl[0].rename("semi_ctl_ch", "solution_semi_ch_ctl") w_ctl[1].rename("semi_ctl_ns", "solution_semi_ns_ctl") # Create solution variables at ptl w_ptl = [(Function(W_ch), Function(W_ns)) \ for i in range(self.parameters["PTL"])] for i, f in enumerate(w_ptl): f[0].rename("semi_ptl%i_ch" % i, "solution_semi_ch_ptl%i" % i) f[1].rename("semi_ptl%i_ns" % i, "solution_semi_ns_ptl%i" % i) return (w_ctl, w_ptl)
def _prepare_solution_fcns(self): # Extract parameters needed to create finite elements N = self.parameters["N"] gdim = self._mesh.geometry().dim() # Group elements for phi, chi, v elements_ch = (N - 1) * [ self._FE["phi"], ] + (N - 1) * [ self._FE["chi"], ] # NOTE: Elements for phi and chi are grouped together to avoid special # treatment of the case with N = 2. For example, if N == 2 and # phi would be represented as a vector with a single component # then a special treatment is needed to plot this single # component (UFL/DOLFIN ban to plot 1D function on a 2D mesh). elements = [] elements.append(MixedElement(elements_ch)) elements.append(VectorElement(self._FE["v"], dim=gdim)) # Append elements for p and th elements.append(self._FE["p"]) if self._FE["th"] is not None: elements.append(self._FE["th"]) # Build function spaces W = FunctionSpace(self._mesh, MixedElement(elements), constrained_domain=self._constrained_domain) self._ndofs["total"] = W.dim() self._subspace["phi"] = [W.sub(0).sub(i) for i in range(N - 1)] self._subspace["chi"] = [ W.sub(0).sub(i) for i in range(N - 1, 2 * (N - 1)) ] self._ndofs["phi"] = W.sub(0).sub(0).dim() self._ndofs["chi"] = W.sub(0).sub(N - 1).dim() if gdim == 1: self._subspace["v"] = [ W.sub(1), ] self._ndofs["v"] = W.sub(1).dim() else: self._subspace["v"] = [W.sub(1).sub(i) for i in range(gdim)] self._ndofs["v"] = W.sub(1).sub(0).dim() self._subspace["p"] = W.sub(2) self._ndofs["p"] = W.sub(2).dim() self._ndofs["th"] = 0 if W.num_sub_spaces() == 4: self._subspace["th"] = W.sub(3) self._ndofs["th"] = W.sub(3).dim() self._ndofs["CH"] = W.sub(0).dim() self._ndofs["NS"] = (gdim * self._ndofs["v"] + self._ndofs["p"] + self._ndofs["th"]) assert self._ndofs["total"] == self._ndofs["CH"] + self._ndofs["NS"] # Create solution variable at ctl w_ctl = (Function(W), ) w_ctl[0].rename("mono_ctl", "solution_mono_ctl") # Create solution variables at ptl w_ptl = [(Function(W), ) for i in range(self.parameters["PTL"])] for (i, f) in enumerate(w_ptl): f[0].rename("mono_ptl%i" % i, "solution_mono_ptl%i" % i) return (w_ctl, w_ptl)