def test_nodal_face_mass_matrix(dim, order=3): from modepy.tools import unit_vertices all_verts = unit_vertices(dim).T basis = mp.simplex_onb(dim, order) np.set_printoptions(linewidth=200) from modepy.matrices import nodal_face_mass_matrix volume_nodes = mp.warp_and_blend_nodes(dim, order) face_nodes = mp.warp_and_blend_nodes(dim - 1, order) for iface in range(dim + 1): verts = np.hstack([all_verts[:, :iface], all_verts[:, iface + 1:]]) fmm = nodal_face_mass_matrix(basis, volume_nodes, face_nodes, order, verts) fmm2 = nodal_face_mass_matrix(basis, volume_nodes, face_nodes, order + 1, verts) assert la.norm(fmm - fmm2, np.inf) < 1e-11 fmm[np.abs(fmm) < 1e-13] = 0 print(fmm) nnz = np.sum(np.abs(fmm) > 0) print(nnz) print( mp.mass_matrix( mp.simplex_onb(dim - 1, order), mp.warp_and_blend_nodes(dim - 1, order), ))
def mass_matrix(self): assert self.is_orthogonal_basis() import modepy as mp return mp.mass_matrix( self.basis(), self.unit_nodes)
def mass_matrix(grp: InterpolatoryElementGroupBase) -> np.ndarray: if not isinstance(grp, InterpolatoryElementGroupBase): raise NoninterpolatoryElementGroupError( f"cannot construct mass matrix on '{type(grp).__name__}'") assert grp.is_orthonormal_basis() return mp.mass_matrix(grp.basis_obj().functions, grp.unit_nodes)
def test_deprecated_nodal_face_mass_matrix(dims, order=3): # FIXME DEPRECATED remove along with nodal_face_mass_matrix (>=2022) vol_shape = mp.Simplex(dims) vol_space = mp.space_for_shape(vol_shape, order) vertices = mp.unit_vertices_for_shape(vol_shape) volume_nodes = mp.edge_clustered_nodes_for_space(vol_space, vol_shape) volume_basis = mp.basis_for_space(vol_space, vol_shape) from modepy.matrices import nodal_face_mass_matrix for face in mp.faces_for_shape(vol_shape): face_space = mp.space_for_shape(face, order) face_nodes = mp.edge_clustered_nodes_for_space(face_space, face) face_vertices = vertices[:, face.volume_vertex_indices] fmm = nodal_face_mass_matrix( volume_basis.functions, volume_nodes, face_nodes, order, face_vertices) fmm2 = nodal_face_mass_matrix( volume_basis.functions, volume_nodes, face_nodes, order+1, face_vertices) error = la.norm(fmm - fmm2, np.inf) / la.norm(fmm2, np.inf) logger.info("fmm error: %.5e", error) assert error < 5e-11, f"error {error:.5e} on face {face.face_index}" fmm[np.abs(fmm) < 1e-13] = 0 nnz = np.sum(fmm > 0) logger.info("fmm: nnz %d\n%s", nnz, fmm) logger.info("mass matrix:\n%s", mp.mass_matrix( mp.basis_for_space(face_space, face).functions, mp.edge_clustered_nodes_for_space(face_space, face)))
def test_nodal_face_mass_matrix(dim, order=3): from modepy.tools import unit_vertices all_verts = unit_vertices(dim).T basis = mp.simplex_onb(dim, order) np.set_printoptions(linewidth=200) from modepy.matrices import nodal_face_mass_matrix volume_nodes = mp.warp_and_blend_nodes(dim, order) face_nodes = mp.warp_and_blend_nodes(dim-1, order) for iface in range(dim+1): verts = np.hstack([all_verts[:, :iface], all_verts[:, iface+1:]]) fmm = nodal_face_mass_matrix(basis, volume_nodes, face_nodes, order, verts) fmm2 = nodal_face_mass_matrix(basis, volume_nodes, face_nodes, order+1, verts) assert la.norm(fmm-fmm2, np.inf) < 1e-11 fmm[np.abs(fmm) < 1e-13] = 0 print(fmm) nnz = np.sum(np.abs(fmm) > 0) print(nnz) print(mp.mass_matrix( mp.simplex_onb(dim-1, order), mp.warp_and_blend_nodes(dim-1, order), ))
def test_nodal_mass_matrix_for_face(dims, shape_cls, order=3): vol_shape = shape_cls(dims) vol_space = mp.space_for_shape(vol_shape, order) volume_nodes = mp.edge_clustered_nodes_for_space(vol_space, vol_shape) volume_basis = mp.basis_for_space(vol_space, vol_shape) from modepy.matrices import (nodal_mass_matrix_for_face, nodal_quad_mass_matrix_for_face) for face in mp.faces_for_shape(vol_shape): face_space = mp.space_for_shape(face, order) face_basis = mp.basis_for_space(face_space, face) face_nodes = mp.edge_clustered_nodes_for_space(face_space, face) face_quad = mp.quadrature_for_space(mp.space_for_shape(face, 2*order), face) face_quad2 = mp.quadrature_for_space( mp.space_for_shape(face, 2*order+2), face) fmm = nodal_mass_matrix_for_face( face, face_quad, face_basis.functions, volume_basis.functions, volume_nodes, face_nodes) fmm2 = nodal_quad_mass_matrix_for_face( face, face_quad2, volume_basis.functions, volume_nodes) for f_face in face_basis.functions: fval_nodal = f_face(face_nodes) fval_quad = f_face(face_quad2.nodes) assert ( la.norm(fmm@fval_nodal - fmm2@fval_quad, np.inf) / la.norm(fval_quad)) < 3e-15 fmm[np.abs(fmm) < 1e-13] = 0 nnz = np.sum(fmm > 0) logger.info("fmm: nnz %d\n%s", nnz, fmm) logger.info("mass matrix:\n%s", mp.mass_matrix(face_basis.functions, face_nodes))
def weights(self): return np.dot( mp.mass_matrix(self.basis(), self.unit_nodes), np.ones(len(self.basis())))
def quadrature_rule(self): basis_fcts = self._basis.functions nodes = self._nodes mass_matrix = mp.mass_matrix(basis_fcts, nodes) weights = np.dot(mass_matrix, np.ones(len(basis_fcts))) return mp.Quadrature(nodes, weights, exact_to=self.order)
def weights(self): return np.dot(mp.mass_matrix(self.basis(), self.unit_nodes), np.ones(len(self.basis())))