v2 - now does nothing more (or less) than revert commits 1228 and 1373.

------------

Way back in September, revision 1228 changed one of the routing data
structures (Table A) to have one entry per road rather than one entry
per arc (a road contains 1 or more arcs). This reduced the number of
Table A entries required which made the maps smaller and, hopefully,
improved the routing because the routing centres could be larger.

However, I have been trying for some time now to find why the routing
is partially broken on my Nuvi 255 for certain combinations of mkgmap
version, extra patches and the options used when compiling the map. The
same maps work fine (as far as I have tested them) on mapsource and
the etrex. Not one routing failure occurred on those that could not be
attributed to something else.

So, after much dicking around with options, patches, etc., I think the
Table A size reduction is the culprit. The attached patch essentially
undoes the good work from September (although this code is simpler than
what was there before). With this, the Nuvi barfs no more. The downside
is that the map has grown again. Can't say whether the routing quality
has changed.

Rolled into this patch is another reversion. The value of
MAX_ARC_LENGTH has been reverted to 75000. Never did believe that was
the real solution.

Please give it a go and report any findings.

Mark

PS - Marko, please try this and see if the routing problems you were
experiencing still occur. Also, please try it on your Nuvi user and see
if their problems go away.

PPS - the one pleasing aspect of all this is that if it proves to be a
sensible change, the node-reduction patch that I keep banging on about
will see the light of day.
diff --git a/src/uk/me/parabola/imgfmt/app/net/TableA.java b/src/uk/me/parabola/imgfmt/app/net/TableA.java
index 599adf7..a0c87ee 100644
--- a/src/uk/me/parabola/imgfmt/app/net/TableA.java
+++ b/src/uk/me/parabola/imgfmt/app/net/TableA.java
@@ -37,7 +37,7 @@ public class TableA {
 	// This table's start position relative to the start of NOD 1
 	private int offset;
 
-	private final LinkedHashMap<RoadDef,Integer> arcs = new LinkedHashMap<RoadDef,Integer>();
+	private final LinkedHashMap<Arc,Integer> arcs = new LinkedHashMap<Arc,Integer>();
 
 	private static int count;
 
@@ -47,16 +47,53 @@ public class TableA {
 	}
 
 	/**
+	 * Internal class tracking all the data a Table A entry needs.
+	 * Basically a "forward arc".
+	 */
+	private class Arc {
+		final RouteNode first; final RouteNode second;
+		final RoadDef roadDef;
+
+		Arc(RouteArc arc) {
+			if (arc.isForward()) {
+				first = arc.getSource();
+				second = arc.getDest();
+			} else {
+				first = arc.getDest();
+				second = arc.getSource();
+			}
+			roadDef = arc.getRoadDef();
+		}
+
+		public boolean equals(Object obj) {
+			Arc arc = (Arc) obj;
+			return first.equals(arc.first)
+				&& second.equals(arc.second)
+				&& roadDef.equals(arc.roadDef);
+		}
+
+		public int hashCode() {
+			return first.hashCode() + 2*second.hashCode() + roadDef.hashCode();
+		}
+
+		public String toString() {
+			return "" + first + "->" + second + " (" + roadDef + ")";
+		}
+	}
+
+	/**
 	 * Add an arc to the table if not present and set its index.
 	 *
 	 * The value may overflow while it isn't certain that
 	 * the table fulfills the size constraint.
 	 */
 	public void addArc(RouteArc arc) {
-		if (!arcs.containsKey(arc.getRoadDef())) {
-			int i = arcs.size();
-			arcs.put(arc.getRoadDef(), i);
-			log.debug("added arc", count, arc, i);
+		Arc narc = new Arc(arc);
+		int i;
+		if (!arcs.containsKey(narc)) {
+			i = arcs.size();
+			arcs.put(narc, i);
+			log.debug("added arc", count, narc, i);
 		}
 	}
 
@@ -65,10 +102,11 @@ public class TableA {
 	 */
 	public byte getIndex(RouteArc arc) {
 		log.debug("getting index", arc);
-		assert arcs.containsKey(arc.getRoadDef()):
-			"Trying to read Table A index for non-registered arc: " + count + " " + arc;
-		int i = arcs.get(arc.getRoadDef());
-		assert i < 0x100 : "Table A index too large: " + arc;
+		Arc narc = new Arc(arc);
+		assert arcs.containsKey(narc):
+			"Trying to read Table A index for non-registered arc: " + count + " " + narc;
+		int i = arcs.get(narc);
+		assert i < 0x100 : "Table A index too large: " + narc;
 		return (byte) i;
 	}
 
@@ -114,18 +152,18 @@ public class TableA {
 	 */
 	public void writePost(ImgFileWriter writer) {
 		writer.position(offset);
-		for (RoadDef roadDef : arcs.keySet()) {
+		for (Arc arc : arcs.keySet()) {
 			// write the table A entries.  Consists of a pointer to net
 			// followed by 2 bytes of class and speed flags and road restrictions.
-			log.debug("writing Table A entry", roadDef);
-			int pos = roadDef.getOffsetNet1();
-			int access = roadDef.getTabAAccess();
+			log.debug("writing Table A entry", arcs.get(arc));
+			int pos = arc.roadDef.getOffsetNet1();
+			int access = arc.roadDef.getTabAAccess();
 			// top bits of access go into net1 offset
 			final int ACCESS_TOP_BITS = 0xc000;
 			pos |= (access & ACCESS_TOP_BITS) << 8;
 			access &= ~ACCESS_TOP_BITS;
 			writer.put3(pos);
-			writer.put((byte) roadDef.getTabAInfo());
+			writer.put((byte) arc.roadDef.getTabAInfo());
 			writer.put((byte) access);
 		}
 	}
diff --git a/src/uk/me/parabola/mkgmap/osmstyle/StyledConverter.java b/src/uk/me/parabola/mkgmap/osmstyle/StyledConverter.java
index 12b537f..16f8938 100644
--- a/src/uk/me/parabola/mkgmap/osmstyle/StyledConverter.java
+++ b/src/uk/me/parabola/mkgmap/osmstyle/StyledConverter.java
@@ -87,8 +87,8 @@ public class StyledConverter implements OsmConverter {
 	// long lines being assigned to the wrong subdivision
 	private final int MAX_LINE_LENGTH = 40000;
 
-	// limit arc lengths to avoid Nuvi routing failures
-	private final int MAX_ARC_LENGTH = 35000;
+	// limit arc lengths to what can be handled by RouteArc
+	private final int MAX_ARC_LENGTH = 75000;
 
 	private final int MAX_POINTS_IN_WAY = LineSplitterFilter.MAX_POINTS_IN_LINE;
 
_______________________________________________
mkgmap-dev mailing list
[email protected]
http://www.mkgmap.org.uk/mailman/listinfo/mkgmap-dev

Reply via email to