Skip to content

Commit 4e1c1f9

Browse files
authored
fix(spatial): handle SE2 angles that round to the period (#86)
1 parent 74402d5 commit 4e1c1f9

2 files changed

Lines changed: 23 additions & 4 deletions

File tree

‎src/pgraph/PGraph.py‎

Lines changed: 7 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -2058,14 +2058,17 @@ def prepare(q: NDArray) -> NDArray | None: # noqa: F811
20582058
return None # far outside the data: let the caller do it
20592059
if weight == 0:
20602060
return xy
2061-
return np.r_[xy, np.mod(weight * q[2], period)]
2061+
angle = np.mod(weight * q[2], period)
2062+
if angle >= period:
2063+
angle = 0.0
2064+
return np.r_[xy, angle]
20622065

20632066
if weight == 0:
20642067
tree = spatial.cKDTree(points[:, :2] - shift, boxsize=[size, size])
20652068
else:
2066-
data = np.column_stack(
2067-
[points[:, :2] - shift, np.mod(weight * points[:, 2], period)]
2068-
)
2069+
angle = np.mod(weight * points[:, 2], period)
2070+
angle[angle >= period] = 0.0
2071+
data = np.column_stack([points[:, :2] - shift, angle])
20692072
tree = spatial.cKDTree(data, boxsize=[size, size, period])
20702073

20712074
self._kdtree = _KDTree(tree, index, p, prepare)

‎tests/test_spatial_index.py‎

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -168,6 +168,22 @@ def test_a_query_across_the_angle_wrap(self):
168168
self.assertEqual(v.name, "a")
169169
self.assertAlmostEqual(d, 0.2)
170170

171+
def test_a_negative_angle_that_rounds_to_the_period(self):
172+
for metric in ("SE2", SE2Metric(0.3)):
173+
with self.subTest(metric=metric):
174+
for angle_is_in_graph in (True, False):
175+
with self.subTest(angle_is_in_graph=angle_is_in_graph):
176+
g = UGraph(dim=3, metric=metric)
177+
boundary_angle = -1e-17 if angle_is_in_graph else 0.0
178+
g.add_vertex([0.0, 0.0, boundary_angle], name="boundary")
179+
g.add_vertex([0.0, 0.0, 0.25], name="other")
180+
g.build_kdtree()
181+
182+
query_angle = 0.0 if angle_is_in_graph else -1e-17
183+
query = [0.0, 0.0, query_angle]
184+
self.assertEqual(g.closest(query)[0].name, "boundary")
185+
self.assertEqual(g.near(query, 1e-12)[0][0].name, "boundary")
186+
171187
def test_a_query_far_outside_is_still_right(self):
172188
g, P = points_graph(UGraph, dim=3, metric=SE2Metric(1.0))
173189
g.build_kdtree()

0 commit comments

Comments
 (0)