Skip to content

Commit 841cb9e

Browse files
committed
Remove turn cost storage optimization for edge-based CH
1 parent 622fe6b commit 841cb9e

File tree

1 file changed

+5
-56
lines changed

1 file changed

+5
-56
lines changed

core/src/main/java/com/graphhopper/routing/ch/CHPreparationGraph.java

Lines changed: 5 additions & 56 deletions
Original file line numberDiff line numberDiff line change
@@ -107,63 +107,12 @@ public static void buildFromGraph(CHPreparationGraph prepareGraph, Graph graph,
107107
prepareGraph.prepareForContraction();
108108
}
109109

110-
/**
111-
* Builds a turn cost function for a given graph('s turn cost storage) and given uTurnCosts.
112-
* The trivial implementation would be simply using {@link Weighting#calcTurnWeight}. However, it turned out
113-
* that storing all turn costs in separate arrays upfront speeds up edge-based CH preparation by about 25%. See #2084
114-
*/
115110
public static TurnCostFunction buildTurnCostFunctionFromTurnCostStorage(Graph graph, Weighting weighting) {
116-
if (!(weighting instanceof AbstractWeighting))
117-
return weighting::calcTurnWeight;
118-
TurnCostProvider turnCostProvider = ((AbstractWeighting) weighting).getTurnCostProvider();
119-
if (!(turnCostProvider instanceof DefaultTurnCostProvider))
120-
return weighting::calcTurnWeight;
121-
DecimalEncodedValue turnCostEnc = ((DefaultTurnCostProvider) turnCostProvider).getTurnCostEnc();
122-
TurnCostStorage turnCostStorage = graph.getTurnCostStorage();
123-
// we maintain a list of inEdge/outEdge/turn-cost triples (we use two arrays for this) that is sorted by nodes
124-
LongArrayList turnCostEdgePairs = new LongArrayList();
125-
DoubleArrayList turnCosts = new DoubleArrayList();
126-
// for each node we store the index of the first turn cost entry/triple in the list
127-
final int[] turnCostNodes = new int[graph.getNodes() + 1];
128-
TurnCostStorage.Iterator tcIter = turnCostStorage.getAllTurnCosts();
129-
int lastNode = -1;
130-
while (tcIter.next()) {
131-
int viaNode = tcIter.getViaNode();
132-
if (viaNode < lastNode)
133-
throw new IllegalStateException();
134-
long edgePair = BitUtil.LITTLE.toLong(tcIter.getFromEdge(), tcIter.getToEdge());
135-
// note that as long as we only use OSM turn restrictions all the turn costs are infinite anyway
136-
double turnCost = tcIter.getCost(turnCostEnc);
137-
int index = turnCostEdgePairs.size();
138-
turnCostEdgePairs.add(edgePair);
139-
turnCosts.add(turnCost);
140-
if (viaNode != lastNode) {
141-
for (int i = lastNode + 1; i <= viaNode; i++) {
142-
turnCostNodes[i] = index;
143-
}
144-
}
145-
lastNode = viaNode;
146-
}
147-
for (int i = lastNode + 1; i <= turnCostNodes.length - 1; i++) {
148-
turnCostNodes[i] = turnCostEdgePairs.size();
149-
}
150-
turnCostNodes[turnCostNodes.length - 1] = turnCostEdgePairs.size();
151-
152-
// currently the u-turn costs are the same for all junctions, so for now we just get them for one of them
153-
double uTurnCosts = weighting.calcTurnWeight(1, 0, 1);
154-
return (inEdge, viaNode, outEdge) -> {
155-
if (!EdgeIterator.Edge.isValid(inEdge) || !EdgeIterator.Edge.isValid(outEdge))
156-
return 0;
157-
else if (inEdge == outEdge)
158-
return uTurnCosts;
159-
// traverse all turn cost entries we have for this viaNode and return the turn costs if we find a match
160-
for (int i = turnCostNodes[viaNode]; i < turnCostNodes[viaNode + 1]; i++) {
161-
long l = turnCostEdgePairs.get(i);
162-
if (inEdge == BitUtil.LITTLE.getIntLow(l) && outEdge == BitUtil.LITTLE.getIntHigh(l))
163-
return turnCosts.get(i);
164-
}
165-
return 0;
166-
};
111+
// At some point we used an optimized version where we copied the turn costs to sorted arrays
112+
// temporarily. This seemed to be around 25% faster according to measurements on the Bavaria
113+
// map, but later this turned out to be no real improvement for large maps (planet, Europe, a
114+
// and even Germany). See also #2084
115+
return weighting::calcTurnWeight;
167116
}
168117

169118
public int getNodes() {

0 commit comments

Comments
 (0)