public static void SaveCandidateIncomingConnections(CandidatePoint candidate, string filename) { int counter = -1; OSMDB result = new OSMDB(); OSMNode osmCandidate = new OSMNode(counter--, candidate.MapPoint.Latitude, candidate.MapPoint.Longitude); osmCandidate.Tags.Add(new OSMTag("observation", candidate.ObservationProbability.ToString())); osmCandidate.Tags.Add(new OSMTag("time", candidate.Layer.TrackPoint.Time.ToString())); result.Nodes.Add(osmCandidate); foreach (var connection in candidate.IncomingConnections) { OSMNode from = new OSMNode(counter--, connection.From.MapPoint.Latitude, connection.From.MapPoint.Longitude); from.Tags.Add(new OSMTag("observation", connection.From.ObservationProbability.ToString())); from.Tags.Add(new OSMTag("time", connection.From.Layer.TrackPoint.Time.ToString())); result.Nodes.Add(from); OSMWay osmConnection = new OSMWay(counter--, new long[] { from.ID, osmCandidate.ID }); osmConnection.Tags.Add(new OSMTag("transmission", connection.TransmissionProbability.ToString())); result.Ways.Add(osmConnection); } result.Save(filename); }
/// <summary> /// Estimates Start of the travel time as an inerpolation between neighbour points /// </summary> /// <param name="db"></param> /// <param name="ways"></param> /// <param name="segmentIndex"></param> /// <returns></returns> static DateTime InterpolateStartTime(OSMDB db, IList <OSMWay> ways, int segmentIndex) { double lenghtBefore = 0; int i = segmentIndex; while (i >= 0 && db.Nodes[ways[i].Nodes[0]].Tags.ContainsTag("time") == false) { i--; lenghtBefore += GetLength(ways[i], db); } DateTime lastTime = DateTime.MinValue; if (i >= 0) { lastTime = DateTime.Parse(db.Nodes[ways[i].Nodes[0]].Tags["time"].Value); } else { throw new ArgumentException("Can not find segment start time"); } double lengthAfter = 0; i = segmentIndex; while (i < ways.Count && db.Nodes[ways[i].Nodes.Last()].Tags.ContainsTag("time") == false) { i++; lengthAfter += GetLength(ways[i], db); } DateTime nextTime = DateTime.MinValue; if (i < ways.Count) { nextTime = DateTime.Parse(db.Nodes[ways[i].Nodes.Last()].Tags["time"].Value); } else { throw new ArgumentException("Can not find segment end time"); } double miliseconds = (nextTime - lastTime).TotalMilliseconds; double totalLength = lenghtBefore + GetLength(ways[segmentIndex], db) + lengthAfter; if (totalLength > 0) { return(lastTime.AddMilliseconds(miliseconds * lenghtBefore / totalLength)); } else { return(lastTime.AddMilliseconds(miliseconds)); } }
/// <summary> /// Get length of the OSMWay in meters /// </summary> /// <param name="way"></param> /// <param name="db"></param> /// <returns></returns> static double GetLength(OSMWay way, OSMDB db) { double result = 0; for (int i = 0; i < way.Nodes.Count - 1; i++) { result += LK.GeoUtils.Calculations.GetDistance2D(db.Nodes[way.Nodes[i]], db.Nodes[way.Nodes[i + 1]]); } return(result); }
static void Main(string[] args) { string configPath = ""; string osmPath = ""; string outputPath = ""; bool showHelp = false; OptionSet parameters = new OptionSet() { { "osm=", v => osmPath = v }, { "c|config=", v => configPath = v }, { "o|output=", v => outputPath = v }, { "h|?|help", v => showHelp = v != null }, }; try { parameters.Parse(args); } catch (OptionException e) { Console.Write("OSM2Routing: "); Console.WriteLine(e.Message); Console.WriteLine("Try `osm2routing --help' for more information."); return; } if (showHelp || string.IsNullOrEmpty(osmPath) || string.IsNullOrEmpty(configPath) || string.IsNullOrEmpty(outputPath)) { ShowHelp(parameters); return; } try { Console.Write("Loading config file ..."); RoutingConfig config = new RoutingConfig(); config.Load(configPath); Console.WriteLine("\t\t\tDone."); Console.Write("Loading OSM file ..."); OSMRoutingDB map = new OSMRoutingDB(); map.Load(config.RoadTypes, osmPath); Console.WriteLine("\t\t\tDone."); Console.Write("Creating routable OSM file ..."); OSMDB routableMap = map.BuildRoutableOSM(); Console.WriteLine("\t\tDone."); Console.Write("Saving routable OSM file ..."); routableMap.Save(outputPath); Console.WriteLine("\t\tDone."); } catch (Exception e) { Console.WriteLine("\nError: " + e.Message); } }
/// <summary> /// Saves path to the OSMDB /// </summary> /// <param name="path">The list of polylines that represent matched path</param> /// <returns>OSMDB with path converted to the OSM format</returns> public OSMDB SaveToOSM(IList <Polyline <IPointGeo> > path) { _db = new OSMDB(); _dbCounter = -1; IPointGeo lastPoint = null; OSMNode node = null; foreach (var line in path) { if (line.Nodes.Count == 0) { continue; } if (line.Nodes.Count == 1) { throw new Exception(); } OSMWay way = new OSMWay(_dbCounter--); way.Tags.Add(new OSMTag("way-id", ((PolylineID)line).WayID.ToString())); way.Tags.Add(new OSMTag("order", (_db.Ways.Count + 1).ToString())); _db.Ways.Add(way); foreach (var point in line.Nodes) { if (point != lastPoint) { lastPoint = point; PointEx pt = (PointEx)point; node = new OSMNode(_dbCounter--, pt.Latitude, pt.Longitude); if (pt.NodeID != 0) { node.Tags.Add(new OSMTag("node-id", pt.NodeID.ToString())); } if (pt.Time != DateTime.MinValue) { node.Tags.Add(new OSMTag("time", pt.Time.ToString())); } if (pt.Crossroad) { node.Tags.Add(new OSMTag("crossroad", "yes")); } _db.Nodes.Add(node); } way.Nodes.Add(node.ID); } } return(_db); }
static void AddTrackToDB(ITravelTimesDB db, string path) { OSMDB track = new OSMDB(); Console.Write("Loading {0} ...", Path.GetFileName(path)); track.Load(path); try { var travelTimes = TravelTime.FromMatchedTrack(track); foreach (var travelTime in travelTimes) { db.AddTravelTime(travelTime); } Console.WriteLine("."); } catch (Exception e) { Console.WriteLine("Error: " + e.Message); } }
static void Main(string[] args) { string osmPath = ""; int eps = -1; int minTraffic = -1; bool showHelp = false; OptionSet parameters = new OptionSet() { { "osm=", "path to the map file", v => osmPath = v }, { "eps=", "size of the eps-neighborhood to be considered (integer)", v => eps = Convert.ToInt32(v) }, { "minTraffic=", "minimum traffic considered (integer)", v => minTraffic = Convert.ToInt32(v) }, { "h|?|help", v => showHelp = v != null }, }; try { parameters.Parse(args); } catch (OptionException e) { Console.Write("TRoute: "); Console.WriteLine(e.Message); Console.WriteLine("Try `TRoute --help' for more information."); return; } if (showHelp || string.IsNullOrEmpty(osmPath) || eps < 0 || minTraffic < 0) { ShowHelp(parameters); return; } var osmFile = new OSMDB(); osmFile.Load(osmPath); var roadGraph = new RoadGraph(); roadGraph.Build(osmFile); // Getting all the nodes with traffic signals Dictionary <double, OSMNode> tagsNodes = new Dictionary <double, OSMNode>(); foreach (var node in osmFile.Nodes) { foreach (var tag in node.Tags) { if (tag.Value.Equals("traffic_signals")) { if (!tagsNodes.Keys.Contains(node.Latitude + node.Longitude)) { tagsNodes.Add(node.Latitude + node.Longitude, node); } } } } var hotRoutes = new FlowScan().Run(roadGraph, eps, minTraffic); // Saving GPX file of the Hot Route HashSet <GPXPoint> listPoints; HashSet <GPXTrackSegment> listSegments; GPXTrackSegment segTrack; List <GPXTrack> track = new List <GPXTrack>(); GPXTrack tr; //Console.WriteLine(hotRoutes.Count); foreach (var hr in hotRoutes) { //Console.WriteLine("Number segs: " + hr.Segments.Count); listSegments = new HashSet <GPXTrackSegment>(); foreach (var seg in hr.Segments) { listPoints = new HashSet <GPXPoint>(); foreach (var segInner in seg.Geometry.Segments) { GPXPoint start; if (tagsNodes.Keys.Contains(segInner.StartPoint.Latitude + segInner.StartPoint.Longitude)) { OSMNode osmNode = tagsNodes[segInner.StartPoint.Latitude + segInner.StartPoint.Longitude]; start = new GPXPoint() { Id = osmNode.ID, Latitude = segInner.StartPoint.Latitude, Longitude = segInner.StartPoint.Longitude, TrafficSignal = true }; } else { OSMNode osmNode = osmFile.Nodes.ToList().First(x => x.Latitude == segInner.StartPoint.Latitude && x.Longitude == segInner.StartPoint.Longitude); start = new GPXPoint() { Id = osmNode.ID, Latitude = segInner.StartPoint.Latitude, Longitude = segInner.StartPoint.Longitude, TrafficSignal = false }; } GPXPoint end; if (tagsNodes.Keys.Contains(segInner.EndPoint.Latitude + segInner.EndPoint.Longitude)) { OSMNode osmNode = tagsNodes[segInner.EndPoint.Latitude + segInner.EndPoint.Longitude]; end = new GPXPoint() { Id = osmNode.ID, Latitude = segInner.EndPoint.Latitude, Longitude = segInner.EndPoint.Longitude, TrafficSignal = true }; } else { OSMNode osmNode = osmFile.Nodes.ToList().First(x => x.Latitude == segInner.EndPoint.Latitude && x.Longitude == segInner.EndPoint.Longitude); end = new GPXPoint() { Id = osmNode.ID, Latitude = segInner.EndPoint.Latitude, Longitude = segInner.EndPoint.Longitude, TrafficSignal = false }; } listPoints.Add(start); listPoints.Add(end); } segTrack = new GPXTrackSegment(listPoints, seg.AvgSpeed, seg.Speed, seg.Id); // passing the traffic segTrack.Traffic = seg.Traffic; listSegments.Add(segTrack); } tr = new GPXTrack(); tr.Segments.AddRange(listSegments); track.Add(tr); } // Bucket Information GPXTrack tBucket = new GPXTrack(); GPXPoint pBucket = new GPXPoint(0, 0, 0, false); GPXTrackSegment sBucket = new GPXTrackSegment(); var bucketInfo = osmFile.Nodes.ToList().Find(x => x.ID == 0); if (bucketInfo != null) { pBucket.StartBucket = TimeSpan.Parse(bucketInfo.Tags.First().Value); pBucket.EndBucket = TimeSpan.Parse(bucketInfo.Tags.Last().Value); } sBucket.Nodes.Add(pBucket); tBucket.Segments.Add(sBucket); var gpx = new GPXDocument() { Tracks = track }; gpx.Tracks.Add(tBucket); gpx.Save("mapWithHotRoutes.gpx"); }
static void Main(string[] args) { string osmPath = ""; string gpxPath = ""; string outputPath = "."; int samplingPeriod = 0; bool showHelp = false; bool filter = false; OptionSet parameters = new OptionSet() { { "osm=", "path to the routable map file", v => osmPath = v }, { "gpx=", "path to the GPX file to process or to the directory to process", v => gpxPath = v }, { "o|output=", "path to the output directory", v => outputPath = v }, { "p|period=", "sampling period of the GPX file", v => samplingPeriod = int.Parse(v) }, { "f|filter", "enables output post processing", v => filter = v != null }, { "h|?|help", v => showHelp = v != null }, }; try { parameters.Parse(args); } catch (OptionException e) { Console.Write("MatchGPX2OSM: "); Console.WriteLine(e.Message); Console.WriteLine("Try `matchgpx2osm --help' for more information."); return; } if (showHelp || string.IsNullOrEmpty(osmPath) || string.IsNullOrEmpty(gpxPath) || string.IsNullOrEmpty(outputPath)) { ShowHelp(parameters); return; } Console.Write("Loading OSM file ..."); OSMDB map = new OSMDB(); map.Load(osmPath); Console.WriteLine("\t\t\tDone."); Console.Write("Building routable road graph ..."); RoadGraph graph = new RoadGraph(); graph.Build(map); Console.WriteLine("\tDone."); STMatching processor = new STMatching(graph); PathReconstructer reconstructor = new PathReconstructer(graph); // Process signle file if (File.Exists(gpxPath)) { ProcessGPXFile(gpxPath, processor, reconstructor, outputPath, samplingPeriod, filter); } // Process all GPX in directory else if (Directory.Exists(gpxPath)) { var files = Directory.GetFiles(gpxPath, "*.gpx"); Console.WriteLine("Found {0} GPX file(s).", files.Length); foreach (var file in files) { ProcessGPXFile(file, processor, reconstructor, outputPath, samplingPeriod, filter); Console.WriteLine(); } } else { Console.WriteLine("No GPX files found"); } }
public static void AddWays(this Polygon <OSMNode> polygon, IList <OSMWay> ways, OSMDB db) { if (ways.Count == 1) { // Check if the created polygon is closed if (ways[0].Nodes.Count > 0 && ways[0].Nodes.First() != ways[0].Nodes.Last()) { throw new ArgumentException("Ways does not form a closed polygon"); } for (int i = 0; i < ways[0].Nodes.Count - 1; i++) { polygon.AddVertex(db.Nodes[ways[0].Nodes[i]]); } } else { long lastVertexID = 0; if (ways[0].Nodes.First() == ways.Last().Nodes.First() || ways[0].Nodes.Last() == ways.Last().Nodes.First()) { lastVertexID = ways.Last().Nodes.First(); } else { lastVertexID = ways.Last().Nodes.Last(); } //// Check orientation of the first way //if (ways[0].Nodes.First() == ways[1].Nodes.First() || ways[0].Nodes.First() == ways[1].Nodes.First()) { // for (int ii = ways[0].; ii < verticesToAdd.Count - 1; ii++) { // AddVertex(verticesToAdd[ii]); // } //} for (int i = 0; i < ways.Count; i++) { List <long> verticesToAdd = new List <long>(); // Checks the way orienatation and picks nodes in correct order if (lastVertexID == ways[i].Nodes[0]) { verticesToAdd.AddRange(ways[i].Nodes); } else if (lastVertexID == ways[i].Nodes.Last()) { verticesToAdd.AddRange(ways[i].Nodes.Reverse()); } else { throw new ArgumentException("Can not create polygon, ways aren't connected"); } for (int ii = 0; ii < verticesToAdd.Count - 1; ii++) { polygon.AddVertex(db.Nodes[verticesToAdd[ii]]); } lastVertexID = verticesToAdd.Last(); } // Check if the created polygon is closed if (polygon.VerticesCount > 0 && polygon.Vertices.First() != db.Nodes[lastVertexID]) { throw new ArgumentException("Ways does not form a closed polygon"); } } }
/// <summary> /// Builds road graph from map data /// </summary> /// <param name="map">OSMDB with preprocessed map data from OSM2Routing utility</param> public void Build(OSMDB map) { Dictionary <long, Node> usedNodes = new Dictionary <long, Node>(); foreach (var segment in map.Ways) { Node start = GetOrCreateNode(segment.Nodes[0], usedNodes); try { start.MapPoint = map.Nodes[segment.Nodes[0]]; } catch (ArgumentException) { continue; // If the start node was not found in the database, skip this path completely } Node end = GetOrCreateNode(segment.Nodes[segment.Nodes.Count - 1], usedNodes); try { end.MapPoint = map.Nodes[segment.Nodes[segment.Nodes.Count - 1]]; } catch (ArgumentException) { continue; // If the end node was not found in the database, skip this path completely } double speed = double.Parse(segment.Tags["speed"].Value, System.Globalization.CultureInfo.InvariantCulture); // Getting the average speed double avgSpeed = 0; if (segment.Tags.ContainsTag("avgSpeed")) { avgSpeed = double.Parse(segment.Tags["avgSpeed"].Value); } int wayId = int.Parse(segment.Tags["way-id"].Value, System.Globalization.CultureInfo.InvariantCulture); long id = segment.ID; ConnectionGeometry geometry = new ConnectionGeometry(); geometry.WayID = wayId; foreach (var n in segment.Nodes) { try { OSMNode mapPoint = map.Nodes[n]; geometry.Nodes.Add(mapPoint); //geometry.Nodes.Add(new PointGeo(mapPoint.Latitude, mapPoint.Longitude)); } catch (ArgumentException) { continue; // If an intermediate node was not found in the database, skip just that node } } _connectionGeometries.Add(geometry); if (segment.Tags["accessible"].Value == "yes") { Connection sc; if (segment.Tags.ContainsTag("traffic")) { var traffic = new HashSet <long>(segment.Tags["traffic"].Value.Split(',').Select(x => long.Parse(x))); sc = new Connection(start, end) { Speed = speed, Geometry = geometry, Traffic = traffic, Id = id, AvgSpeed = avgSpeed }; } else { sc = new Connection(start, end) { Speed = speed, Geometry = geometry, Traffic = new HashSet <long>(), Id = id, AvgSpeed = avgSpeed }; } geometry.Connections.Add(sc); _connections.Add(sc); } if (segment.Tags["accessible-reverse"].Value == "yes") { Connection sc; if (segment.Tags.ContainsTag("traffic")) { var traffic = new HashSet <long>(segment.Tags["traffic"].Value.Split(',').Select(x => long.Parse(x))); sc = new Connection(end, start) { Speed = speed, Geometry = geometry, Traffic = traffic, Id = id, AvgSpeed = avgSpeed }; } else { sc = new Connection(end, start) { Speed = speed, Geometry = geometry, Traffic = new HashSet <long>(), Id = id, AvgSpeed = avgSpeed }; } geometry.Connections.Add(sc); _connections.Add(sc); } } }
/// <summary> /// Creates a new instance of the analyzer /// </summary> /// <param name="map"></param> public TTAnalyzer(OSMDB map) { _map = map; }
/// <summary> /// Creates a new instance of the OSMFIlteredDB /// </summary> public OSMRoutingDB() { _storage = new OSMDB(); _usedNodes = new Dictionary <long, List <long> >(); _ways = new Dictionary <long, long>(); }
static void Main(string[] args) { DateTime span = DateTime.Now; string osmPath = ""; string gpxPath = ""; string xmlPath = ""; string outputPath = "."; int samplingPeriod = 0; bool showHelp = false; bool filter = false; OptionSet parameters = new OptionSet() { { "osm=", "path to the routable map file", v => osmPath = v }, { "gpx=", "path to the GPX file to process or to the directory to process", v => gpxPath = v }, { "xml=", "path to the XML file with the time buckets", v => xmlPath = v }, { "o|output=", "path to the output directory", v => outputPath = v }, { "p|period=", "sampling period of the GPX file", v => samplingPeriod = int.Parse(v) }, { "f|filter", "enables output post processing", v => filter = v != null }, { "h|?|help", v => showHelp = v != null }, }; try { parameters.Parse(args); } catch (OptionException e) { Console.Write("FDI: "); Console.WriteLine(e.Message); Console.WriteLine("Try `fdi --help' for more information."); return; } if (showHelp || string.IsNullOrEmpty(osmPath) || string.IsNullOrEmpty(gpxPath) || string.IsNullOrEmpty(xmlPath) || string.IsNullOrEmpty(outputPath)) { ShowHelp(parameters); return; } if (outputPath[outputPath.Length - 1] == '"') { outputPath = outputPath.Substring(0, outputPath.Length - 1); } Console.Write("Loading OSM file ..."); OSMDB map = new OSMDB(); map.Load(osmPath); Console.WriteLine("\t\t\tDone."); Console.Write("Building routable road graph ..."); RoadGraph graph = new RoadGraph(); graph.Build(map); Console.WriteLine("\tDone."); TMM processor = new TMM(graph) { _db = map }; PathReconstructer reconstructor = new PathReconstructer(graph) { _db = map }; XMLDocument xml = new XMLDocument(); xml.Load(xmlPath); var buckets = xml.Buckets; // Process single file if (File.Exists(gpxPath)) { List <GPXTrack> result = new List <GPXTrack>(); result.AddRange(getAllGpxTrackList(gpxPath)); ProcessGPXFile(gpxPath, processor, reconstructor, outputPath, samplingPeriod, filter, buckets); GenerateOsmFiles(buckets, reconstructor, map, result); GenerateGpxFiles(buckets, gpxPath, 0); } // Process all GPX in directory else if (Directory.Exists(gpxPath)) { var files = Directory.GetFiles(gpxPath, "*.gpx"); List <GPXTrack> result = new List <GPXTrack>(); Console.WriteLine("Found {0} GPX file(s).", files.Length); for (int i = 0; i < files.Length; i++) { ProcessGPXFile(files[i], processor, reconstructor, outputPath, samplingPeriod, filter, buckets); GenerateGpxFiles(buckets, gpxPath, i); result.AddRange(getAllGpxTrackList(files[i])); Console.WriteLine("NEW FILE BEING PROCESSED"); } GenerateOsmFiles(buckets, reconstructor, map, result); } else { Console.WriteLine("No GPX files found"); } Console.WriteLine("\tDone."); Console.WriteLine("\tSpan=" + (DateTime.Now - span)); }
static void GenerateOsmFiles(List <Bucket> buckets, PathReconstructer reconstructor, OSMDB map, List <GPXTrack> gpxTrackList) { foreach (var b in buckets) { if (b.Paths.Any()) { var mapCopy = ObjectCopier.Clone <OSMDB>(map); List <Polyline <IPointGeo> > pathList = new List <Polyline <IPointGeo> >(); OSMNode bucketInfo = new OSMNode(0, 0, 0); OSMTag start = new OSMTag("start", b.Start.ToString()); OSMTag end = new OSMTag("end", b.End.ToString()); bucketInfo.Tags.Add(start); bucketInfo.Tags.Add(end); foreach (var p in b.Paths) { var uniquePath = p.Value.GroupBy(x => new { x.Id }).Select(x => x.First()); foreach (var seg in uniquePath) { if (seg.Id != 0) { var matchingWay = mapCopy.Ways[seg.Id]; var avgSpeed = getAverageSpeed(p.Key, gpxTrackList); if (avgSpeed != null) { if (matchingWay.Tags.ContainsTag("avgSpeed")) { matchingWay.Tags["avgSpeed"].Value = avgSpeed; } else { matchingWay.Tags.Add(new OSMTag("avgSpeed", avgSpeed)); } } if (matchingWay.Tags.ContainsTag("traffic")) { matchingWay.Tags["traffic"].Value += "," + p.Key; } else { matchingWay.Tags.Add(new OSMTag("traffic", p.Key)); } } } pathList.AddRange(uniquePath); } //OSMDB resultMap = reconstructor.SaveToOSM(pathList); //resultMap.Save("map" + b.Name + ".osm"); mapCopy.Nodes.Add(bucketInfo); mapCopy.Save("map" + b.Name + ".osm"); } } }
static void Main(string[] args) { string dbPath = ""; string mapPath = ""; string trackPath = ""; string outputPath = "."; bool addTracks = false; bool showHelp = false; bool analyze = false; OptionSet parameters = new OptionSet() { { "db=", "path to the travel times database", v => dbPath = v }, { "add", "adds specified tracks to the DB", v => addTracks = v != null }, { "track=", "path to the matched GPS track to process or to the directory to process", v => trackPath = v }, { "map=", "path to the routable map", v => mapPath = v }, { "a|analyze", v => analyze = v != null }, { "o|output=", "path to the output directory", v => outputPath = v }, { "h|?|help", v => showHelp = v != null }, }; try { parameters.Parse(args); } catch (OptionException e) { Console.Write("Analyzer: "); Console.WriteLine(e.Message); Console.WriteLine("Try `analyzer --help' for more information."); return; } if (showHelp || string.IsNullOrEmpty(dbPath) || string.IsNullOrEmpty(outputPath)) { ShowHelp(parameters); return; } Console.Write("Loading travel times database ..."); XmlTravelTimeDB db = new XmlTravelTimeDB(); if (File.Exists(dbPath)) { db.Load(dbPath); } Console.WriteLine("\t\t\tDone."); if (addTracks) { if (File.Exists(trackPath)) { AddTrackToDB(db, trackPath); } else if (Directory.Exists(trackPath)) { var files = Directory.GetFiles(trackPath, "*.osm"); Console.WriteLine("Found {0} GPX file(s).", files.Length); foreach (var file in files) { AddTrackToDB(db, file); } } Console.Write("Saving travel times database ..."); db.Save(dbPath); Console.WriteLine("\t\t\tDone."); } if (analyze) { Console.Write("Loading routable map ..."); OSMDB map = new OSMDB(); map.Load(mapPath); Console.WriteLine("\t\t\t\tDone."); IModelsRepository modelsRepository = new XmlModelsRepository(outputPath); TTAnalyzer analyzer = new TTAnalyzer(map); foreach (var segment in db.TravelTimesSegments) { Model m = analyzer.Analyze(db.GetTravelTimes(segment), segment); if (m != null) { modelsRepository.AddModel(m); } } Console.Write("Saving models ..."); modelsRepository.Commit(); } }
/// <summary> /// Creates a list of travel times from the matched track /// </summary> /// <param name="track"></param> /// <returns></returns> public static IEnumerable <TravelTime> FromMatchedTrack(OSMDB track) { List <TravelTime> result = new List <TravelTime>(); var orderedWays = track.Ways.OrderBy(way => int.Parse(way.Tags["order"].Value)).ToList(); //Find start of the first segment int index = 0; while (index < orderedWays.Count && track.Nodes[orderedWays[index].Nodes[0]].Tags.ContainsTag("crossroad") == false) { index++; } while (index < orderedWays.Count) { int startNodeId = int.Parse(track.Nodes[orderedWays[index].Nodes[0]].Tags["node-id"].Value); DateTime segmentStartTime = DateTime.MinValue; if (track.Nodes[orderedWays[index].Nodes[0]].Tags.ContainsTag("time")) { segmentStartTime = DateTime.Parse(track.Nodes[orderedWays[index].Nodes[0]].Tags["time"].Value); } else { segmentStartTime = InterpolateStartTime(track, orderedWays, index); } List <GPXPoint> points = new List <GPXPoint>(); points.Add(new GPXPoint(track.Nodes[orderedWays[index].Nodes[0]].Latitude, track.Nodes[orderedWays[index].Nodes[0]].Longitude, segmentStartTime)); while (index < orderedWays.Count && track.Nodes[orderedWays[index].Nodes.Last()].Tags.ContainsTag("crossroad") == false) { if (track.Nodes[orderedWays[index].Nodes.Last()].Tags.ContainsTag("time")) { points.Add(new GPXPoint(track.Nodes[orderedWays[index].Nodes.Last()].Latitude, track.Nodes[orderedWays[index].Nodes.Last()].Longitude, DateTime.Parse(track.Nodes[orderedWays[index].Nodes.Last()].Tags["time"].Value))); } index++; } if (index < orderedWays.Count) { int endNodeId = int.Parse(track.Nodes[orderedWays[index].Nodes.Last()].Tags["node-id"].Value); DateTime segmentEndTime = DateTime.MinValue; if (track.Nodes[orderedWays[index].Nodes.Last()].Tags.ContainsTag("time")) { segmentEndTime = DateTime.Parse(track.Nodes[orderedWays[index].Nodes.Last()].Tags["time"].Value); } else { segmentEndTime = InterpolateEndTime(track, orderedWays, index); } points.Add(new GPXPoint(track.Nodes[orderedWays[index].Nodes.Last()].Latitude, track.Nodes[orderedWays[index].Nodes.Last()].Longitude, segmentEndTime)); int wayId = int.Parse(orderedWays[index].Tags["way-id"].Value); SegmentInfo segment = new SegmentInfo() { NodeFromID = startNodeId, NodeToID = endNodeId, WayID = wayId }; List <double> avgSpeeds = new List <double>(); for (int i = 0; i < points.Count - 1; i++) { avgSpeeds.Add(Calculations.GetDistance2D(points[i], points[i + 1]) / (points[i + 1].Time - points[i].Time).TotalSeconds); } TravelTime tt = new TravelTime(segment, segmentStartTime, segmentEndTime); int ii = 0; while (ii < avgSpeeds.Count) { if (avgSpeeds[ii] < 1.0) { Stop stop = new Stop() { From = points[ii].Time }; while (ii < avgSpeeds.Count && avgSpeeds[ii] < 1.0) { ii++; } stop.To = points[ii].Time; tt.Stops.Add(stop); } ii++; } result.Add(tt); index++; } } return(result); }
/// <summary> /// Builds road graph from map data /// </summary> /// <param name="map">OSMDB with preprocessed map data from OSM2Routing utility</param> public void Build(OSMDB map) { Dictionary <long, Node> usedNodes = new Dictionary <long, Node>(); foreach (var segment in map.Ways) { Node start = GetOrCreateNode(segment.Nodes[0], usedNodes); try { start.MapPoint = map.Nodes[segment.Nodes[0]]; } catch (ArgumentException) { continue; // If the start node was not found in the database, skip this path completely } Node end = GetOrCreateNode(segment.Nodes[segment.Nodes.Count - 1], usedNodes); try { end.MapPoint = map.Nodes[segment.Nodes[segment.Nodes.Count - 1]]; } catch (ArgumentException) { continue; // If the end node was not found in the database, skip this path completely } double speed = double.Parse(segment.Tags["speed"].Value, System.Globalization.CultureInfo.InvariantCulture); int wayId = int.Parse(segment.Tags["way-id"].Value, System.Globalization.CultureInfo.InvariantCulture); ConnectionGeometry geometry = new ConnectionGeometry(); geometry.WayID = wayId; foreach (var n in segment.Nodes) { try { OSMNode mapPoint = map.Nodes[n]; geometry.Nodes.Add(mapPoint); //geometry.Nodes.Add(new PointGeo(mapPoint.Latitude, mapPoint.Longitude)); } catch (ArgumentException) { continue; // If an intermediate node was not found in the database, skip just that node } } _connectionGeometries.Add(geometry); if (segment.Tags["accessible"].Value == "yes") { Connection sc = new Connection(start, end) { Speed = speed, Geometry = geometry }; geometry.Connections.Add(sc); _connections.Add(sc); } if (segment.Tags["accessible-reverse"].Value == "yes") { Connection sc = new Connection(end, start) { Speed = speed, Geometry = geometry }; geometry.Connections.Add(sc); _connections.Add(sc); } } }
/// <summary> /// Splits ways at road crossings, check for oneway roads and save results in OSMDB /// </summary> /// <returns>OSMDB object with road segments and used nodes</returns> public OSMDB BuildRoutableOSM() { OSMDB result = new OSMDB(); int counter = -1; foreach (OSMRoad route in _storage.Ways) { OSMWay segment = new OSMWay(counter--); OSMTag wayIDTag = new OSMTag("way-id", route.ID.ToString()); OSMTag speedTag = new OSMTag("speed", route.Speed.ToString()); string wayAccessibility = route.IsAccessible() ? "yes" : "no"; OSMTag wayAccessibilityTag = new OSMTag("accessible", wayAccessibility); string wayAccessibilityReverse = route.IsAccessibleReverse() ? "yes" : "no"; OSMTag wayAccessibilityReverseTag = new OSMTag("accessible-reverse", wayAccessibilityReverse); for (int i = 0; i < route.Nodes.Count; i++) { segment.Nodes.Add(route.Nodes[i]); if ((UsedNodes[route.Nodes[i]].Count > 1) && (i > 0) && (i < (route.Nodes.Count - 1))) { segment.Tags.Add(wayIDTag); segment.Tags.Add(speedTag); segment.Tags.Add(wayAccessibilityTag); segment.Tags.Add(wayAccessibilityReverseTag); result.Ways.Add(segment); segment = new OSMWay(counter--); segment.Nodes.Add(route.Nodes[i]); } } segment.Tags.Add(wayIDTag); segment.Tags.Add(speedTag); segment.Tags.Add(wayAccessibilityTag); segment.Tags.Add(wayAccessibilityReverseTag); result.Ways.Add(segment); } foreach (OSMNode node in _storage.Nodes) { OSMNode newNode = new OSMNode(node.ID, node.Latitude, node.Longitude); // preserve junction and highway tags on nodes if (node.Tags.ContainsTag("junction")) { newNode.Tags.Add(node.Tags["junction"]); } if (node.Tags.ContainsTag("highway")) { newNode.Tags.Add(node.Tags["highway"]); } if (_usedNodes[node.ID].Count > 1) { newNode.Tags.Add(new OSMTag("crossroad", "yes")); } result.Nodes.Add(newNode); } return(result); }