Skip to content

Commit 2df7116

Browse files
committed
clean up index matching code
1 parent d9f4d67 commit 2df7116

File tree

2 files changed

+36
-38
lines changed

2 files changed

+36
-38
lines changed

meshmode/mesh/__init__.py

Lines changed: 28 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -1345,6 +1345,29 @@ def _concatenate_face_ids(face_ids_list):
13451345
faces=np.concatenate([ids.faces for ids in face_ids_list]))
13461346

13471347

1348+
def _find_matching_index_pairs_merged(indices):
1349+
"""
1350+
Return an array of dimension ``(2, nmatches)`` containing pairs of indices into
1351+
*indices* representing entries that are the same.
1352+
"""
1353+
order = np.lexsort(indices)
1354+
diffs = np.diff(indices[:, order], axis=1)
1355+
match_indices, = (~np.any(diffs, axis=0)).nonzero()
1356+
return np.stack((order[match_indices], order[match_indices+1]))
1357+
1358+
1359+
def _find_matching_index_pairs(left_indices, right_indices):
1360+
"""
1361+
Return an array of dimension ``(2, nmatches)`` containing pairs of indices into
1362+
*left_indices* (row 0) and *right_indices* (row 1) representing entries that
1363+
are the same.
1364+
"""
1365+
index_pairs = _find_matching_index_pairs_merged(
1366+
np.concatenate((left_indices, right_indices), axis=1))
1367+
index_pairs[1, :] -= left_indices.shape[1]
1368+
return index_pairs
1369+
1370+
13481371
def _match_faces_by_vertices(groups, face_ids, vertex_index_map_func=None):
13491372
"""
13501373
Return matching faces in *face_ids* (expressed as pairs of indices into
@@ -1388,13 +1411,8 @@ def vertex_index_map_func(vertices):
13881411

13891412
# Normalize vertex-based "face identifiers" by sorting
13901413
face_vertex_indices_increasing = np.sort(face_vertex_indices, axis=0)
1391-
# Lexicographically sort the face vertex indices, then diff the result to find
1392-
# faces with the same vertices
1393-
order = np.lexsort(face_vertex_indices_increasing)
1394-
diffs = np.diff(face_vertex_indices_increasing[:, order], axis=1)
1395-
match_indices, = (~np.any(diffs, axis=0)).nonzero()
13961414

1397-
return np.stack((order[match_indices], order[match_indices+1]))
1415+
return _find_matching_index_pairs_merged(face_vertex_indices_increasing)
13981416

13991417

14001418
def _compute_facial_adjacency_from_vertices(
@@ -1486,22 +1504,10 @@ def _compute_facial_adjacency_from_vertices(
14861504
is_tagged = np.full(len(bdry_elements), False)
14871505

14881506
for tag, tagged_elements_and_faces in tag_to_faces[igrp].items():
1489-
# Combine known tagged faces and current boundary faces into a
1490-
# single array, lexicographically sort them, and find identical
1491-
# neighboring entries to get tags
1492-
extended_elements_and_faces = np.concatenate((
1493-
tagged_elements_and_faces,
1494-
np.stack(
1495-
(bdry_elements, bdry_element_faces),
1496-
axis=-1)))
1497-
order = np.lexsort(extended_elements_and_faces.T)
1498-
diffs = np.diff(extended_elements_and_faces[order, :], axis=0)
1499-
match_indices, = (~np.any(diffs, axis=1)).nonzero()
1500-
# lexsort is stable, so the second entry in each match corresponds
1501-
# to the yet-to-be-tagged boundary face
1502-
face_indices = (
1503-
order[match_indices+1]
1504-
- len(tagged_elements_and_faces))
1507+
face_index_pairs = _find_matching_index_pairs(
1508+
tagged_elements_and_faces.T,
1509+
np.stack((bdry_elements, bdry_element_faces)))
1510+
face_indices = face_index_pairs[1, :]
15051511
if len(face_indices) > 0:
15061512
elements = bdry_elements[face_indices]
15071513
element_faces = bdry_element_faces[face_indices]

meshmode/mesh/io.py

Lines changed: 8 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -272,26 +272,18 @@ def get_mesh(self, return_tag_to_elements_map=False):
272272
for tag, tagged_fvis in tag_to_fvis.items():
273273
for fid, ref_fvi in enumerate(group.face_vertex_indices()):
274274
fvis = group.vertex_indices[:, ref_fvi]
275-
# Combine known tagged fvis and current group fvis into a single
276-
# array, lexicographically sort them, and find identical
277-
# neighboring entries to get tags
278275
if tagged_fvis.shape[1] < fvis.shape[1]:
276+
# tagged_fvis does not contain any faces with the right
277+
# number of vertices
279278
continue
280279
padded_fvis = np.full((fvis.shape[0], tagged_fvis.shape[1]), -1)
281280
padded_fvis[:, :fvis.shape[1]] = fvis
282-
extended_fvis = np.concatenate((tagged_fvis, padded_fvis))
283-
# Make sure vertices are in the same order
284-
extended_fvis = np.sort(extended_fvis, axis=1)
285-
# Lexicographically sort the face vertex indices, then diff the
286-
# result to find tagged faces with the same vertices
287-
order = np.lexsort(extended_fvis.T)
288-
diffs = np.diff(extended_fvis[order, :], axis=0)
289-
match_indices, = (~np.any(diffs, axis=1)).nonzero()
290-
# lexsort is stable, so the second entry in each match
291-
# corresponds to the group face
292-
face_element_indices = (
293-
order[match_indices+1]
294-
- len(tagged_fvis))
281+
from meshmode.mesh import _find_matching_index_pairs
282+
face_element_index_pairs = _find_matching_index_pairs(
283+
# Make sure the vertices are in the same order
284+
np.sort(tagged_fvis, axis=1).T,
285+
np.sort(padded_fvis, axis=1).T)
286+
face_element_indices = face_element_index_pairs[1, :]
295287
if len(face_element_indices) > 0:
296288
elements_and_faces = np.stack(
297289
(

0 commit comments

Comments
 (0)