Skip to content

Commit eb1d399

Browse files
authored
Merge pull request #5894 from xlaussel/avoid_samelookup_in_heap_map
Avoid samelookup in heap map
2 parents 6bf68fb + 89a9bc9 commit eb1d399

File tree

7 files changed

+293
-237
lines changed

7 files changed

+293
-237
lines changed

include/engine/routing_algorithms/routing_base_ch.hpp

Lines changed: 28 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -24,21 +24,21 @@ namespace ch
2424
// Stalling
2525
template <bool DIRECTION, typename HeapT>
2626
bool stallAtNode(const DataFacade<Algorithm> &facade,
27-
const NodeID node,
28-
const EdgeWeight weight,
27+
const typename HeapT::HeapNode &heapNode,
2928
const HeapT &query_heap)
3029
{
31-
for (auto edge : facade.GetAdjacentEdgeRange(node))
30+
for (auto edge : facade.GetAdjacentEdgeRange(heapNode.node))
3231
{
3332
const auto &data = facade.GetEdgeData(edge);
3433
if (DIRECTION == REVERSE_DIRECTION ? data.forward : data.backward)
3534
{
3635
const NodeID to = facade.GetTarget(edge);
3736
const EdgeWeight edge_weight = data.weight;
3837
BOOST_ASSERT_MSG(edge_weight > 0, "edge_weight invalid");
39-
if (query_heap.WasInserted(to))
38+
const auto toHeapNode = query_heap.GetHeapNodeIfWasInserted(to);
39+
if (toHeapNode)
4040
{
41-
if (query_heap.GetKey(to) + edge_weight < weight)
41+
if (toHeapNode->weight + edge_weight < heapNode.weight)
4242
{
4343
return true;
4444
}
@@ -50,11 +50,10 @@ bool stallAtNode(const DataFacade<Algorithm> &facade,
5050

5151
template <bool DIRECTION>
5252
void relaxOutgoingEdges(const DataFacade<Algorithm> &facade,
53-
const NodeID node,
54-
const EdgeWeight weight,
53+
const SearchEngineData<Algorithm>::QueryHeap::HeapNode &heapNode,
5554
SearchEngineData<Algorithm>::QueryHeap &heap)
5655
{
57-
for (const auto edge : facade.GetAdjacentEdgeRange(node))
56+
for (const auto edge : facade.GetAdjacentEdgeRange(heapNode.node))
5857
{
5958
const auto &data = facade.GetEdgeData(edge);
6059
if (DIRECTION == FORWARD_DIRECTION ? data.forward : data.backward)
@@ -63,19 +62,21 @@ void relaxOutgoingEdges(const DataFacade<Algorithm> &facade,
6362
const EdgeWeight edge_weight = data.weight;
6463

6564
BOOST_ASSERT_MSG(edge_weight > 0, "edge_weight invalid");
66-
const EdgeWeight to_weight = weight + edge_weight;
65+
const EdgeWeight to_weight = heapNode.weight + edge_weight;
6766

67+
const auto toHeapNode = heap.GetHeapNodeIfWasInserted(to);
6868
// New Node discovered -> Add to Heap + Node Info Storage
69-
if (!heap.WasInserted(to))
69+
if (!toHeapNode)
7070
{
71-
heap.Insert(to, to_weight, node);
71+
heap.Insert(to, to_weight, heapNode.node);
7272
}
7373
// Found a shorter Path -> Update weight
74-
else if (to_weight < heap.GetKey(to))
74+
else if (to_weight < toHeapNode->weight)
7575
{
7676
// new parent
77-
heap.GetData(to).parent = node;
78-
heap.DecreaseKey(to, to_weight);
77+
toHeapNode->data.parent = heapNode.node;
78+
toHeapNode->weight = to_weight;
79+
heap.DecreaseKey(*toHeapNode);
7980
}
8081
}
8182
}
@@ -122,35 +123,35 @@ void routingStep(const DataFacade<Algorithm> &facade,
122123
const bool force_loop_forward,
123124
const bool force_loop_reverse)
124125
{
125-
const NodeID node = forward_heap.DeleteMin();
126-
const EdgeWeight weight = forward_heap.GetKey(node);
126+
auto heapNode = forward_heap.DeleteMinGetHeapNode();
127+
const auto reverseHeapNode = reverse_heap.GetHeapNodeIfWasInserted(heapNode.node);
127128

128-
if (reverse_heap.WasInserted(node))
129+
if (reverseHeapNode)
129130
{
130-
const EdgeWeight new_weight = reverse_heap.GetKey(node) + weight;
131+
const EdgeWeight new_weight = reverseHeapNode->weight + heapNode.weight;
131132
if (new_weight < upper_bound)
132133
{
133134
// if loops are forced, they are so at the source
134-
if ((force_loop_forward && forward_heap.GetData(node).parent == node) ||
135-
(force_loop_reverse && reverse_heap.GetData(node).parent == node) ||
135+
if ((force_loop_forward && heapNode.data.parent == heapNode.node) ||
136+
(force_loop_reverse && reverseHeapNode->data.parent == heapNode.node) ||
136137
// in this case we are looking at a bi-directional way where the source
137138
// and target phantom are on the same edge based node
138139
new_weight < 0)
139140
{
140141
// check whether there is a loop present at the node
141-
for (const auto edge : facade.GetAdjacentEdgeRange(node))
142+
for (const auto edge : facade.GetAdjacentEdgeRange(heapNode.node))
142143
{
143144
const auto &data = facade.GetEdgeData(edge);
144145
if (DIRECTION == FORWARD_DIRECTION ? data.forward : data.backward)
145146
{
146147
const NodeID to = facade.GetTarget(edge);
147-
if (to == node)
148+
if (to == heapNode.node)
148149
{
149150
const EdgeWeight edge_weight = data.weight;
150151
const EdgeWeight loop_weight = new_weight + edge_weight;
151152
if (loop_weight >= 0 && loop_weight < upper_bound)
152153
{
153-
middle_node_id = node;
154+
middle_node_id = heapNode.node;
154155
upper_bound = loop_weight;
155156
}
156157
}
@@ -161,7 +162,7 @@ void routingStep(const DataFacade<Algorithm> &facade,
161162
{
162163
BOOST_ASSERT(new_weight >= 0);
163164

164-
middle_node_id = node;
165+
middle_node_id = heapNode.node;
165166
upper_bound = new_weight;
166167
}
167168
}
@@ -170,19 +171,19 @@ void routingStep(const DataFacade<Algorithm> &facade,
170171
// make sure we don't terminate too early if we initialize the weight
171172
// for the nodes in the forward heap with the forward/reverse offset
172173
BOOST_ASSERT(min_edge_offset <= 0);
173-
if (weight + min_edge_offset > upper_bound)
174+
if (heapNode.weight + min_edge_offset > upper_bound)
174175
{
175176
forward_heap.DeleteAll();
176177
return;
177178
}
178179

179180
// Stalling
180-
if (STALLING && stallAtNode<DIRECTION>(facade, node, weight, forward_heap))
181+
if (STALLING && stallAtNode<DIRECTION>(facade, heapNode, forward_heap))
181182
{
182183
return;
183184
}
184185

185-
relaxOutgoingEdges<DIRECTION>(facade, node, weight, forward_heap);
186+
relaxOutgoingEdges<DIRECTION>(facade, heapNode, forward_heap);
186187
}
187188

188189
template <bool UseDuration>

include/engine/routing_algorithms/routing_base_mld.hpp

Lines changed: 49 additions & 41 deletions
Original file line numberDiff line numberDiff line change
@@ -228,40 +228,42 @@ retrievePackedPathFromHeap(const SearchEngineData<Algorithm>::QueryHeap &forward
228228
template <bool DIRECTION, typename Algorithm, typename... Args>
229229
void relaxOutgoingEdges(const DataFacade<Algorithm> &facade,
230230
typename SearchEngineData<Algorithm>::QueryHeap &forward_heap,
231-
const NodeID node,
232-
const EdgeWeight weight,
231+
const typename SearchEngineData<Algorithm>::QueryHeap::HeapNode &heapNode,
233232
Args... args)
234233
{
235234
const auto &partition = facade.GetMultiLevelPartition();
236235
const auto &cells = facade.GetCellStorage();
237236
const auto &metric = facade.GetCellMetric();
238237

239-
const auto level = getNodeQueryLevel(partition, node, args...);
238+
const auto level = getNodeQueryLevel(partition, heapNode.node, args...);
240239

241-
if (level >= 1 && !forward_heap.GetData(node).from_clique_arc)
240+
if (level >= 1 && !heapNode.data.from_clique_arc)
242241
{
243242
if (DIRECTION == FORWARD_DIRECTION)
244243
{
245244
// Shortcuts in forward direction
246-
const auto &cell = cells.GetCell(metric, level, partition.GetCell(level, node));
245+
const auto &cell =
246+
cells.GetCell(metric, level, partition.GetCell(level, heapNode.node));
247247
auto destination = cell.GetDestinationNodes().begin();
248-
for (auto shortcut_weight : cell.GetOutWeight(node))
248+
for (auto shortcut_weight : cell.GetOutWeight(heapNode.node))
249249
{
250250
BOOST_ASSERT(destination != cell.GetDestinationNodes().end());
251251
const NodeID to = *destination;
252252

253-
if (shortcut_weight != INVALID_EDGE_WEIGHT && node != to)
253+
if (shortcut_weight != INVALID_EDGE_WEIGHT && heapNode.node != to)
254254
{
255-
const EdgeWeight to_weight = weight + shortcut_weight;
256-
BOOST_ASSERT(to_weight >= weight);
257-
if (!forward_heap.WasInserted(to))
255+
const EdgeWeight to_weight = heapNode.weight + shortcut_weight;
256+
BOOST_ASSERT(to_weight >= heapNode.weight);
257+
const auto toHeapNode = forward_heap.GetHeapNodeIfWasInserted(to);
258+
if (!toHeapNode)
258259
{
259-
forward_heap.Insert(to, to_weight, {node, true});
260+
forward_heap.Insert(to, to_weight, {heapNode.node, true});
260261
}
261-
else if (to_weight < forward_heap.GetKey(to))
262+
else if (to_weight < toHeapNode->weight)
262263
{
263-
forward_heap.GetData(to) = {node, true};
264-
forward_heap.DecreaseKey(to, to_weight);
264+
toHeapNode->data = {heapNode.node, true};
265+
toHeapNode->weight = to_weight;
266+
forward_heap.DecreaseKey(*toHeapNode);
265267
}
266268
}
267269
++destination;
@@ -270,25 +272,28 @@ void relaxOutgoingEdges(const DataFacade<Algorithm> &facade,
270272
else
271273
{
272274
// Shortcuts in backward direction
273-
const auto &cell = cells.GetCell(metric, level, partition.GetCell(level, node));
275+
const auto &cell =
276+
cells.GetCell(metric, level, partition.GetCell(level, heapNode.node));
274277
auto source = cell.GetSourceNodes().begin();
275-
for (auto shortcut_weight : cell.GetInWeight(node))
278+
for (auto shortcut_weight : cell.GetInWeight(heapNode.node))
276279
{
277280
BOOST_ASSERT(source != cell.GetSourceNodes().end());
278281
const NodeID to = *source;
279282

280-
if (shortcut_weight != INVALID_EDGE_WEIGHT && node != to)
283+
if (shortcut_weight != INVALID_EDGE_WEIGHT && heapNode.node != to)
281284
{
282-
const EdgeWeight to_weight = weight + shortcut_weight;
283-
BOOST_ASSERT(to_weight >= weight);
284-
if (!forward_heap.WasInserted(to))
285+
const EdgeWeight to_weight = heapNode.weight + shortcut_weight;
286+
BOOST_ASSERT(to_weight >= heapNode.weight);
287+
const auto toHeapNode = forward_heap.GetHeapNodeIfWasInserted(to);
288+
if (!toHeapNode)
285289
{
286-
forward_heap.Insert(to, to_weight, {node, true});
290+
forward_heap.Insert(to, to_weight, {heapNode.node, true});
287291
}
288-
else if (to_weight < forward_heap.GetKey(to))
292+
else if (to_weight < toHeapNode->weight)
289293
{
290-
forward_heap.GetData(to) = {node, true};
291-
forward_heap.DecreaseKey(to, to_weight);
294+
toHeapNode->data = {heapNode.node, true};
295+
toHeapNode->weight = to_weight;
296+
forward_heap.DecreaseKey(*toHeapNode);
292297
}
293298
}
294299
++source;
@@ -297,7 +302,7 @@ void relaxOutgoingEdges(const DataFacade<Algorithm> &facade,
297302
}
298303

299304
// Boundary edges
300-
for (const auto edge : facade.GetBorderEdgeRange(level, node))
305+
for (const auto edge : facade.GetBorderEdgeRange(level, heapNode.node))
301306
{
302307
const auto &edge_data = facade.GetEdgeData(edge);
303308

@@ -310,21 +315,23 @@ void relaxOutgoingEdges(const DataFacade<Algorithm> &facade,
310315
checkParentCellRestriction(partition.GetCell(level + 1, to), args...))
311316
{
312317
const auto node_weight =
313-
facade.GetNodeWeight(DIRECTION == FORWARD_DIRECTION ? node : to);
318+
facade.GetNodeWeight(DIRECTION == FORWARD_DIRECTION ? heapNode.node : to);
314319
const auto turn_penalty = facade.GetWeightPenaltyForEdgeID(edge_data.turn_id);
315320

316321
// TODO: BOOST_ASSERT(edge_data.weight == node_weight + turn_penalty);
317322

318-
const EdgeWeight to_weight = weight + node_weight + turn_penalty;
323+
const EdgeWeight to_weight = heapNode.weight + node_weight + turn_penalty;
319324

320-
if (!forward_heap.WasInserted(to))
325+
const auto toHeapNode = forward_heap.GetHeapNodeIfWasInserted(to);
326+
if (!toHeapNode)
321327
{
322-
forward_heap.Insert(to, to_weight, {node, false});
328+
forward_heap.Insert(to, to_weight, {heapNode.node, false});
323329
}
324-
else if (to_weight < forward_heap.GetKey(to))
330+
else if (to_weight < toHeapNode->weight)
325331
{
326-
forward_heap.GetData(to) = {node, false};
327-
forward_heap.DecreaseKey(to, to_weight);
332+
toHeapNode->data = {heapNode.node, false};
333+
toHeapNode->weight = to_weight;
334+
forward_heap.DecreaseKey(*toHeapNode);
328335
}
329336
}
330337
}
@@ -341,34 +348,35 @@ void routingStep(const DataFacade<Algorithm> &facade,
341348
const bool force_loop_reverse,
342349
Args... args)
343350
{
344-
const auto node = forward_heap.DeleteMin();
345-
const auto weight = forward_heap.GetKey(node);
351+
const auto heapNode = forward_heap.DeleteMinGetHeapNode();
352+
const auto weight = heapNode.weight;
346353

347-
BOOST_ASSERT(!facade.ExcludeNode(node));
354+
BOOST_ASSERT(!facade.ExcludeNode(heapNode.node));
348355

349356
// Upper bound for the path source -> target with
350357
// weight(source -> node) = weight weight(to -> target) ≤ reverse_weight
351358
// is weight + reverse_weight
352359
// More tighter upper bound requires additional condition reverse_heap.WasRemoved(to)
353360
// with weight(to -> target) = reverse_weight and all weights ≥ 0
354-
if (reverse_heap.WasInserted(node))
361+
const auto reverseHeapNode = reverse_heap.GetHeapNodeIfWasInserted(heapNode.node);
362+
if (reverseHeapNode)
355363
{
356-
auto reverse_weight = reverse_heap.GetKey(node);
364+
auto reverse_weight = reverseHeapNode->weight;
357365
auto path_weight = weight + reverse_weight;
358366

359367
// MLD uses loops forcing only to prune single node paths in forward and/or
360368
// backward direction (there is no need to force loops in MLD but in CH)
361-
if (!(force_loop_forward && forward_heap.GetData(node).parent == node) &&
362-
!(force_loop_reverse && reverse_heap.GetData(node).parent == node) &&
369+
if (!(force_loop_forward && heapNode.data.parent == heapNode.node) &&
370+
!(force_loop_reverse && reverseHeapNode->data.parent == heapNode.node) &&
363371
(path_weight >= 0) && (path_weight < path_upper_bound))
364372
{
365-
middle_node = node;
373+
middle_node = heapNode.node;
366374
path_upper_bound = path_weight;
367375
}
368376
}
369377

370378
// Relax outgoing edges from node
371-
relaxOutgoingEdges<DIRECTION>(facade, forward_heap, node, weight, args...);
379+
relaxOutgoingEdges<DIRECTION>(facade, forward_heap, heapNode, args...);
372380
}
373381

374382
// With (s, middle, t) we trace back the paths middle -> s and middle -> t.

0 commit comments

Comments
 (0)