public RouteSegment loadRouteSegment(int x31, int y31, int memoryLimit) { long tileId = getRoutingTile(x31, y31, memoryLimit, OPTION_SMART_LOAD); TLongObjectHashMap<RouteDataObject> excludeDuplications = new TLongObjectHashMap<RouteDataObject>(); RouteSegment original = null; if (tileRoutes.containsKey(tileId)) { List<RouteDataObject> routes = tileRoutes.get(tileId); if (routes != null) { for (RouteDataObject ro : routes) { for (int i = 0; i < ro.pointsX.length; i++) { if (ro.getPoint31XTile(i) == x31 && ro.getPoint31YTile(i) == y31) { excludeDuplications.put(calcRouteId(ro, i), ro); RouteSegment segment = new RouteSegment(ro, i); segment.next = original; original = segment; } } } } } List<RoutingSubregionTile> subregions = indexedSubregions.get(tileId); if (subregions != null) { for (RoutingSubregionTile rs : subregions) { original = rs.loadRouteSegment(x31, y31, this, excludeDuplications, original); } } return original; }
public int getCurrentlyLoadedTiles() { int cnt = 0; for (RoutingSubregionTile t : this.subregionTiles) { if (t.isLoaded()) { cnt++; } } return cnt; }
public void unloadAllData(RoutingContext except) { for (RoutingSubregionTile tl : subregionTiles) { if (tl.isLoaded()) { if (except == null || except.searchSubregionTile(tl.subregion) < 0) { tl.unload(); unloadedTiles++; global.size -= tl.tileStatistics.size; } } } subregionTiles.clear(); tileRoutes.clear(); indexedSubregions.clear(); }
private void loadSubregionTile(final RoutingSubregionTile ts, boolean loadObjectsInMemory) { boolean wasUnloaded = ts.isUnloaded(); int ucount = ts.getUnloadCont(); if (nativeLib == null) { long now = System.nanoTime(); try { BinaryMapIndexReader reader = reverseMap.get(ts.subregion.routeReg); ts.setLoadedNonNative(); List<RouteDataObject> res = reader.loadRouteIndexData(ts.subregion); // System.out.println(ts.subregion.shiftToData + " " + res); for (RouteDataObject ro : res) { if (ro != null && config.router.acceptLine(ro)) { ts.add(ro); } } } catch (IOException e) { throw new RuntimeException("Loading data exception", e); } timeToLoad += (System.nanoTime() - now); } else { long now = System.nanoTime(); NativeRouteSearchResult ns = nativeLib.loadRouteRegion(ts.subregion, loadObjectsInMemory); // System.out.println(ts.subregion.shiftToData + " " + Arrays.toString(ns.objects)); ts.setLoadedNative(ns, this); timeToLoad += (System.nanoTime() - now); } loadedTiles++; if (wasUnloaded) { if (ucount == 1) { loadedPrevUnloadedTiles++; } } else { if (global != null) { global.allRoutes += ts.tileStatistics.allRoutes; global.coordinates += ts.tileStatistics.coordinates; } distinctLoadedTiles++; } global.size += ts.tileStatistics.size; }
private void getAllObjects(long tileId, final List<RouteDataObject> toFillIn) { TLongObjectHashMap<RouteDataObject> excludeDuplications = new TLongObjectHashMap<RouteDataObject>(); if (tileRoutes.containsKey(tileId)) { List<RouteDataObject> routes = tileRoutes.get(tileId); if (routes != null) { for (RouteDataObject ro : routes) { if (!excludeDuplications.contains(ro.id)) { excludeDuplications.put(ro.id, ro); toFillIn.add(ro); } } } } List<RoutingSubregionTile> subregions = indexedSubregions.get(tileId); if (subregions != null) { for (RoutingSubregionTile rs : subregions) { rs.loadAllObjects(toFillIn, this, excludeDuplications); } } }
public RoutingContext(RoutingContext cp) { this.config = cp.config; this.map.putAll(cp.map); this.useBaseMap = cp.useBaseMap; this.reverseMap.putAll(cp.reverseMap); this.nativeLib = cp.nativeLib; // copy local data and clear caches for (RoutingSubregionTile tl : subregionTiles) { if (tl.isLoaded()) { subregionTiles.add(tl); for (RouteSegment rs : tl.routes.valueCollection()) { RouteSegment s = rs; while (s != null) { s.parentRoute = null; s.parentSegmentEnd = 0; s.distanceFromStart = 0; s.distanceToEnd = 0; s = s.next; } } } } }
public void unloadUnusedTiles(int memoryLimit) { float desirableSize = memoryLimit * 0.7f; List<RoutingSubregionTile> list = new ArrayList<RoutingSubregionTile>(subregionTiles.size() / 2); int loaded = 0; for (RoutingSubregionTile t : subregionTiles) { if (t.isLoaded()) { list.add(t); loaded++; } } maxLoadedTiles = Math.max(maxLoadedTiles, getCurrentlyLoadedTiles()); Collections.sort( list, new Comparator<RoutingSubregionTile>() { private int pow(int base, int pw) { int r = 1; for (int i = 0; i < pw; i++) { r *= base; } return r; } @Override public int compare(RoutingSubregionTile o1, RoutingSubregionTile o2) { int v1 = (o1.access + 1) * pow(10, o1.getUnloadCont() - 1); int v2 = (o2.access + 1) * pow(10, o2.getUnloadCont() - 1); return v1 < v2 ? -1 : (v1 == v2 ? 0 : 1); } }); int i = 0; while (getCurrentEstimatedSize() >= desirableSize && (list.size() - i) > loaded / 5 && i < list.size()) { RoutingSubregionTile unload = list.get(i); i++; // System.out.println("Unload " + unload); unload.unload(); unloadedTiles++; global.size -= unload.tileStatistics.size; // tile could be cleaned from routing tiles and deleted from whole list } for (RoutingSubregionTile t : subregionTiles) { t.access /= 3; } }
@SuppressWarnings("unused") private long getRoutingTile(int x31, int y31, int memoryLimit, int loadOptions) { // long now = System.nanoTime(); long xloc = x31 >> (31 - config.ZOOM_TO_LOAD_TILES); long yloc = y31 >> (31 - config.ZOOM_TO_LOAD_TILES); long tileId = (xloc << config.ZOOM_TO_LOAD_TILES) + yloc; if (loadOptions != OPTION_NO_LOAD) { if (memoryLimit == 0) { memoryLimit = config.memoryLimitation; } if (getCurrentEstimatedSize() > 0.9 * memoryLimit) { int sz1 = getCurrentEstimatedSize(); long h1 = 0; if (SHOW_GC_SIZE && sz1 > 0.7 * memoryLimit) { runGCUsedMemory(); h1 = runGCUsedMemory(); } int clt = getCurrentlyLoadedTiles(); long us1 = (Runtime.getRuntime().totalMemory() - Runtime.getRuntime().freeMemory()); unloadUnusedTiles(memoryLimit); if (h1 != 0 && getCurrentlyLoadedTiles() != clt) { int sz2 = getCurrentEstimatedSize(); runGCUsedMemory(); long h2 = runGCUsedMemory(); float mb = (1 << 20); log.warn( "Unload tiles : estimated " + (sz1 - sz2) / mb + " ?= " + (h1 - h2) / mb + " actual"); log.warn( "Used after " + h2 / mb + " of " + Runtime.getRuntime().totalMemory() / mb + " max " + maxMemory() / mb); } else { float mb = (1 << 20); int sz2 = getCurrentEstimatedSize(); log.warn( "Unload tiles : occupied before " + sz1 / mb + " Mb - now " + sz2 / mb + "MB " + memoryLimit / mb + " limit MB " + config.memoryLimitation / mb); long us2 = (Runtime.getRuntime().totalMemory() - Runtime.getRuntime().freeMemory()); log.warn( "Used memory before " + us1 / mb + "after " + us1 / mb + " of max " + maxMemory() / mb); } } if (!indexedSubregions.containsKey(tileId)) { List<RoutingSubregionTile> collection = loadTileHeaders(x31, y31); indexedSubregions.put(tileId, collection); } List<RoutingSubregionTile> subregions = indexedSubregions.get(tileId); if (subregions != null) { for (RoutingSubregionTile ts : subregions) { if (!ts.isLoaded()) { loadSubregionTile(ts, loadOptions == OPTION_IN_MEMORY_LOAD); } } } } // timeToLoad += (System.nanoTime() - now); return tileId; }