/// <summary> /// /// </summary> /// <param name="from"></param> /// <param name="to"></param> /// <returns></returns> public static double GetDistance(this LngLatPoint from, LngLatPoint to) { var sCoord = new GeoCoordinate(from.Lat, from.Lng); var eCoord = new GeoCoordinate(to.Lat, to.Lng); return(sCoord.GetDistanceTo(eCoord)); }
public static double[] ToDblArr(this LngLatPoint lngLatPoint) { return(new[] { lngLatPoint.Lng, lngLatPoint.Lat }); }
/// <summary> /// /// </summary> /// <param name="path"></param> /// <param name="locations"></param> /// <returns></returns> private static Tuple <IEnumerable <Activity>, List <RoutePoint> > CalculateActivitiesAndWpCoords(RouteResponsePath path, IReadOnlyList <Location> locations) { var activities = new List <Activity>(); var points = path.Points; var snappedPts = path.SnappedWaypoints; var times = path.Details.Times; var wpCoords = new List <RoutePoint>(); Func <Location, ResponseCoordinatesArray, int, Tuple <int, LngLatPoint> > findClosest = (loc, coords, skpIdx) => { try { var lc = coords .Skip(skpIdx) .OrderBy(p => loc.ToLngLatPoint() .GetDistance(new LngLatPoint() { Lng = p[0] ?? 0, Lat = p[1] ?? 0 })) .FirstOrDefault(); var idx = coords.FindIndex(p => p.Equals(lc)); return(new Tuple <int, LngLatPoint>(idx, new LngLatPoint() { Lng = lc[0] ?? 0, Lat = lc[1] ?? 0 })); } catch (Exception e) { Console.WriteLine(e); throw; } }; Func <int, int, ResponseCoordinatesArray, Tuple <double, long, RoutePoint> > computeTotTimeAndDistance = (frmIdx, toIdx, coords) => { try { var src = coords.Skip(frmIdx).Take(toIdx - frmIdx).ToArray(); var dist = 0.0; var wps = new RoutePoint(); for (var i = 0; i < src.Count(); i++) { var ths = src[i]; wps.Coordinates.Add(new[] { ths[0] ?? 0.0, ths[1] ?? 0.0 }); if (i == 0) { continue; } var prv = src[i - 1]; // compute for the distance var srcPt = new LngLatPoint(prv[0], prv[1]); var dstPt = new LngLatPoint(ths[0], ths[1]); dist += srcPt.GetDistance(dstPt); } // compute total travel time var tmSrc = times.Where(p => p[0] >= frmIdx && p[1] < toIdx); var totSecs = tmSrc.Sum(s => s[2]); return(new Tuple <double, long, RoutePoint>(dist, totSecs ?? 0, wps)); } catch (Exception e) { Console.WriteLine(e); throw; } }; Tuple <int, LngLatPoint> lstClosest = null; for (var i = 0; i < locations.Count; i++) { try { var loc = locations[i]; if (i == 0) { activities.Add(new Activity(Activity.TypeEnum.Start, loc.LocationId, loc.LocationId)); } else { var closest = findClosest(loc, points.Coordinates, lstClosest?.Item1 ?? 0); var tupDistTimeCoords = computeTotTimeAndDistance(lstClosest?.Item1 ?? 0, closest.Item1, points.Coordinates); var type = (i == (locations.Count - 1)) ? Activity.TypeEnum.End : Activity.TypeEnum.Service; activities.Add(new Activity(id: loc.LocationId, type: type, locationId: loc.LocationId, arrTime: tupDistTimeCoords.Item2 / 1000, drivingTime: tupDistTimeCoords.Item2 / 1000, endTime: tupDistTimeCoords.Item2 / 1000, waitingTime: 0, distance: tupDistTimeCoords.Item1)); wpCoords.Add(tupDistTimeCoords.Item3); lstClosest = closest; } } catch (Exception e) { Console.WriteLine(e); throw; } } return(new Tuple <IEnumerable <Activity>, List <RoutePoint> >(activities, wpCoords)); }