diff --git a/meshmode/mesh/__init__.py b/meshmode/mesh/__init__.py index fd4580449e06384eb326df577d5a0afb5a4b0530..f3d33c37549db9c4a9d85562b2cd1da9e0bd278e 100644 --- a/meshmode/mesh/__init__.py +++ b/meshmode/mesh/__init__.py @@ -723,7 +723,7 @@ class Mesh(Record): # }}} if vertices is None: - is_conforming = False + is_conforming = None if not is_conforming: if nodal_adjacency is None: @@ -828,6 +828,10 @@ class Mesh(Record): @property def nvertices(self): + if self.vertices is None: + from meshmode import DataUnavailable + raise DataUnavailable("vertices") + return self.vertices.shape[-1] @property @@ -837,9 +841,6 @@ class Mesh(Record): @property def nodal_adjacency(self): from meshmode import DataUnavailable - if self.vertices is None: - raise DataUnavailable("vertices") - if self._nodal_adjacency is False: raise DataUnavailable("nodal_adjacency") @@ -862,9 +863,6 @@ class Mesh(Record): @property def facial_adjacency_groups(self): from meshmode import DataUnavailable - if self.vertices is None: - raise DataUnavailable("vertices") - if self._facial_adjacency_groups is False: raise DataUnavailable("facial_adjacency_groups") diff --git a/meshmode/mesh/refinement/no_adjacency.py b/meshmode/mesh/refinement/no_adjacency.py index e257653415ead8699663b621a48cf8a18e2af5c0..f37f66215ded63f530db8d5a2cb465d38771b5db 100644 --- a/meshmode/mesh/refinement/no_adjacency.py +++ b/meshmode/mesh/refinement/no_adjacency.py @@ -146,19 +146,19 @@ class RefinerWithoutAdjacency(object): """ mesh = self._current_mesh - if mesh.vertices is None: - raise RuntimeError("Meshes without vertices cannot be refined.") - refine_flags = np.asarray(refine_flags, dtype=np.bool) if len(refine_flags) != mesh.nelements: raise ValueError("length of refine_flags does not match " "element count of last generated mesh") + perform_vertex_updates = mesh.vertices is not None + new_el_groups = [] group_refinement_records = [] additional_vertices = [] - inew_vertex = mesh.nvertices + if perform_vertex_updates: + inew_vertex = mesh.nvertices for igrp, group in enumerate(mesh.groups): bisection_info = self._get_bisection_tesselation_info( @@ -197,55 +197,59 @@ class RefinerWithoutAdjacency(object): # {{{ get new vertices together - midpoints = bisection_info.resampler.get_midpoints( - group, bisection_info, refining_el_old_indices) + if perform_vertex_updates: + midpoints = bisection_info.resampler.get_midpoints( + group, bisection_info, refining_el_old_indices) - new_vertex_indices = np.empty( - (new_nelements, group.vertex_indices.shape[1]), - dtype=mesh.vertex_id_dtype) - new_vertex_indices.fill(-17) + new_vertex_indices = np.empty( + (new_nelements, group.vertex_indices.shape[1]), + dtype=mesh.vertex_id_dtype) + new_vertex_indices.fill(-17) - # copy over unchanged vertices - new_vertex_indices[unrefined_el_new_indices] = \ - group.vertex_indices[~grp_flags] + # copy over unchanged vertices + new_vertex_indices[unrefined_el_new_indices] = \ + group.vertex_indices[~grp_flags] - for old_iel in refining_el_old_indices: - new_iel_base = child_el_indices[old_iel] + for old_iel in refining_el_old_indices: + new_iel_base = child_el_indices[old_iel] - refining_vertices = np.empty(len(bisection_info.ref_vertices), + refining_vertices = np.empty(len(bisection_info.ref_vertices), dtype=mesh.vertex_id_dtype) - refining_vertices.fill(-17) + refining_vertices.fill(-17) - # carry over old vertices - refining_vertices[bisection_info.orig_vertex_indices] = \ - group.vertex_indices[old_iel] + # carry over old vertices + refining_vertices[bisection_info.orig_vertex_indices] = \ + group.vertex_indices[old_iel] - for imidpoint, (iref_midpoint, (v1, v2)) in enumerate(zip( - bisection_info.midpoint_indices, - bisection_info.midpoint_vertex_pairs)): + for imidpoint, (iref_midpoint, (v1, v2)) in enumerate(zip( + bisection_info.midpoint_indices, + bisection_info.midpoint_vertex_pairs)): - global_v1 = group.vertex_indices[old_iel, v1] - global_v2 = group.vertex_indices[old_iel, v2] + global_v1 = group.vertex_indices[old_iel, v1] + global_v2 = group.vertex_indices[old_iel, v2] - if global_v1 > global_v2: - global_v1, global_v2 = global_v2, global_v1 + if global_v1 > global_v2: + global_v1, global_v2 = global_v2, global_v1 - try: - global_midpoint = self.global_vertex_pair_to_midpoint[ - global_v1, global_v2] - except KeyError: - global_midpoint = inew_vertex - additional_vertices.append(midpoints[old_iel][:, imidpoint]) - inew_vertex += 1 + try: + global_midpoint = self.global_vertex_pair_to_midpoint[ + global_v1, global_v2] + except KeyError: + global_midpoint = inew_vertex + additional_vertices.append( + midpoints[old_iel][:, imidpoint]) + inew_vertex += 1 - refining_vertices[iref_midpoint] = global_midpoint + refining_vertices[iref_midpoint] = global_midpoint - assert (refining_vertices >= 0).all() + assert (refining_vertices >= 0).all() - new_vertex_indices[new_iel_base:new_iel_base+nchildren] = \ - refining_vertices[bisection_info.children] + new_vertex_indices[new_iel_base:new_iel_base+nchildren] = \ + refining_vertices[bisection_info.children] - assert (new_vertex_indices >= 0).all() + assert (new_vertex_indices >= 0).all() + else: + new_vertex_indices = None # }}} @@ -279,11 +283,14 @@ class RefinerWithoutAdjacency(object): nodes=new_nodes, unit_nodes=group.unit_nodes)) - new_vertices = np.empty( - (mesh.ambient_dim, mesh.nvertices + len(additional_vertices)), - mesh.vertices.dtype) - new_vertices[:, :mesh.nvertices] = mesh.vertices - new_vertices[:, mesh.nvertices:] = np.array(additional_vertices).T + if perform_vertex_updates: + new_vertices = np.empty( + (mesh.ambient_dim, mesh.nvertices + len(additional_vertices)), + mesh.vertices.dtype) + new_vertices[:, :mesh.nvertices] = mesh.vertices + new_vertices[:, mesh.nvertices:] = np.array(additional_vertices).T + else: + new_vertices = None from meshmode.mesh import Mesh new_mesh = Mesh(new_vertices, new_el_groups, is_conforming=( diff --git a/meshmode/mesh/refinement/resampler.py b/meshmode/mesh/refinement/resampler.py index 794c1c5a2362d1255f5e3d329c48fb766c6229a9..4631c9caa7220ee7a742670d10b0a7a5998003bd 100644 --- a/meshmode/mesh/refinement/resampler.py +++ b/meshmode/mesh/refinement/resampler.py @@ -74,7 +74,8 @@ class SimplexResampler(object): follows their ordering in the tesselation (see also :meth:`SimplexResampler.get_vertex_pair_to_midpoint_order`) """ - assert len(group.vertex_indices[0]) == group.dim + 1 + if group.vertex_indices is not None: + assert len(group.vertex_indices[0]) == group.dim + 1 # Get midpoints, converted to unit coordinates. midpoints = -1 + np.array([vertex for vertex in @@ -106,7 +107,8 @@ class SimplexResampler(object): The ordering of the child nodes follows the ordering of ``tesselation.children.`` """ - assert len(group.vertex_indices[0]) == group.dim + 1 + if group.vertex_indices is not None: + assert len(group.vertex_indices[0]) == group.dim + 1 from meshmode.mesh.refinement.utils import map_unit_nodes_to_children diff --git a/test/test_meshmode.py b/test/test_meshmode.py index ef3f6d4c3e83459789a4aacdf65736e3f3dd201b..c73c029264ecf625d2c0b2e684c153befa2221f9 100644 --- a/test/test_meshmode.py +++ b/test/test_meshmode.py @@ -1153,6 +1153,10 @@ def test_mesh_without_vertices(ctx_factory): groups = [grp.copy(nodes=grp.nodes, vertex_indices=None) for grp in mesh.groups] mesh = Mesh(None, groups, is_conforming=False) + # try refining it + from meshmode.mesh.refinement import refine_uniformly + mesh = refine_uniformly(mesh, 1) + # make sure the world doesn't end from meshmode.discretization import Discretization from meshmode.discretization.poly_element import \