@Test public void internalDisconnect() { GraphHopperStorage storage = createGHStorage(); BaseGraph graph = (BaseGraph) storage.getGraph(Graph.class); EdgeIteratorState iter0 = graph.edge(0, 1, 10, true); EdgeIteratorState iter2 = graph.edge(1, 2, 10, true); EdgeIteratorState iter3 = graph.edge(0, 3, 10, true); EdgeExplorer explorer = graph.createEdgeExplorer(); assertEquals(GHUtility.asSet(3, 1), GHUtility.getNeighbors(explorer.setBaseNode(0))); assertEquals(GHUtility.asSet(2, 0), GHUtility.getNeighbors(explorer.setBaseNode(1))); // remove edge "1-2" but only from 1 not from 2 graph.edgeAccess.internalEdgeDisconnect( iter2.getEdge(), -1, iter2.getBaseNode(), iter2.getAdjNode()); assertEquals(GHUtility.asSet(0), GHUtility.getNeighbors(explorer.setBaseNode(1))); assertEquals(GHUtility.asSet(1), GHUtility.getNeighbors(explorer.setBaseNode(2))); // let 0 unchanged -> no side effects assertEquals(GHUtility.asSet(3, 1), GHUtility.getNeighbors(explorer.setBaseNode(0))); // remove edge "0-1" but only from 0 graph.edgeAccess.internalEdgeDisconnect( iter0.getEdge(), (long) iter3.getEdge() * graph.edgeEntryBytes, iter0.getBaseNode(), iter0.getAdjNode()); assertEquals(GHUtility.asSet(3), GHUtility.getNeighbors(explorer.setBaseNode(0))); assertEquals(GHUtility.asSet(0), GHUtility.getNeighbors(explorer.setBaseNode(3))); assertEquals(GHUtility.asSet(0), GHUtility.getNeighbors(explorer.setBaseNode(1))); storage.close(); }
@Test public void testPathRecursiveUnpacking() { // use an encoder where it is possible to store 2 weights per edge FlagEncoder encoder = new Bike2WeightFlagEncoder(); ShortestWeighting weighting = new ShortestWeighting(encoder); EncodingManager em = new EncodingManager(encoder); GraphHopperStorage ghStorage = createGHStorage(em, Collections.<Weighting>singleton(weighting), false); CHGraphImpl g2 = (CHGraphImpl) ghStorage.getGraph(CHGraph.class, weighting); g2.edge(0, 1, 1, true); EdgeIteratorState iter1_1 = g2.edge(0, 2, 1.4, false); EdgeIteratorState iter1_2 = g2.edge(2, 5, 1.4, false); g2.edge(1, 2, 1, true); g2.edge(1, 3, 3, true); g2.edge(2, 3, 1, true); g2.edge(4, 3, 1, true); g2.edge(2, 5, 1.4, true); g2.edge(3, 5, 1, true); g2.edge(5, 6, 1, true); g2.edge(4, 6, 1, true); g2.edge(6, 7, 1, true); EdgeIteratorState iter2_2 = g2.edge(5, 7); iter2_2.setDistance(1.4).setFlags(encoder.setProperties(10, true, false)); ghStorage.freeze(); // simulate preparation CHEdgeIteratorState iter2_1 = g2.shortcut(0, 5); iter2_1.setDistance(2.8).setFlags(encoder.setProperties(10, true, false)); iter2_1.setSkippedEdges(iter1_1.getEdge(), iter1_2.getEdge()); CHEdgeIteratorState tmp = g2.shortcut(0, 7); tmp.setDistance(4.2).setFlags(encoder.setProperties(10, true, false)); tmp.setSkippedEdges(iter2_1.getEdge(), iter2_2.getEdge()); g2.setLevel(1, 0); g2.setLevel(3, 1); g2.setLevel(4, 2); g2.setLevel(6, 3); g2.setLevel(2, 4); g2.setLevel(5, 5); g2.setLevel(7, 6); g2.setLevel(0, 7); AlgorithmOptions opts = new AlgorithmOptions(AlgorithmOptions.DIJKSTRA_BI, encoder, weighting); Path p = new PrepareContractionHierarchies( new GHDirectory("", DAType.RAM_INT), ghStorage, g2, encoder, weighting, TraversalMode.NODE_BASED) .createAlgo(g2, opts) .calcPath(0, 7); assertEquals(Helper.createTList(0, 2, 5, 7), p.calcNodes()); assertEquals(1064, p.getTime()); assertEquals(4.2, p.getDistance(), 1e-5); }
@Test public void testNameIndex() { graph = createGraph(); EdgeIteratorState iter1 = graph.edge(0, 1, 10, true); iter1.setName("named street1"); EdgeIteratorState iter2 = graph.edge(0, 1, 10, true); iter2.setName("named street2"); assertEquals( "named street1", graph.getEdgeProps(iter1.getEdge(), iter1.getAdjNode()).getName()); assertEquals( "named street2", graph.getEdgeProps(iter2.getEdge(), iter2.getAdjNode()).getName()); }
@Test public void testPathRecursiveUnpacking() { // use an encoder where it is possible to store 2 weights per edge FlagEncoder encoder = new Bike2WeightFlagEncoder(); EncodingManager em = new EncodingManager(encoder); LevelGraphStorage g2 = (LevelGraphStorage) createGraph(em, false); g2.edge(0, 1, 1, true); EdgeIteratorState iter1_1 = g2.edge(0, 2, 1.4, false); EdgeIteratorState iter1_2 = g2.edge(2, 5, 1.4, false); g2.edge(1, 2, 1, true); g2.edge(1, 3, 3, true); g2.edge(2, 3, 1, true); g2.edge(4, 3, 1, true); g2.edge(2, 5, 1.4, true); g2.edge(3, 5, 1, true); g2.edge(5, 6, 1, true); g2.edge(4, 6, 1, true); g2.edge(6, 7, 1, true); EdgeIteratorState iter2_2 = g2.edge(5, 7); iter2_2.setDistance(1.4).setFlags(encoder.setProperties(10, true, false)); // simulate preparation EdgeSkipIterState iter2_1 = g2.shortcut(0, 5); iter2_1.setDistance(2.8).setFlags(encoder.setProperties(10, true, false)); iter2_1.setSkippedEdges(iter1_1.getEdge(), iter1_2.getEdge()); EdgeSkipIterState tmp = g2.shortcut(0, 7); tmp.setDistance(4.2).setFlags(encoder.setProperties(10, true, false)); tmp.setSkippedEdges(iter2_1.getEdge(), iter2_2.getEdge()); g2.setLevel(1, 0); g2.setLevel(3, 1); g2.setLevel(4, 2); g2.setLevel(6, 3); g2.setLevel(2, 4); g2.setLevel(5, 5); g2.setLevel(7, 6); g2.setLevel(0, 7); Path p = new PrepareContractionHierarchies(encoder, new ShortestWeighting()) .setGraph(g2) .createAlgo() .calcPath(0, 7); assertEquals(Helper.createTList(0, 2, 5, 7), p.calcNodes()); assertEquals(1064, p.getMillis()); assertEquals(4.2, p.getDistance(), 1e-5); }
@Test public void testEdgeProperties() { graph = createGraph(); EdgeIteratorState iter1 = graph.edge(0, 1, 10, true); EdgeIteratorState iter2 = graph.edge(0, 2, 20, true); int edgeId = iter1.getEdge(); EdgeIteratorState iter = graph.getEdgeProps(edgeId, 0); assertEquals(10, iter.getDistance(), 1e-5); edgeId = iter2.getEdge(); iter = graph.getEdgeProps(edgeId, 0); assertEquals(2, iter.getBaseNode()); assertEquals(0, iter.getAdjNode()); assertEquals(20, iter.getDistance(), 1e-5); iter = graph.getEdgeProps(edgeId, 2); assertEquals(0, iter.getBaseNode()); assertEquals(2, iter.getAdjNode()); assertEquals(20, iter.getDistance(), 1e-5); iter = graph.getEdgeProps(edgeId, Integer.MIN_VALUE); assertFalse(iter == null); assertEquals(0, iter.getBaseNode()); assertEquals(2, iter.getAdjNode()); iter = graph.getEdgeProps(edgeId, 1); assertTrue(iter == null); // delete graph.markNodeRemoved(1); graph.optimize(); // throw exception if accessing deleted edge try { graph.getEdgeProps(iter1.getEdge(), -1); assertTrue(false); } catch (Exception ex) { } }
@Test public void testSave_and_fileFormat() throws IOException { graph = newGHStorage(new RAMDirectory(defaultGraphLoc, true), true).create(defaultSize); NodeAccess na = graph.getNodeAccess(); assertTrue(na.is3D()); na.setNode(0, 10, 10, 0); na.setNode(1, 11, 20, 1); na.setNode(2, 12, 12, 0.4); EdgeIteratorState iter2 = graph.edge(0, 1, 100, true); iter2.setWayGeometry(Helper.createPointList3D(1.5, 1, 0, 2, 3, 0)); EdgeIteratorState iter1 = graph.edge(0, 2, 200, true); iter1.setWayGeometry(Helper.createPointList3D(3.5, 4.5, 0, 5, 6, 0)); graph.edge(9, 10, 200, true); graph.edge(9, 11, 200, true); graph.edge(1, 2, 120, false); iter1.setName("named street1"); iter2.setName("named street2"); checkGraph(graph); graph.flush(); graph.close(); graph = newGHStorage(new MMapDirectory(defaultGraphLoc), true); assertTrue(graph.loadExisting()); assertEquals(12, graph.getNodes()); checkGraph(graph); assertEquals( "named street1", graph.getEdgeIteratorState(iter1.getEdge(), iter1.getAdjNode()).getName()); assertEquals( "named street2", graph.getEdgeIteratorState(iter2.getEdge(), iter2.getAdjNode()).getName()); graph.edge(3, 4, 123, true).setWayGeometry(Helper.createPointList3D(4.4, 5.5, 0, 6.6, 7.7, 0)); checkGraph(graph); }
@Override public void doPost(HttpServletRequest httpReq, HttpServletResponse httpRes) throws ServletException, IOException { String infoStr = httpReq.getRemoteAddr() + " " + httpReq.getLocale() + " " + httpReq.getHeader("User-Agent"); String type = httpReq.getContentType(); GPXFile gpxFile; if (type.contains("application/xml")) { try { gpxFile = parseXML(httpReq); } catch (Exception ex) { logger.warn("Cannot parse XML for " + httpReq.getQueryString() + ", " + infoStr); httpRes.setStatus(SC_BAD_REQUEST); httpRes.getWriter().append(errorsToXML(Collections.<Throwable>singletonList(ex))); return; } } else { throw new IllegalArgumentException("content type not supported " + type); } final String format = getParam(httpReq, "type", "json"); boolean writeGPX = GPX_FORMAT.equals(format); boolean pointsEncoded = getBooleanParam(httpReq, "points_encoded", true); boolean enableInstructions = writeGPX || getBooleanParam(httpReq, "instructions", true); boolean enableElevation = getBooleanParam(httpReq, "elevation", false); boolean forceRepair = getBooleanParam(httpReq, "force_repair", false); // TODO export OSM IDs instead, use https://github.com/karussell/graphhopper-osm-id-mapping boolean enableTraversalKeys = getBooleanParam(httpReq, "traversal_keys", false); int maxNodesToVisit = (int) getLongParam(httpReq, "max_nodes_to_visit", 500); int separatedSearchDistance = (int) getLongParam(httpReq, "separated_search_distance", 300); String vehicle = getParam(httpReq, "vehicle", "car"); Locale locale = Helper.getLocale(getParam(httpReq, "locale", "en")); GHResponse matchGHRsp = new GHResponse(); MatchResult matchRsp = null; StopWatch sw = new StopWatch().start(); try { FlagEncoder encoder = hopper.getEncodingManager().getEncoder(vehicle); MapMatching matching = new MapMatching(hopper.getGraphHopperStorage(), locationIndexMatch, encoder); matching.setForceRepair(forceRepair); matching.setMaxNodesToVisit(maxNodesToVisit); matching.setSeparatedSearchDistance(separatedSearchDistance); matchRsp = matching.doWork(gpxFile.getEntries()); // fill GHResponse for identical structure Path path = matching.calcPath(matchRsp); Translation tr = trMap.getWithFallBack(locale); new PathMerger().doWork(matchGHRsp, Collections.singletonList(path), tr); } catch (Exception ex) { matchGHRsp.addError(ex); } logger.info( httpReq.getQueryString() + ", " + infoStr + ", took:" + sw.stop().getSeconds() + ", entries:" + gpxFile.getEntries().size() + ", " + matchGHRsp.getDebugInfo()); if (EXTENDED_JSON_FORMAT.equals(format)) { if (matchGHRsp.hasErrors()) { httpRes.setStatus(SC_BAD_REQUEST); httpRes.getWriter().append(new JSONArray(matchGHRsp.getErrors()).toString()); } else { httpRes.getWriter().write(new MatchResultToJson(matchRsp).exportTo().toString()); } } else if (GPX_FORMAT.equals(format)) { String xml = createGPXString(httpReq, httpRes, matchGHRsp); if (matchGHRsp.hasErrors()) { httpRes.setStatus(SC_BAD_REQUEST); httpRes.getWriter().append(xml); } else { writeResponse(httpRes, xml); } } else { Map<String, Object> map = routeSerializer.toJSON( matchGHRsp, true, pointsEncoded, enableElevation, enableInstructions); if (matchGHRsp.hasErrors()) { writeJsonError(httpRes, SC_BAD_REQUEST, new JSONObject(map)); } else { if (enableTraversalKeys) { if (matchRsp == null) { throw new IllegalStateException( "match response has to be none-null if no error happened"); } // encode edges as traversal keys which includes orientation // decode simply by multiplying with 0.5 List<Integer> traversalKeylist = new ArrayList<Integer>(); for (EdgeMatch em : matchRsp.getEdgeMatches()) { EdgeIteratorState edge = em.getEdgeState(); traversalKeylist.add( GHUtility.createEdgeKey( edge.getBaseNode(), edge.getAdjNode(), edge.getEdge(), false)); } map.put("traversal_keys", traversalKeylist); } writeJson(httpReq, httpRes, new JSONObject(map)); } } }