From add9eb5c4c537f7365a652a12ced7ced7a175560 Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Sat, 17 Feb 2018 21:08:26 +0800 Subject: [PATCH 01/37] refactor --- .../Topology/DijkstraRouter.cs | 19 ++++++--------- .../Topology/IGraphRouter.cs | 11 +-------- .../Topology/UbodtRouter.cs | 23 +++++++++++++++++++ 3 files changed, 31 insertions(+), 22 deletions(-) create mode 100644 src/Sandwych.MapMatchingKit/Topology/UbodtRouter.cs diff --git a/src/Sandwych.MapMatchingKit/Topology/DijkstraRouter.cs b/src/Sandwych.MapMatchingKit/Topology/DijkstraRouter.cs index bc6349a..cd56377 100644 --- a/src/Sandwych.MapMatchingKit/Topology/DijkstraRouter.cs +++ b/src/Sandwych.MapMatchingKit/Topology/DijkstraRouter.cs @@ -23,7 +23,7 @@ public class DijkstraRouter : IGraphRouter /// /// Route mark representation. /// - private class Mark : IComparable + private sealed class Mark : IComparable { public TEdge MarkedEdge { get; } public TEdge PredecessorEdge { get; } @@ -81,20 +81,15 @@ public IDictionary> Route(P source, IEnumerable

targets } public IDictionary> Route(P source, IEnumerable

targets, Func cost, - Func bound, double max) + Func bound = null, double max = double.NaN) { return Ssmt(source, targets, cost, bound, max); } - public IDictionary)> Route(IEnumerable

sources, IEnumerable

targets, Func cost) - { - return msmt(sources, targets, cost, null, double.NaN); - } - public IDictionary)> Route(IEnumerable

sources, IEnumerable

targets, Func cost, Func bound, double max) { - return msmt(sources, targets, cost, bound, max); + return Msmt(sources, targets, cost, bound, max); } private IEnumerable Ssst(P source, P target, Func cost, Func bound, double max) @@ -105,8 +100,8 @@ private IEnumerable Ssst(P source, P target, Func cost, Fu private IDictionary> Ssmt(P source, IEnumerable

targets, Func cost, Func bound, double max = double.NaN) { - var sources = new P[] { source }; - var map = msmt(sources, targets, cost, bound, max); + var sources = new P[1] { source }; + var map = Msmt(sources, targets, cost, bound, max); var result = new Dictionary>(map.Count); foreach (var entry in map) { @@ -115,7 +110,7 @@ private IDictionary> Ssmt(P source, IEnumerable

targets return result; } - private IDictionary)> msmt(IEnumerable

sources, IEnumerable

targets, Func cost, + private IDictionary)> Msmt(IEnumerable

sources, IEnumerable

targets, Func cost, Func bound, double max) { /* @@ -129,6 +124,7 @@ private IDictionary> Ssmt(P source, IEnumerable

targets this.Logger.LogDebug("initialize target {0} with edge {1} and fraction {2}", target, target.Edge.Id, target.Fraction); } + if (!targetEdges.ContainsKey(target.Edge)) { targetEdges[target.Edge] = new HashSet

() { target }; @@ -179,7 +175,6 @@ private IDictionary> Ssmt(P source, IEnumerable

targets { this.Logger.LogDebug("reached target {0} with start edge {1} from {2} to {3} with {4} cost", target, source.Edge.Id, source.Fraction, target.Fraction, reachcost); - } var reach = new Mark(source.Edge, null, reachcost, reachbound); diff --git a/src/Sandwych.MapMatchingKit/Topology/IGraphRouter.cs b/src/Sandwych.MapMatchingKit/Topology/IGraphRouter.cs index b7a35db..4ebf265 100644 --- a/src/Sandwych.MapMatchingKit/Topology/IGraphRouter.cs +++ b/src/Sandwych.MapMatchingKit/Topology/IGraphRouter.cs @@ -10,19 +10,10 @@ public interface IGraphRouter where P : IEdgePoint { - IEnumerable Route(P source, P target, Func cost); - - IEnumerable Route(P source, P target, Func cost, Func bound, double max); - - IDictionary> Route(P source, IEnumerable

targets, Func cost); - IDictionary> Route(P source, IEnumerable

targets, Func cost, - Func bound, double max); + Func bound = null, double max = double.NaN); - IDictionary)> Route(IEnumerable

sources, IEnumerable

targets, Func cost); - IDictionary)> Route(IEnumerable

sources, IEnumerable

targets, Func cost, - Func bound, double max); } diff --git a/src/Sandwych.MapMatchingKit/Topology/UbodtRouter.cs b/src/Sandwych.MapMatchingKit/Topology/UbodtRouter.cs new file mode 100644 index 0000000..9e6bfdb --- /dev/null +++ b/src/Sandwych.MapMatchingKit/Topology/UbodtRouter.cs @@ -0,0 +1,23 @@ +using System; +using System.Collections.Generic; +using System.Text; +using Microsoft.Extensions.Logging; +using Sandwych.MapMatchingKit.Roads; +using Sandwych.MapMatchingKit.Utility; + +namespace Sandwych.MapMatchingKit.Topology +{ + public class UbodtRouter : IGraphRouter + where TEdge : class, IGraphEdge + where P : IEdgePoint + { + public ILogger Logger { get; set; } = NullLogger.Instance; + + public IDictionary> Route(P source, IEnumerable

targets, Func cost, Func bound = null, double max = double.NaN) + { + throw new NotImplementedException(); + } + + } + +} From b8312d664fa7ac9cb2a5ec081ca67720e82e7279 Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Thu, 22 Feb 2018 02:38:57 +0800 Subject: [PATCH 02/37] refactor Router's unit tests --- Sandwych.MapMatchingKit.sln | 5 +- .../Topology/IGraphRouter.cs | 2 + .../Topology/UbodtRouter.cs | 324 ++++++++++++++- .../Topology/AbstractRouterTest.cs | 204 ++++++++++ .../Topology/DijkstraRouterTest.cs | 379 +----------------- .../Topology/Models.cs | 43 ++ .../Topology/UbodtRouterTest.cs | 12 + 7 files changed, 590 insertions(+), 379 deletions(-) create mode 100644 test/Sandwych.MapMatchingKit.Tests/Topology/AbstractRouterTest.cs create mode 100644 test/Sandwych.MapMatchingKit.Tests/Topology/Models.cs create mode 100644 test/Sandwych.MapMatchingKit.Tests/Topology/UbodtRouterTest.cs diff --git a/Sandwych.MapMatchingKit.sln b/Sandwych.MapMatchingKit.sln index fb455f6..657084f 100644 --- a/Sandwych.MapMatchingKit.sln +++ b/Sandwych.MapMatchingKit.sln @@ -1,7 +1,7 @@  Microsoft Visual Studio Solution File, Format Version 12.00 # Visual Studio 15 -VisualStudioVersion = 15.0.27130.2026 +VisualStudioVersion = 15.0.27130.2036 MinimumVisualStudioVersion = 10.0.40219.1 Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Sandwych.Hmm", "src\Sandwych.Hmm\Sandwych.Hmm.csproj", "{13A3865C-37AB-49B6-9687-CA285DF2EB04}" EndProject @@ -18,6 +18,9 @@ EndProject Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Sandwych.MapMatchingKit.Examples.HelloWorldApp", "examples\Sandwych.MapMatchingKit.Examples.HelloWorldApp\Sandwych.MapMatchingKit.Examples.HelloWorldApp.csproj", "{2CCF3F1B-FFF3-4153-952D-4564BEB4C11A}" EndProject Global + GlobalSection(Performance) = preSolution + HasPerformanceSessions = true + EndGlobalSection GlobalSection(SolutionConfigurationPlatforms) = preSolution Debug|Any CPU = Debug|Any CPU Release|Any CPU = Release|Any CPU diff --git a/src/Sandwych.MapMatchingKit/Topology/IGraphRouter.cs b/src/Sandwych.MapMatchingKit/Topology/IGraphRouter.cs index 4ebf265..a2cd6e3 100644 --- a/src/Sandwych.MapMatchingKit/Topology/IGraphRouter.cs +++ b/src/Sandwych.MapMatchingKit/Topology/IGraphRouter.cs @@ -14,6 +14,8 @@ IDictionary> Route(P source, IEnumerable

targets, Func< Func bound = null, double max = double.NaN); + IDictionary)> Route(IEnumerable

sources, IEnumerable

targets, Func cost, + Func bound = null, double max = double.NaN); } diff --git a/src/Sandwych.MapMatchingKit/Topology/UbodtRouter.cs b/src/Sandwych.MapMatchingKit/Topology/UbodtRouter.cs index 9e6bfdb..7d73444 100644 --- a/src/Sandwych.MapMatchingKit/Topology/UbodtRouter.cs +++ b/src/Sandwych.MapMatchingKit/Topology/UbodtRouter.cs @@ -12,10 +12,330 @@ public class UbodtRouter : IGraphRouter where P : IEdgePoint { public ILogger Logger { get; set; } = NullLogger.Instance; + ///

+ /// Route mark representation. + /// + private sealed class Mark : IComparable + { + public TEdge MarkedEdge { get; } + public TEdge PredecessorEdge { get; } + public double Cost { get; } + public double BoundingCost { get; } + + /// + /// Constructor of an entry. + /// + /// {@link AbstractEdge} defining the route mark. + /// Predecessor {@link AbstractEdge}. + /// Cost value to this route mark. + /// Bounding cost value to this route mark. + public Mark(TEdge markedEdge, TEdge predecessorEdge, Double cost, Double boundingCost) + { + this.MarkedEdge = markedEdge; + this.PredecessorEdge = predecessorEdge; + this.Cost = cost; + this.BoundingCost = boundingCost; + } + + public int CompareTo(Mark other) + { + if (this.Cost < other.Cost) + { + return -1; + } + else if (this.Cost > other.Cost) + { + return 1; + } + else + { + return 0; + } + } + + public override int GetHashCode() => + (this.MarkedEdge, this.PredecessorEdge, this.Cost, this.BoundingCost).GetHashCode(); + } + + public IEnumerable Route(P source, P target, Func cost) + { + return Ssst(source, target, cost, null, double.NaN); + } + + public IEnumerable Route(P source, P target, Func cost, Func bound, double max) + { + return Ssst(source, target, cost, bound, max); + } + + public IDictionary> Route(P source, IEnumerable

targets, Func cost) + { + return Ssmt(source, targets, cost, null, double.NaN); + } + + public IDictionary> Route(P source, IEnumerable

targets, Func cost, + Func bound = null, double max = double.NaN) + { + return Ssmt(source, targets, cost, bound, max); + } + + public IDictionary)> Route(IEnumerable

sources, IEnumerable

targets, Func cost, + Func bound, double max) + { + return Msmt(sources, targets, cost, bound, max); + } + + private IEnumerable Ssst(P source, P target, Func cost, Func bound, double max) + { + var targets = new P[] { target }; + return Ssmt(source, targets, cost, bound, max)[target]; + } + + private IDictionary> Ssmt(P source, IEnumerable

targets, Func cost, Func bound, double max = double.NaN) + { + var sources = new P[1] { source }; + var map = Msmt(sources, targets, cost, bound, max); + var result = new Dictionary>(map.Count); + foreach (var entry in map) + { + result[entry.Key] = entry.Value.Item2; + } + return result; + } - public IDictionary> Route(P source, IEnumerable

targets, Func cost, Func bound = null, double max = double.NaN) + private IDictionary)> Msmt(IEnumerable

sources, IEnumerable

targets, Func cost, + Func bound, double max) { - throw new NotImplementedException(); + /* + * Initialize map of edges to target points. + */ + var targetEdges = new Dictionary>(); + foreach (var target in targets) + { + if (this.Logger.IsEnabled(LogLevel.Debug)) + { + this.Logger.LogDebug("initialize target {0} with edge {1} and fraction {2}", + target, target.Edge.Id, target.Fraction); + } + + if (!targetEdges.ContainsKey(target.Edge)) + { + targetEdges[target.Edge] = new HashSet

() { target }; + } + else + { + targetEdges[target.Edge].Add(target); + } + } + + /* + * Setup data structures + */ + var priorities = new PriorityQueue(); + var entries = new Dictionary(); + var finishs = new Dictionary(); + var reaches = new Dictionary(); + var starts = new Dictionary(); + + /* + * Initialize map of edges with start points + */ + foreach (var source in sources) + { + // initialize sources as start edges + var startcost = source.Edge.Cost(1.0 - source.Fraction, cost); //cost.cost(source.Edge, 1 - source.Fraction); + var startbound = bound != null ? source.Edge.Cost(1.0 - source.Fraction, bound) : 0D; //bound.cost(source.Edge.Cost(), 1 - source.Fraction) : 0.0; + + if (this.Logger.IsEnabled(LogLevel.Debug)) + { + this.Logger.LogDebug("init source {0} with start edge {1} and fraction {2} with {3} cost", + source, source.Edge.Id, source.Fraction, startcost); + } + + if (targetEdges.TryGetValue(source.Edge, out var targetsMap)) + { + // start edge reaches target edge + foreach (var target in targetsMap) + { + if (target.Fraction < source.Fraction) + { + continue; + } + var reachcost = startcost - source.Edge.Cost(1.0 - target.Fraction, cost); // cost.cost(source.Edge, 1 - target.Fraction); + var reachbound = bound != null ? startcost - source.Edge.Cost(1.0 - target.Fraction, bound) : 0D; //, // bound.cost(source.Edge, 1 - target.Fraction) : 0.0; + + if (this.Logger.IsEnabled(LogLevel.Debug)) + { + this.Logger.LogDebug("reached target {0} with start edge {1} from {2} to {3} with {4} cost", + target, source.Edge.Id, source.Fraction, target.Fraction, reachcost); + } + + var reach = new Mark(source.Edge, null, reachcost, reachbound); + reaches.Add(reach, target); + starts.Add(reach, source); + priorities.Enqueue(reach); + } + } + + if (!entries.TryGetValue(source.Edge, out var start)) + { + if (this.Logger.IsEnabled(LogLevel.Debug)) + { + this.Logger.LogDebug("add source {0} with start edge {1} and fraction {2} with {3} cost", + source, source.Edge.Id, source.Fraction, startcost); + } + start = new Mark(source.Edge, null, startcost, startbound); + entries[source.Edge] = start; + starts[start] = source; + priorities.Enqueue(start); + } + else + { + if (startcost < start.Cost) + { + if (this.Logger.IsEnabled(LogLevel.Debug)) + { + this.Logger.LogDebug("update source {0} with start edge {1} and fraction {2} with {3} cost", + source, source.Edge.Id, source.Fraction, startcost); + } + start = new Mark(source.Edge, null, startcost, startbound); + entries[source.Edge] = start; + starts[start] = source; + priorities.Remove(start); + priorities.Enqueue(start); + } + } + } + + /* + * Dijkstra algorithm. + */ + while (priorities.Count > 0) + { + var current = priorities.Dequeue(); + + if (targetEdges.Count == 0) + { + if (this.Logger.IsEnabled(LogLevel.Debug)) + { + this.Logger.LogDebug("finshed all targets"); + } + break; + } + + if (!double.IsNaN(max) && current.BoundingCost > max) + { + if (this.Logger.IsEnabled(LogLevel.Debug)) + { + this.Logger.LogDebug("reached maximum bound"); + } + continue; + } + + /* + * Finish target if reached. + */ + { + if (reaches.TryGetValue(current, out var target)) + { + if (finishs.ContainsKey(target)) + { + continue; + } + else + { + if (this.Logger.IsEnabled(LogLevel.Debug)) + { + this.Logger.LogDebug("finished target {0} with edge {1} and fraction {2} with {3} cost", + target, current.MarkedEdge, target.Fraction, current.Cost); + } + + finishs[target] = current; + + var edges = targetEdges[current.MarkedEdge]; + edges.Remove(target); + + if (edges.Count == 0) + { + targetEdges.Remove(current.MarkedEdge); + } + continue; + } + } + } + + if (this.Logger.IsEnabled(LogLevel.Debug)) + { + this.Logger.LogDebug("succeed edge {0} with {1} cost", current.MarkedEdge.Id, current.Cost); + } + + var successors = current.MarkedEdge.Successors; + + foreach (var successor in successors) + { + var succcost = current.Cost + cost(successor); + var succbound = bound != null ? current.BoundingCost + bound(successor) : 0.0; + + if (targetEdges.ContainsKey(successor)) + { + // reach target edge + foreach (var targetEdge in targetEdges[successor]) + { + var reachcost = succcost - successor.Cost(1.0 - targetEdge.Fraction, cost); + var reachbound = bound != null ? succbound - successor.Cost(1.0 - targetEdge.Fraction, bound) : 0.0; /// bound(successor, 1 - target.Fraction) : 0.0; + if (this.Logger.IsEnabled(LogLevel.Debug)) + { + this.Logger.LogDebug("reached target {0} with successor edge {1} and fraction {2} with {3} cost", + targetEdge, successor.Id, targetEdge.Fraction, reachcost); + } + + var reach = new Mark(successor, current.MarkedEdge, reachcost, reachbound); + reaches.Add(reach, targetEdge); + priorities.Enqueue(reach); + } + } + + if (!entries.ContainsKey(successor)) + { + if (this.Logger.IsEnabled(LogLevel.Debug)) + { + this.Logger.LogDebug("added successor edge {0} with {1} cost", successor.Id, succcost); + } + Mark mark = new Mark(successor, current.MarkedEdge, succcost, succbound); + entries.Add(successor, mark); + priorities.Enqueue(mark); + } + } + } + + var paths = new Dictionary)>(); + + foreach (P targetPoint in targets) + { + if (finishs.ContainsKey(targetPoint)) + { + var path = new List(); + var iterator = finishs[targetPoint]; + Mark start = null; + while (iterator != null) + { + path.Add(iterator.MarkedEdge); + start = iterator; + iterator = iterator.PredecessorEdge != null ? entries.GetOrNull(iterator.PredecessorEdge) : null; + } + path.Reverse(); + var tp = (starts[start], path); + paths.Add(targetPoint, tp); + } + } + + /* + entries.Clear(); + finishs.Clear(); + reaches.Clear(); + priorities.Clear(); + */ + + return paths; } } diff --git a/test/Sandwych.MapMatchingKit.Tests/Topology/AbstractRouterTest.cs b/test/Sandwych.MapMatchingKit.Tests/Topology/AbstractRouterTest.cs new file mode 100644 index 0000000..82b8496 --- /dev/null +++ b/test/Sandwych.MapMatchingKit.Tests/Topology/AbstractRouterTest.cs @@ -0,0 +1,204 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using Xunit; +using Sandwych.MapMatchingKit.Topology; + +namespace Sandwych.MapMatchingKit.Tests.Topology +{ + public abstract class AbstractRouterTest : TestBase + { + protected abstract IGraphRouter CreateRouter(); + + protected void AssertSinglePath(IEnumerable expectedPath, IEnumerable sources, IEnumerable targets) + { + var router = this.CreateRouter(); + var routes = router.Route(sources, targets, e => e.Weight, null, double.NaN); + var route = routes[targets.First()]; + + Assert.Equal(expectedPath.First(), route.Item1.Edge.Id); + Assert.Equal(expectedPath, route.Item2.Select(r => r.Id)); + } + + protected void AssertMultiplePaths(IReadOnlyDictionary> expectedPaths, + IEnumerable sources, IEnumerable targets, + Func bound = null, double max = double.NaN) + { + var router = this.CreateRouter(); + var routes = router.Route(sources, targets, e => e.Weight, bound, max); + + Assert.Equal(expectedPaths.Count(), routes.Count()); + + foreach (var pair in routes) + { + var route = pair.Value.Item2; + var expectedPath = expectedPaths[pair.Key.Edge.Id]; + + Assert.NotNull(route); + Assert.Equal(expectedPath.First(), pair.Value.Item1.Edge.Id); + Assert.Equal(expectedPath.Count(), route.Count()); + Assert.Equal(expectedPath, route.Select(r => r.Id)); + } + } + + + [Fact] + public void TestSameRoad() + { + var roads = new Road[] { + new Road(0, 0, 1, 100), + new Road(1, 1, 0, 20), + new Road(2, 0, 2, 100), + new Road(3, 1, 2, 100), + new Road(4, 1, 3, 100) + }; + var map = new Graph(roads); + + AssertSinglePath( + expectedPath: new long[] { 0L }, + sources: new RoadPoint[] { new RoadPoint(map.Edges[0L], 0.3) }, + targets: new RoadPoint[] { new RoadPoint(map.Edges[0L], 0.3) }); + + AssertSinglePath( + expectedPath: new long[] { 0L }, + sources: new RoadPoint[] { new RoadPoint(map.Edges[0L], 0.3) }, + targets: new RoadPoint[] { new RoadPoint(map.Edges[0L], 0.7) }); + + AssertSinglePath( + expectedPath: new long[] { 0L, 1L, 0L }, + sources: new RoadPoint[] { new RoadPoint(map.Edges[0L], 0.7) }, + targets: new RoadPoint[] { new RoadPoint(map.Edges[0L], 0.3) }); + + AssertSinglePath( + expectedPath: new long[] { 1L, 0L }, + sources: new RoadPoint[] { new RoadPoint(map.Edges[0], 0.8), new RoadPoint(map.Edges[1L], 0.2) }, + targets: new RoadPoint[] { new RoadPoint(map.Edges[0L], 0.7) }); + } + + [Fact] + public void TestSelfLoop() + { + var roads = new Road[] { + new Road(0, 0, 0, 100), + new Road(1, 0, 0, 100), + }; + var map = new Graph(roads); + + AssertSinglePath( + expectedPath: new long[] { 0L }, + sources: new RoadPoint[] { new RoadPoint(map.Edges[0L], 0.3) }, + targets: new RoadPoint[] { new RoadPoint(map.Edges[0L], 0.7) }); + + AssertSinglePath( + expectedPath: new long[] { 0L, 0L }, + sources: new RoadPoint[] { new RoadPoint(map.Edges[0L], 0.7) }, + targets: new RoadPoint[] { new RoadPoint(map.Edges[0L], 0.3) }); + + AssertSinglePath( + expectedPath: new long[] { 0L, 0L }, + sources: new RoadPoint[] { new RoadPoint(map.Edges[0L], 0.8), new RoadPoint(map.Edges[1L], 0.2) }, + targets: new RoadPoint[] { new RoadPoint(map.Edges[0L], 0.2) }); + + AssertSinglePath( + expectedPath: new long[] { 1L, 0L }, + sources: new RoadPoint[] { new RoadPoint(map.Edges[0L], 0.4), new RoadPoint(map.Edges[1L], 0.6) }, + targets: new RoadPoint[] { new RoadPoint(map.Edges[0L], 0.3) }); + } + + [Fact] + public void TestShortestPath() + { + var roads = new Road[] { + new Road(0, 0, 1, 100), + new Road(1, 1, 0, 100), + new Road(2, 0, 2, 160), + new Road(3, 2, 0, 160), + new Road(4, 1, 2, 50), + new Road(5, 2, 1, 50), + new Road(6, 1, 3, 200), + new Road(7, 3, 1, 200), + new Road(8, 2, 3, 100), + new Road(9, 3, 2, 100), + new Road(10, 2, 4, 40), + new Road(11, 4, 2, 40), + new Road(12, 3, 4, 100), + new Road(13, 4, 3, 100), + new Road(14, 3, 5, 200), + new Road(15, 5, 3, 200), + new Road(16, 4, 5, 60), + new Road(17, 5, 4, 60), + }; + var map = new Graph(roads); + { + // (0.7, 100) + 50 + 40 + 60 + (0.3, 200) = 280 + var paths = new Dictionary>() { + { 14L, new long[] { 0L, 4L, 8L, 14L } }, + { 15L, new long[] { 0L, 4L, 10L, 16L, 15L } }, + }; + AssertMultiplePaths( + expectedPaths: paths, + sources: new RoadPoint[] { new RoadPoint(map.Edges[0], 0.3), new RoadPoint(map.Edges[1], 0.7) }, + targets: new RoadPoint[] { new RoadPoint(map.Edges[14], 0.3), new RoadPoint(map.Edges[15], 0.7) }); + } + { + // (0.7, 100) + 50 + 100 + (0.1, 200) = 240 + var paths = new Dictionary>() { + { 14L, new long[] { 0L, 4L, 8L, 14L } }, + { 15L, new long[] { 0L, 4L, 10L, 16L, 15L } }, + }; + AssertMultiplePaths( + expectedPaths: paths, + sources: new RoadPoint[] { new RoadPoint(map.Edges[0], 0.3), new RoadPoint(map.Edges[1], 0.7) }, + targets: new RoadPoint[] { new RoadPoint(map.Edges[14], 0.1), new RoadPoint(map.Edges[15], 0.9) }); + } + + var router = new DijkstraRouter(); + { + // (0.7, 100) + 50 + 100 + (0.1, 200) = 240 + var sources = new RoadPoint[] { new RoadPoint(map.GetEdge(0), 0.3), }; + var targets = new RoadPoint[] { new RoadPoint(map.GetEdge(14), 0.1), }; + var route = router.Route(sources, targets, e => e.Weight, e => e.Weight, 200.0); + + Assert.NotNull(route); + Assert.Empty(route); + } + { + // (0.7, 100) + 50 + 100 + (0.1, 200) = 240 + // (0.7, 100) + 50 + 100 + (0.8, 200) = 380 + + var sources = new RoadPoint[] { + new RoadPoint(map.GetEdge(0), 0.3), + new RoadPoint(map.GetEdge(1), 0.7), + }; + var targets = new RoadPoint[] { + new RoadPoint(map.GetEdge(14), 0.1), + new RoadPoint(map.GetEdge(14), 0.8), + }; + var routes = router.Route(sources, targets, e => e.Weight, null, double.NaN); + var paths = new Dictionary() { + { 14L, new long[] { 0L, 4L, 8L, 14L } } + }; + + Assert.Equal(2, routes.Count()); + + foreach (var pair in routes) + { + var route = pair.Value.Item2; + var path = paths[pair.Key.Edge.Id]; + + Assert.NotNull(route); + Assert.Equal(path[0], pair.Value.Item1.Edge.Id); + Assert.Equal(path.Count(), route.Count()); + + int i = 0; + foreach (var road in route) + { + Assert.Equal((long)path[i++], road.Id); + } + } + } + } + + } +} diff --git a/test/Sandwych.MapMatchingKit.Tests/Topology/DijkstraRouterTest.cs b/test/Sandwych.MapMatchingKit.Tests/Topology/DijkstraRouterTest.cs index e132727..543a3bb 100644 --- a/test/Sandwych.MapMatchingKit.Tests/Topology/DijkstraRouterTest.cs +++ b/test/Sandwych.MapMatchingKit.Tests/Topology/DijkstraRouterTest.cs @@ -7,384 +7,11 @@ namespace Sandwych.MapMatchingKit.Tests.Topology { - public class DijkstraRouterTest + public class DijkstraRouterTest : AbstractRouterTest { - private class Road : AbstractGraphEdge - { - public float Weight { get; } - - public Road(long id, long source, long target, float weight) : base(id, source, target) - { - this.Weight = weight; - } - - public override int GetHashCode() => - (this.Id, this.Weight).GetHashCode(); - } - - private class Graph : AbstractGraph - { - public Graph(IEnumerable roads) : base(roads) - { - - } - } - - private readonly struct RoadPoint : IEdgePoint - { - public Road Edge { get; } - public double Fraction { get; } - - public RoadPoint(Road road, double fraction) - { - this.Edge = road; - this.Fraction = fraction; - } - - public override int GetHashCode() => - (this.Edge, this.Fraction).GetHashCode(); - } - - [Fact] - public void TestSameRoad() - { - var roads = new Road[] { - new Road(0, 0, 1, 100), - new Road(1, 1, 0, 20), - new Road(2, 0, 2, 100), - new Road(3, 1, 2, 100), - new Road(4, 1, 3, 100) - }; - var map = new Graph(roads); - - var router = new DijkstraRouter(); - { - var sources = new RoadPoint[] { new RoadPoint(map.Edges[0L], 0.3) }; - var targets = new RoadPoint[] { new RoadPoint(map.Edges[0L], 0.3) }; - - var routes = router.Route(sources, targets, e => e.Weight, null, double.NaN); - - var route = routes[targets.First()]; - var path = new long[] { 0L }; - - Assert.Equal(path.First(), route.Item1.Edge.Id); - Assert.Equal(path.Length, route.Item2.Count()); - - int i = 0; - foreach (var road in route.Item2) - { - Assert.Equal(path[i++], road.Id); - } - } - { - var sources = new RoadPoint[] { new RoadPoint(map.Edges[0L], 0.3) }; - var targets = new RoadPoint[] { new RoadPoint(map.Edges[0L], 0.7) }; - var routes = router.Route(sources, targets, e => e.Weight, null, double.NaN); - - var route = routes[targets.First()]; - var path = new long[] { 0L }; - - Assert.Equal(path.First(), route.Item1.Edge.Id); - Assert.Equal(path.Length, route.Item2.Count()); - - int i = 0; - foreach (var road in route.Item2) - { - Assert.Equal(path[i++], road.Id); - } - } - { - var sources = new RoadPoint[] { new RoadPoint(map.Edges[0L], 0.7) }; - var targets = new RoadPoint[] { new RoadPoint(map.Edges[0L], 0.3) }; - var routes = router.Route(sources, targets, e => e.Weight, null, double.NaN); - - var route = routes[targets.First()]; - var path = new long[] { 0L, 1L, 0L }; - - Assert.Equal(path.First(), route.Item1.Edge.Id); - Assert.Equal(path.Length, route.Item2.Count()); - - int i = 0; - foreach (var road in route.Item2) - { - Assert.Equal(path[i++], road.Id); - } - } - { - var sources = new RoadPoint[] { - new RoadPoint(map.GetEdge(0), 0.8), - new RoadPoint(map.GetEdge(1), 0.2), - }; - var targets = new RoadPoint[] { new RoadPoint(map.GetEdge(0), 0.7) }; - var routes = router.Route(sources, targets, e => e.Weight, null, double.NaN); - - var route = routes[targets.First()]; - var path = new long[] { 1L, 0L }; - - Assert.Equal(path.First(), route.Item1.Edge.Id); - Assert.Equal(path.Length, route.Item2.Count()); - - int i = 0; - foreach (var road in route.Item2) - { - Assert.Equal(path[i++], road.Id); - } - } - } - - [Fact] - public void TestSelfLoop() - { - var roads = new Road[] { - new Road(0, 0, 0, 100), - new Road(1, 0, 0, 100), - }; - var map = new Graph(roads); - var router = new DijkstraRouter(); - { - var sources = new RoadPoint[] { new RoadPoint(map.GetEdge(0), 0.3) }; - var targets = new RoadPoint[] { new RoadPoint(map.GetEdge(0), 0.7) }; - - var routes = router.Route(sources, targets, e => e.Weight, null, double.NaN); - - var route = routes[targets.First()]; - var path = new long[] { 0L }; - - Assert.Equal(path.First(), route.Item1.Edge.Id); - Assert.Equal(path.Length, route.Item2.Count()); - - int i = 0; - foreach (var road in route.Item2) - { - Assert.Equal(path[i++], road.Id); - } - } - { - var sources = new RoadPoint[] { - new RoadPoint( map.GetEdge(0), 0.7) - }; - var targets = new RoadPoint[] { - new RoadPoint(map.GetEdge(0), 0.3) - }; - - var routes = router.Route(sources, targets, e => e.Weight, null, double.NaN); - - var route = routes[targets.First()]; - var path = new long[] { 0L, 0L }; - - Assert.Equal(path.First(), route.Item1.Edge.Id); - Assert.Equal(path.Length, route.Item2.Count()); - - int i = 0; - foreach (var road in route.Item2) - { - Assert.Equal(path[i++], road.Id); - } - } - { - var sources = new RoadPoint[] { - new RoadPoint( map.GetEdge(0), 0.8), - new RoadPoint( map.GetEdge(1), 0.2), - }; - var targets = new RoadPoint[] { - new RoadPoint(map.GetEdge(0), 0.2) - }; - - var routes = router.Route(sources, targets, e => e.Weight, null, double.NaN); - - var route = routes[targets.First()]; - var path = new long[] { 0L, 0L }; - - Assert.Equal(path.First(), route.Item1.Edge.Id); - Assert.Equal(path.Length, route.Item2.Count()); - - int i = 0; - foreach (var road in route.Item2) - { - Assert.Equal(path[i++], road.Id); - } - } - { - var sources = new RoadPoint[] { - new RoadPoint( map.GetEdge(0), 0.4), - new RoadPoint( map.GetEdge(1), 0.6), - }; - var targets = new RoadPoint[] { - new RoadPoint(map.GetEdge(0), 0.3) - }; - - var routes = router.Route(sources, targets, e => e.Weight, null, double.NaN); - - var route = routes[targets.First()]; - var path = new long[] { 1L, 0L }; - - Assert.Equal(path.First(), route.Item1.Edge.Id); - Assert.Equal(path.Length, route.Item2.Count()); - - int i = 0; - foreach (var road in route.Item2) - { - Assert.Equal(path[i++], road.Id); - } - } - } - - [Fact] - public void TestShortestPath() - { - var roads = new Road[] { - new Road(0, 0, 1, 100), - new Road(1, 1, 0, 100), - new Road(2, 0, 2, 160), - new Road(3, 2, 0, 160), - new Road(4, 1, 2, 50), - new Road(5, 2, 1, 50), - new Road(6, 1, 3, 200), - new Road(7, 3, 1, 200), - new Road(8, 2, 3, 100), - new Road(9, 3, 2, 100), - new Road(10, 2, 4, 40), - new Road(11, 4, 2, 40), - new Road(12, 3, 4, 100), - new Road(13, 4, 3, 100), - new Road(14, 3, 5, 200), - new Road(15, 5, 3, 200), - new Road(16, 4, 5, 60), - new Road(17, 5, 4, 60), - }; - var map = new Graph(roads); - var router = new DijkstraRouter(); - { - // (0.7, 100) + 50 + 40 + 60 + (0.3, 200) = 280 - - var sources = new RoadPoint[] { - new RoadPoint(map.GetEdge(0), 0.3), - new RoadPoint(map.GetEdge(1), 0.7), - }; - - var targets = new RoadPoint[] { - new RoadPoint(map.GetEdge(14), 0.3), - new RoadPoint(map.GetEdge(15), 0.7), - }; - - var routes = router.Route(sources, targets, e => e.Weight, null, double.NaN); - - var paths = new Dictionary() { - { 14L, new long[] { 0L, 4L, 8L, 14L } }, - { 15L, new long[] { 0L, 4L, 10L, 16L, 15L } }, - }; - - Assert.Equal(paths.Count(), routes.Count()); - - foreach (var pair in routes) - { - var route = pair.Value.Item2; - Assert.NotNull(paths[pair.Key.Edge.Id]); - var path = paths[pair.Key.Edge.Id]; - - Assert.NotNull(route); - Assert.Equal(path.First(), pair.Value.Item1.Edge.Id); - Assert.Equal(path.Count(), route.Count()); - - int i = 0; - foreach (var road in route) - { - Assert.Equal((long)path[i++], road.Id); - } - } - } - { - // (0.7, 100) + 50 + 100 + (0.1, 200) = 240 - - var sources = new RoadPoint[] { - new RoadPoint(map.GetEdge(0), 0.3), - new RoadPoint(map.GetEdge(1), 0.7), - }; - - var targets = new RoadPoint[] { - new RoadPoint(map.GetEdge(14), 0.1), - new RoadPoint(map.GetEdge(15), 0.9), - }; - - var routes = router.Route(sources, targets, e => e.Weight, null, double.NaN); - - var paths = new Dictionary() { - { 14L, new long[] { 0L, 4L, 8L, 14L } }, - { 15L, new long[] { 0L, 4L, 10L, 16L, 15L } }, - }; - - Assert.Equal(paths.Count(), routes.Count()); - - foreach (var pair in routes) - { - var route = pair.Value; - Assert.NotNull(paths[pair.Key.Edge.Id]); - var path = paths[pair.Key.Edge.Id]; - - Assert.Equal(path[0], pair.Value.Item1.Edge.Id); - Assert.Equal(path.Count(), route.Item2.Count()); - - int i = 0; - foreach (var road in route.Item2) - { - Assert.Equal((long)path[i++], road.Id); - } - } - } - { - // (0.7, 100) + 50 + 100 + (0.1, 200) = 240 - var sources = new RoadPoint[] { - new RoadPoint(map.GetEdge(0), 0.3), - }; - - var targets = new RoadPoint[] { - new RoadPoint(map.GetEdge(14), 0.1), - }; - var route = router.Route(sources, targets, e => e.Weight, e => e.Weight, 200.0); - Assert.NotNull(route); - Assert.Empty(route); - - } - { - // (0.7, 100) + 50 + 100 + (0.1, 200) = 240 - // (0.7, 100) + 50 + 100 + (0.8, 200) = 380 - - var sources = new RoadPoint[] { - new RoadPoint(map.GetEdge(0), 0.3), - new RoadPoint(map.GetEdge(1), 0.7), - }; - - var targets = new RoadPoint[] { - new RoadPoint(map.GetEdge(14), 0.1), - new RoadPoint(map.GetEdge(14), 0.8), - }; - - var routes = router.Route(sources, targets, e => e.Weight, null, double.NaN); - - var paths = new Dictionary() { - { 14L, new long[] { 0L, 4L, 8L, 14L } } - }; - - Assert.Equal(2, routes.Count()); - - foreach (var pair in routes) - { - var route = pair.Value.Item2; - var path = paths[pair.Key.Edge.Id]; - - Assert.NotNull(route); - Assert.Equal(path[0], pair.Value.Item1.Edge.Id); - Assert.Equal(path.Count(), route.Count()); - - int i = 0; - foreach (var road in route) - { - Assert.Equal((long)path[i++], road.Id); - } - } - } - } + protected override IGraphRouter CreateRouter() => new DijkstraRouter(); + } } diff --git a/test/Sandwych.MapMatchingKit.Tests/Topology/Models.cs b/test/Sandwych.MapMatchingKit.Tests/Topology/Models.cs new file mode 100644 index 0000000..823b0a4 --- /dev/null +++ b/test/Sandwych.MapMatchingKit.Tests/Topology/Models.cs @@ -0,0 +1,43 @@ +using Sandwych.MapMatchingKit.Topology; +using System; +using System.Collections.Generic; +using System.Text; + +namespace Sandwych.MapMatchingKit.Tests.Topology +{ + public class Road : AbstractGraphEdge + { + public float Weight { get; } + + public Road(long id, long source, long target, float weight) : base(id, source, target) + { + this.Weight = weight; + } + + public override int GetHashCode() => + (this.Id, this.Weight).GetHashCode(); + } + + public class Graph : AbstractGraph + { + public Graph(IEnumerable roads) : base(roads) + { + + } + } + + public readonly struct RoadPoint : IEdgePoint + { + public Road Edge { get; } + public double Fraction { get; } + + public RoadPoint(Road road, double fraction) + { + this.Edge = road; + this.Fraction = fraction; + } + + public override int GetHashCode() => + (this.Edge, this.Fraction).GetHashCode(); + } +} diff --git a/test/Sandwych.MapMatchingKit.Tests/Topology/UbodtRouterTest.cs b/test/Sandwych.MapMatchingKit.Tests/Topology/UbodtRouterTest.cs new file mode 100644 index 0000000..1e1d7f6 --- /dev/null +++ b/test/Sandwych.MapMatchingKit.Tests/Topology/UbodtRouterTest.cs @@ -0,0 +1,12 @@ +using System; +using System.Collections.Generic; +using System.Text; +using Sandwych.MapMatchingKit.Topology; + +namespace Sandwych.MapMatchingKit.Tests.Topology +{ + public class UbodtRouterTest : AbstractRouterTest + { + protected override IGraphRouter CreateRouter() => new UbodtRouter(); + } +} From 847d907ff6e4db7ad498577970da8168515d89f3 Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Thu, 22 Feb 2018 14:56:35 +0800 Subject: [PATCH 03/37] more api doc --- src/Sandwych.MapMatchingKit/Roads/Road.cs | 14 +- src/Sandwych.MapMatchingKit/Roads/RoadMap.cs | 17 ++- .../Spatial/GeodesicInterception.cs | 124 +++++++++--------- .../Topology/AbstractGraph.cs | 1 + .../Topology/AbstractGraphEdge.cs | 21 ++- .../Topology/IGraphEdge.cs | 24 ++++ .../Topology/Ubodt/UbodTable.cs | 10 ++ .../Topology/{ => Ubodt}/UbodtRouter.cs | 0 .../Topology/Ubodt/UbodtRow.cs | 16 +++ 9 files changed, 154 insertions(+), 73 deletions(-) create mode 100644 src/Sandwych.MapMatchingKit/Topology/Ubodt/UbodTable.cs rename src/Sandwych.MapMatchingKit/Topology/{ => Ubodt}/UbodtRouter.cs (100%) create mode 100644 src/Sandwych.MapMatchingKit/Topology/Ubodt/UbodtRow.cs diff --git a/src/Sandwych.MapMatchingKit/Roads/Road.cs b/src/Sandwych.MapMatchingKit/Roads/Road.cs index 2d8c36f..6e8d596 100644 --- a/src/Sandwych.MapMatchingKit/Roads/Road.cs +++ b/src/Sandwych.MapMatchingKit/Roads/Road.cs @@ -9,13 +9,13 @@ namespace Sandwych.MapMatchingKit.Roads { ///

- /// Directed road wrapper of {@link BaseRoad} objects in a directed road map ({@link RoadMap}). * + /// Directed road wrapper of objects in a directed road map (). /// - /// Note: Since {@link Road} objects are directional representations of {@link BaseRoad} - /// objects, each {@link BaseRoad} is split into two {@link Road} objects. For that purpose, it uses - /// the identifier i of each {@link BaseRoad} to define identifiers of the respective - /// {@link Road} objects, where i * 2 is the identifier of the forward directed {@link Road} - /// and i * 2 + 1 of the backward directed {@link Road}. + /// Note: Since objects are directional representations of + /// objects, each is split into two objects. For that purpose, it uses + /// the identifier i of each to define identifiers of the respective + /// {@link Road} objects, where i * 2 is the identifier of the forward directed + /// and i * 2 + 1 of the backward directed . /// /// public class Road : AbstractGraphEdge @@ -31,7 +31,7 @@ public class Road : AbstractGraphEdge public Heading Headeing { get; } /// - /// Gets road's geometry as a {@link Polyline} from the road's source to its target. + /// Gets road's geometry as a from the road's source to its target. /// public ILineString Geometry { get; } diff --git a/src/Sandwych.MapMatchingKit/Roads/RoadMap.cs b/src/Sandwych.MapMatchingKit/Roads/RoadMap.cs index c14936c..75b28a4 100644 --- a/src/Sandwych.MapMatchingKit/Roads/RoadMap.cs +++ b/src/Sandwych.MapMatchingKit/Roads/RoadMap.cs @@ -9,13 +9,17 @@ namespace Sandwych.MapMatchingKit.Roads { - /// Implementation of a road map with (directed) roads, i.e. {@link Road} objects. It provides a road - /// network for routing that is derived from {@link Graph} and spatial search of roads with a - /// {@link SpatialIndex}. + /// /// - /// Note: Since {@link Road} objects are directed representations of {@link BaseRoad} objects, - /// identifiers have a special mapping, see {@link Road}. + /// Implementation of a road map with (directed) roads, i.e. objects. It provides a road + /// network for routing that is derived from and spatial search of roads with a + /// . /// + /// + /// Note: Since objects are directed representations of objects, + /// identifiers have a special mapping, see . + /// + /// public sealed class RoadMap : AbstractGraph { public ISpatialIndex Index { get; } @@ -24,6 +28,9 @@ public sealed class RoadMap : AbstractGraph public RoadMap(IEnumerable roads, ISpatialOperation spatial) : base(roads) { _spatial = spatial; + + // The original Barefoot is using Quad Tree for spatial indexing, however, in my experiment, NTS's STRtree is + // much faster than NTS's Quadtree. this.Index = new RtreeIndex(roads.Select(x => x.RoadInfo), spatial, r => r.Geometry, r => r.Length); } diff --git a/src/Sandwych.MapMatchingKit/Spatial/GeodesicInterception.cs b/src/Sandwych.MapMatchingKit/Spatial/GeodesicInterception.cs index 18f0274..de6266a 100644 --- a/src/Sandwych.MapMatchingKit/Spatial/GeodesicInterception.cs +++ b/src/Sandwych.MapMatchingKit/Spatial/GeodesicInterception.cs @@ -23,80 +23,86 @@ namespace Sandwych.MapMatchingKit.Spatial { - /* - *

- * Note: Intercept.java has been ported to Java from its C++ equivalent Intercept.cpp, authored - * by C. F. F. Karney and licensed under MIT/X11 license. The following documentation is mostly the - * same as for its C++ equivalent, but has been adopted to apply to this Java implementation. - *

- * Simple solution to the interception using the gnomonic projection. The interception problem is, - * given a geodesic a and a point b, determine the point p on the geodesic - * a that is closest to point b. The gnomonic projection and the solution to the - * interception problem are derived in Section 8 of - *

- *

- * In gnomonic projection geodesics are nearly straight; and they are exactly straight if they go - * through the center of projection. The interception can then be found as follows: Guess an - * interception point. Project the resulting line segments into gnomonic, compute their intersection - * in this projection, use this intersection point as the new center, and repeat. - *

- * CAUTION: The solution to the interception problem is valid only under the following - * conditions: - *

    - *
  • The two points defining the geodesic and the point of interception must be in the same - * hemisphere centered at the interception point for the gnomonic projection to be defined.
  • - *
- */ - /// + /// /// Geodesic interception. + /// + /// + /// Note: Intercept.java has been ported to Java from its C++ equivalent Intercept.cpp, authored + /// by C. F. F. Karney and licensed under MIT/X11 license. The following documentation is mostly the + /// same as for its C++ equivalent, but has been adopted to apply to this Java implementation. + /// + /// + /// Simple solution to the interception using the gnomonic projection. The interception problem is, + /// given a geodesic a and a point b, determine the point p on the geodesic + /// a that is closest to point b. The gnomonic projection and the solution to the + /// interception problem are derived in Section 8 of + /// + /// + /// + /// In gnomonic projection geodesics are nearly straight; and they are exactly straight if they go + /// through the center of projection. The interception can then be found as follows: Guess an + /// interception point. Project the resulting line segments into gnomonic, compute their intersection + /// in this projection, use this intersection point as the new center, and repeat. + /// + /// + /// CAUTION: The solution to the interception problem is valid only under the following + /// conditions: + ///
    + ///
  • The two points defining the geodesic and the point of interception must be in the same + /// hemisphere centered at the interception point for the gnomonic projection to be defined.
  • + ///
+ ///
///
public readonly struct GeodesicInterception { private static readonly double eps = 0.01 * Math.Sqrt(GeoMath.Epsilon); - /** - * Maximum number of iterations for calculation of interception point. (The solution should - * usually converge before reaching the maximum number of iterations. The default is 10.) - */ + + + /// + /// Maximum number of iterations for calculation of interception point. (The solution should + /// usually converge before reaching the maximum number of iterations. The default is 10.) + /// public const int Maxit = 10; + private readonly Gnomonic _gnom; - /** - * Constructor for Intercept. - *

- * - * @param earth the {@link Geodesic} object to use for geodesic calculations. By default the - * WGS84 ellipsoid should be used. - */ + ///

+ /// Constructor for Intercept. + /// + /// the object to use for geodesic calculations. By default the WGS84 ellipsoid should be used. public GeodesicInterception(in Geodesic earth) { this._gnom = new Gnomonic(earth); } - /** - * Interception of a point b to a geodesic a. - *

- * - * @param lata1 latitude of point 1 of geodesic a (degrees). - * @param lona1 longitude of point 1 of geodesic a (degrees). - * @param lata2 latitude of point 2 of geodesic a (degrees). - * @param lona2 longitude of point 2 of geodesic a (degrees). - * @param latb1 latitude of point b (degrees). - * @param lonb1 longitude of point b (degrees). - * @return a {@link GeodesicData} object, defining a geodesic from point b to the - * intersection point, with the following fields: lat1, lon1, azi1, - * lat2, lon2, azi2, s12, a12. - *

- * lat1 should be in the range [−90°, 90°]; lon1 and - * azi1 should be in the range [−540°, 540°). The values of - * lon2 and azi2 returned are in the range [−180°, 180°). - */ + ///

+ /// Interception of a point b to a geodesic a. + /// + /// latitude of point 1 of geodesic a (degrees). + /// longitude of point 1 of geodesic a (degrees). + /// latitude of point 2 of geodesic a (degrees). + /// longitude of point 2 of geodesic a (degrees). + /// latitude of point b (degrees). + /// longitude of point b (degrees). + /// + /// + /// a object, defining a geodesic from point b to the + /// intersection point, with the following fields: lat1, lon1, azi1, + /// lat2, lon2, azi2, s12, a12. + /// + /// + /// lat1 should be in the range [−90°, 90°]; lon1 and + /// azi1 should be in the range [−540°, 540°). The values of + /// lon2 and azi2 returned are in the range [−180°, 180°). + /// + /// public GeodesicData Intercept(double lata1, double lona1, double lata2, double lona2, double latb1, double lonb1) { diff --git a/src/Sandwych.MapMatchingKit/Topology/AbstractGraph.cs b/src/Sandwych.MapMatchingKit/Topology/AbstractGraph.cs index eeae929..e53d632 100644 --- a/src/Sandwych.MapMatchingKit/Topology/AbstractGraph.cs +++ b/src/Sandwych.MapMatchingKit/Topology/AbstractGraph.cs @@ -5,6 +5,7 @@ namespace Sandwych.MapMatchingKit.Topology { + public abstract class AbstractGraph : IGraph where TEdge : AbstractGraphEdge { diff --git a/src/Sandwych.MapMatchingKit/Topology/AbstractGraphEdge.cs b/src/Sandwych.MapMatchingKit/Topology/AbstractGraphEdge.cs index 1879dd8..e334d6b 100644 --- a/src/Sandwych.MapMatchingKit/Topology/AbstractGraphEdge.cs +++ b/src/Sandwych.MapMatchingKit/Topology/AbstractGraphEdge.cs @@ -4,7 +4,14 @@ namespace Sandwych.MapMatchingKit.Topology { - public abstract class AbstractGraphEdge : IGraphEdge + + /// + /// Abstract edge in a directed . + /// + /// Implementation of in a directed graph. + /// (Use the curiously recurring template pattern (CRTP) for type-safe use of customized edge type.) + /// + public abstract class AbstractGraphEdge : IGraphEdge, IEquatable where TEdge : class, IGraphEdge { public long Id { get; } @@ -25,7 +32,7 @@ public AbstractGraphEdge(long id, long source, long target) this.Target = target; } - public IEnumerable Successors + public virtual IEnumerable Successors { get { @@ -48,5 +55,15 @@ public IEnumerable Successors } public override int GetHashCode() => this.Id.GetHashCode(); + + public virtual bool Equals(TEdge other) + { + if (object.ReferenceEquals(this, other)) + { + return true; + } + + return this.Id == other.Id; + } } } diff --git a/src/Sandwych.MapMatchingKit/Topology/IGraphEdge.cs b/src/Sandwych.MapMatchingKit/Topology/IGraphEdge.cs index 1839b22..41c1d4e 100644 --- a/src/Sandwych.MapMatchingKit/Topology/IGraphEdge.cs +++ b/src/Sandwych.MapMatchingKit/Topology/IGraphEdge.cs @@ -4,19 +4,43 @@ namespace Sandwych.MapMatchingKit.Topology { + /// + /// The interface of edge in a directed . + /// + /// Implementation of in a directed graph. + /// (Use the curiously recurring template pattern (CRTP) for type-safe use of customized edge type.) + /// public interface IGraphEdge where T : IGraphEdge { + /// + /// Gets the edge's identifier. + /// long Id { get; } + /// + /// Gets the edge's source vertex. + /// long Source { get; } + /// + /// Gets the edge's target vertex. + /// long Target { get; } + /// + /// Gets the edge's neighbor. + /// T Neighbor { get; } + /// + /// Gets the edge's successor. + /// T Successor { get; } + /// + /// Gets the edge's successor edges. + /// IEnumerable Successors { get; } } } diff --git a/src/Sandwych.MapMatchingKit/Topology/Ubodt/UbodTable.cs b/src/Sandwych.MapMatchingKit/Topology/Ubodt/UbodTable.cs new file mode 100644 index 0000000..2b69617 --- /dev/null +++ b/src/Sandwych.MapMatchingKit/Topology/Ubodt/UbodTable.cs @@ -0,0 +1,10 @@ +using System; +using System.Collections.Generic; +using System.Text; + +namespace Sandwych.MapMatchingKit.Topology +{ + public sealed class UbodTable + { + } +} diff --git a/src/Sandwych.MapMatchingKit/Topology/UbodtRouter.cs b/src/Sandwych.MapMatchingKit/Topology/Ubodt/UbodtRouter.cs similarity index 100% rename from src/Sandwych.MapMatchingKit/Topology/UbodtRouter.cs rename to src/Sandwych.MapMatchingKit/Topology/Ubodt/UbodtRouter.cs diff --git a/src/Sandwych.MapMatchingKit/Topology/Ubodt/UbodtRow.cs b/src/Sandwych.MapMatchingKit/Topology/Ubodt/UbodtRow.cs new file mode 100644 index 0000000..f60dc65 --- /dev/null +++ b/src/Sandwych.MapMatchingKit/Topology/Ubodt/UbodtRow.cs @@ -0,0 +1,16 @@ +using System; +using System.Collections.Generic; +using System.Text; + +namespace Sandwych.MapMatchingKit.Topology +{ + public readonly struct UbodtRow + { + public long Source { get; } + public long Target { get; } + public long NextNode { get; } + public long PrevNode { get; } + public long NextEdge { get; } + public double Cost { get; } + } +} From eb612689fc640dddeb5954801bc590f3486f1ec9 Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Thu, 22 Feb 2018 17:11:28 +0800 Subject: [PATCH 04/37] refactor DijkstraRouter --- .../Roads/RoadPoint.cs | 9 +- .../Topology/DijkstraRouter.cs | 86 +++-- .../Topology/{EdgePoint.cs => IEdgePoint.cs} | 2 +- .../Topology/IGraphEdge.cs | 2 +- .../Topology/IGraphRouter.cs | 12 +- .../Topology/Ubodt/UbodtRouter.cs | 324 +----------------- .../Topology/Models.cs | 5 +- 7 files changed, 75 insertions(+), 365 deletions(-) rename src/Sandwych.MapMatchingKit/Topology/{EdgePoint.cs => IEdgePoint.cs} (79%) diff --git a/src/Sandwych.MapMatchingKit/Roads/RoadPoint.cs b/src/Sandwych.MapMatchingKit/Roads/RoadPoint.cs index 0d56f56..8d67abf 100644 --- a/src/Sandwych.MapMatchingKit/Roads/RoadPoint.cs +++ b/src/Sandwych.MapMatchingKit/Roads/RoadPoint.cs @@ -44,12 +44,11 @@ public RoadPoint(in Road road, double fraction) : this(road, fraction, Geography } public override int GetHashCode() => - (this.Edge, this.Fraction, this.Coordinate, this.Azimuth).GetHashCode(); + (this.Edge, this.Fraction).GetHashCode(); - public bool Equals(RoadPoint other) - { - return object.ReferenceEquals(this.Edge, other.Edge) && this.Fraction == other.Fraction && this.Coordinate == other.Coordinate && this.Azimuth == other.Azimuth; - } + public bool Equals(RoadPoint other) => + this.Edge == other.Edge && Math.Abs(this.Fraction - other.Fraction) < 10E-6; + } } diff --git a/src/Sandwych.MapMatchingKit/Topology/DijkstraRouter.cs b/src/Sandwych.MapMatchingKit/Topology/DijkstraRouter.cs index cd56377..948edd6 100644 --- a/src/Sandwych.MapMatchingKit/Topology/DijkstraRouter.cs +++ b/src/Sandwych.MapMatchingKit/Topology/DijkstraRouter.cs @@ -16,20 +16,24 @@ namespace Sandwych.MapMatchingKit.Topology /// type of positions in the network. public class DijkstraRouter : IGraphRouter where TEdge : class, IGraphEdge - where P : IEdgePoint + where P : IEdgePoint, IEquatable

{ public ILogger Logger { get; set; } = NullLogger.Instance; ///

/// Route mark representation. /// - private sealed class Mark : IComparable + private readonly struct Mark : IComparable, IEquatable { public TEdge MarkedEdge { get; } public TEdge PredecessorEdge { get; } public double Cost { get; } public double BoundingCost { get; } + private readonly static Mark s_empty = new Mark(null, null, double.NaN, double.NaN); + public static ref readonly Mark Empty => ref s_empty; + public bool IsEmpty => double.IsNaN(this.Cost); + /// /// Constructor of an entry. /// @@ -47,6 +51,11 @@ public Mark(TEdge markedEdge, TEdge predecessorEdge, Double cost, Double boundin public int CompareTo(Mark other) { + if (this.IsEmpty || other.IsEmpty) + { + throw new InvalidOperationException(); + } + if (this.Cost < other.Cost) { return -1; @@ -63,40 +72,28 @@ public int CompareTo(Mark other) public override int GetHashCode() => (this.MarkedEdge, this.PredecessorEdge, this.Cost, this.BoundingCost).GetHashCode(); - } - public IEnumerable Route(P source, P target, Func cost) - { - return Ssst(source, target, cost, null, double.NaN); + public bool Equals(Mark other) + { + if (this.IsEmpty || other.IsEmpty) + { + throw new InvalidOperationException(); + } + return this.CompareTo(other) == 0; + } } - public IEnumerable Route(P source, P target, Func cost, Func bound, double max) - { - return Ssst(source, target, cost, bound, max); - } + public IDictionary> Route(P source, IEnumerable

targets, + Func cost, Func bound = null, double max = double.NaN) => + Ssmt(source, targets, cost, bound, max); - public IDictionary> Route(P source, IEnumerable

targets, Func cost) - { - return Ssmt(source, targets, cost, null, double.NaN); - } + public IDictionary)> Route(IEnumerable

sources, IEnumerable

targets, + Func cost, Func bound = null, double max = double.NaN) => + Msmt(sources, targets, cost, bound, max); - public IDictionary> Route(P source, IEnumerable

targets, Func cost, - Func bound = null, double max = double.NaN) - { - return Ssmt(source, targets, cost, bound, max); - } - - public IDictionary)> Route(IEnumerable

sources, IEnumerable

targets, Func cost, - Func bound, double max) - { - return Msmt(sources, targets, cost, bound, max); - } - - private IEnumerable Ssst(P source, P target, Func cost, Func bound, double max) - { - var targets = new P[] { target }; - return Ssmt(source, targets, cost, bound, max)[target]; - } + public IEnumerable Route(P source, P target, + Func cost, Func bound = null, double max = double.NaN) => + Ssmt(source, new P[] { target }, cost, bound, max)[target]; private IDictionary> Ssmt(P source, IEnumerable

targets, Func cost, Func bound, double max = double.NaN) { @@ -116,7 +113,7 @@ private IDictionary> Ssmt(P source, IEnumerable

targets /* * Initialize map of edges to target points. */ - var targetEdges = new Dictionary>(); + var targetEdges = new Dictionary>(); foreach (var target in targets) { if (this.Logger.IsEnabled(LogLevel.Debug)) @@ -127,7 +124,7 @@ private IDictionary> Ssmt(P source, IEnumerable

targets if (!targetEdges.ContainsKey(target.Edge)) { - targetEdges[target.Edge] = new HashSet

() { target }; + targetEdges[target.Edge] = new HashSet

{ target }; } else { @@ -159,6 +156,7 @@ private IDictionary> Ssmt(P source, IEnumerable

targets source, source.Edge.Id, source.Fraction, startcost); } + //On the same edge if (targetEdges.TryGetValue(source.Edge, out var targetsMap)) { // start edge reaches target edge @@ -308,7 +306,7 @@ private IDictionary> Ssmt(P source, IEnumerable

targets { this.Logger.LogDebug("added successor edge {0} with {1} cost", successor.Id, succcost); } - Mark mark = new Mark(successor, current.MarkedEdge, succcost, succbound); + var mark = new Mark(successor, current.MarkedEdge, succcost, succbound); entries.Add(successor, mark); priorities.Enqueue(mark); } @@ -323,12 +321,26 @@ private IDictionary> Ssmt(P source, IEnumerable

targets { var path = new List(); var iterator = finishs[targetPoint]; - Mark start = null; - while (iterator != null) + var start = Mark.Empty; + while (!iterator.IsEmpty) { path.Add(iterator.MarkedEdge); start = iterator; - iterator = iterator.PredecessorEdge != null ? entries.GetOrNull(iterator.PredecessorEdge) : null; + if (iterator.PredecessorEdge != null) + { + if (entries.TryGetValue(iterator.PredecessorEdge, out var pem)) + { + iterator = pem; + } + else + { + iterator = Mark.Empty; + } + } + else + { + iterator = Mark.Empty; + } } path.Reverse(); var tp = (starts[start], path); diff --git a/src/Sandwych.MapMatchingKit/Topology/EdgePoint.cs b/src/Sandwych.MapMatchingKit/Topology/IEdgePoint.cs similarity index 79% rename from src/Sandwych.MapMatchingKit/Topology/EdgePoint.cs rename to src/Sandwych.MapMatchingKit/Topology/IEdgePoint.cs index ff66736..f2f8877 100644 --- a/src/Sandwych.MapMatchingKit/Topology/EdgePoint.cs +++ b/src/Sandwych.MapMatchingKit/Topology/IEdgePoint.cs @@ -5,7 +5,7 @@ namespace Sandwych.MapMatchingKit.Topology { public interface IEdgePoint - where TEdge : IGraphEdge + where TEdge : IGraphEdge, IEquatable { TEdge Edge { get; } double Fraction { get; } diff --git a/src/Sandwych.MapMatchingKit/Topology/IGraphEdge.cs b/src/Sandwych.MapMatchingKit/Topology/IGraphEdge.cs index 41c1d4e..23d5d9c 100644 --- a/src/Sandwych.MapMatchingKit/Topology/IGraphEdge.cs +++ b/src/Sandwych.MapMatchingKit/Topology/IGraphEdge.cs @@ -10,7 +10,7 @@ namespace Sandwych.MapMatchingKit.Topology /// Implementation of in a directed graph. /// (Use the curiously recurring template pattern (CRTP) for type-safe use of customized edge type.) /// - public interface IGraphEdge + public interface IGraphEdge : IEquatable where T : IGraphEdge { ///

diff --git a/src/Sandwych.MapMatchingKit/Topology/IGraphRouter.cs b/src/Sandwych.MapMatchingKit/Topology/IGraphRouter.cs index a2cd6e3..1681155 100644 --- a/src/Sandwych.MapMatchingKit/Topology/IGraphRouter.cs +++ b/src/Sandwych.MapMatchingKit/Topology/IGraphRouter.cs @@ -7,15 +7,17 @@ namespace Sandwych.MapMatchingKit.Topology { public interface IGraphRouter where TEdge : IGraphEdge - where P : IEdgePoint + where P : IEdgePoint, IEquatable

{ - IDictionary> Route(P source, IEnumerable

targets, Func cost, - Func bound = null, double max = double.NaN); + IEnumerable Route(P source, P target, + Func cost, Func bound = null, double max = double.NaN); + IDictionary> Route(P source, IEnumerable

targets, + Func cost, Func bound = null, double max = double.NaN); - IDictionary)> Route(IEnumerable

sources, IEnumerable

targets, Func cost, - Func bound = null, double max = double.NaN); + IDictionary)> Route(IEnumerable

sources, IEnumerable

targets, + Func cost, Func bound = null, double max = double.NaN); } diff --git a/src/Sandwych.MapMatchingKit/Topology/Ubodt/UbodtRouter.cs b/src/Sandwych.MapMatchingKit/Topology/Ubodt/UbodtRouter.cs index 7d73444..9c5e9d5 100644 --- a/src/Sandwych.MapMatchingKit/Topology/Ubodt/UbodtRouter.cs +++ b/src/Sandwych.MapMatchingKit/Topology/Ubodt/UbodtRouter.cs @@ -9,335 +9,29 @@ namespace Sandwych.MapMatchingKit.Topology { public class UbodtRouter : IGraphRouter where TEdge : class, IGraphEdge - where P : IEdgePoint + where P : IEdgePoint, IEquatable

{ public ILogger Logger { get; set; } = NullLogger.Instance; - ///

- /// Route mark representation. - /// - private sealed class Mark : IComparable - { - public TEdge MarkedEdge { get; } - public TEdge PredecessorEdge { get; } - public double Cost { get; } - public double BoundingCost { get; } - - /// - /// Constructor of an entry. - /// - /// {@link AbstractEdge} defining the route mark. - /// Predecessor {@link AbstractEdge}. - /// Cost value to this route mark. - /// Bounding cost value to this route mark. - public Mark(TEdge markedEdge, TEdge predecessorEdge, Double cost, Double boundingCost) - { - this.MarkedEdge = markedEdge; - this.PredecessorEdge = predecessorEdge; - this.Cost = cost; - this.BoundingCost = boundingCost; - } - - public int CompareTo(Mark other) - { - if (this.Cost < other.Cost) - { - return -1; - } - else if (this.Cost > other.Cost) - { - return 1; - } - else - { - return 0; - } - } - - public override int GetHashCode() => - (this.MarkedEdge, this.PredecessorEdge, this.Cost, this.BoundingCost).GetHashCode(); - } - - public IEnumerable Route(P source, P target, Func cost) - { - return Ssst(source, target, cost, null, double.NaN); - } - - public IEnumerable Route(P source, P target, Func cost, Func bound, double max) - { - return Ssst(source, target, cost, bound, max); - } - - public IDictionary> Route(P source, IEnumerable

targets, Func cost) - { - return Ssmt(source, targets, cost, null, double.NaN); - } public IDictionary> Route(P source, IEnumerable

targets, Func cost, Func bound = null, double max = double.NaN) { - return Ssmt(source, targets, cost, bound, max); - } - - public IDictionary)> Route(IEnumerable

sources, IEnumerable

targets, Func cost, - Func bound, double max) - { - return Msmt(sources, targets, cost, bound, max); + throw new NotImplementedException(); } - private IEnumerable Ssst(P source, P target, Func cost, Func bound, double max) + public IDictionary)> Route(IEnumerable

sources, IEnumerable

targets, Func cost = null, + Func bound = null, double max = double.NaN) { - var targets = new P[] { target }; - return Ssmt(source, targets, cost, bound, max)[target]; + throw new NotImplementedException(); } - private IDictionary> Ssmt(P source, IEnumerable

targets, Func cost, Func bound, double max = double.NaN) + public IEnumerable Route(P source, P target, Func cost, Func bound = null, double max = double.NaN) { - var sources = new P[1] { source }; - var map = Msmt(sources, targets, cost, bound, max); - var result = new Dictionary>(map.Count); - foreach (var entry in map) - { - result[entry.Key] = entry.Value.Item2; - } - return result; + throw new NotImplementedException(); } + } - private IDictionary)> Msmt(IEnumerable

sources, IEnumerable

targets, Func cost, - Func bound, double max) - { - /* - * Initialize map of edges to target points. - */ - var targetEdges = new Dictionary>(); - foreach (var target in targets) - { - if (this.Logger.IsEnabled(LogLevel.Debug)) - { - this.Logger.LogDebug("initialize target {0} with edge {1} and fraction {2}", - target, target.Edge.Id, target.Fraction); - } - - if (!targetEdges.ContainsKey(target.Edge)) - { - targetEdges[target.Edge] = new HashSet

() { target }; - } - else - { - targetEdges[target.Edge].Add(target); - } - } - - /* - * Setup data structures - */ - var priorities = new PriorityQueue(); - var entries = new Dictionary(); - var finishs = new Dictionary(); - var reaches = new Dictionary(); - var starts = new Dictionary(); - - /* - * Initialize map of edges with start points - */ - foreach (var source in sources) - { - // initialize sources as start edges - var startcost = source.Edge.Cost(1.0 - source.Fraction, cost); //cost.cost(source.Edge, 1 - source.Fraction); - var startbound = bound != null ? source.Edge.Cost(1.0 - source.Fraction, bound) : 0D; //bound.cost(source.Edge.Cost(), 1 - source.Fraction) : 0.0; - - if (this.Logger.IsEnabled(LogLevel.Debug)) - { - this.Logger.LogDebug("init source {0} with start edge {1} and fraction {2} with {3} cost", - source, source.Edge.Id, source.Fraction, startcost); - } - - if (targetEdges.TryGetValue(source.Edge, out var targetsMap)) - { - // start edge reaches target edge - foreach (var target in targetsMap) - { - if (target.Fraction < source.Fraction) - { - continue; - } - var reachcost = startcost - source.Edge.Cost(1.0 - target.Fraction, cost); // cost.cost(source.Edge, 1 - target.Fraction); - var reachbound = bound != null ? startcost - source.Edge.Cost(1.0 - target.Fraction, bound) : 0D; //, // bound.cost(source.Edge, 1 - target.Fraction) : 0.0; - - if (this.Logger.IsEnabled(LogLevel.Debug)) - { - this.Logger.LogDebug("reached target {0} with start edge {1} from {2} to {3} with {4} cost", - target, source.Edge.Id, source.Fraction, target.Fraction, reachcost); - } - - var reach = new Mark(source.Edge, null, reachcost, reachbound); - reaches.Add(reach, target); - starts.Add(reach, source); - priorities.Enqueue(reach); - } - } - - if (!entries.TryGetValue(source.Edge, out var start)) - { - if (this.Logger.IsEnabled(LogLevel.Debug)) - { - this.Logger.LogDebug("add source {0} with start edge {1} and fraction {2} with {3} cost", - source, source.Edge.Id, source.Fraction, startcost); - } - start = new Mark(source.Edge, null, startcost, startbound); - entries[source.Edge] = start; - starts[start] = source; - priorities.Enqueue(start); - } - else - { - if (startcost < start.Cost) - { - if (this.Logger.IsEnabled(LogLevel.Debug)) - { - this.Logger.LogDebug("update source {0} with start edge {1} and fraction {2} with {3} cost", - source, source.Edge.Id, source.Fraction, startcost); - } - start = new Mark(source.Edge, null, startcost, startbound); - entries[source.Edge] = start; - starts[start] = source; - priorities.Remove(start); - priorities.Enqueue(start); - } - } - } - - /* - * Dijkstra algorithm. - */ - while (priorities.Count > 0) - { - var current = priorities.Dequeue(); - - if (targetEdges.Count == 0) - { - if (this.Logger.IsEnabled(LogLevel.Debug)) - { - this.Logger.LogDebug("finshed all targets"); - } - break; - } - - if (!double.IsNaN(max) && current.BoundingCost > max) - { - if (this.Logger.IsEnabled(LogLevel.Debug)) - { - this.Logger.LogDebug("reached maximum bound"); - } - continue; - } - - /* - * Finish target if reached. - */ - { - if (reaches.TryGetValue(current, out var target)) - { - if (finishs.ContainsKey(target)) - { - continue; - } - else - { - if (this.Logger.IsEnabled(LogLevel.Debug)) - { - this.Logger.LogDebug("finished target {0} with edge {1} and fraction {2} with {3} cost", - target, current.MarkedEdge, target.Fraction, current.Cost); - } - - finishs[target] = current; - - var edges = targetEdges[current.MarkedEdge]; - edges.Remove(target); - - if (edges.Count == 0) - { - targetEdges.Remove(current.MarkedEdge); - } - continue; - } - } - } - - if (this.Logger.IsEnabled(LogLevel.Debug)) - { - this.Logger.LogDebug("succeed edge {0} with {1} cost", current.MarkedEdge.Id, current.Cost); - } - - var successors = current.MarkedEdge.Successors; - - foreach (var successor in successors) - { - var succcost = current.Cost + cost(successor); - var succbound = bound != null ? current.BoundingCost + bound(successor) : 0.0; - - if (targetEdges.ContainsKey(successor)) - { - // reach target edge - foreach (var targetEdge in targetEdges[successor]) - { - var reachcost = succcost - successor.Cost(1.0 - targetEdge.Fraction, cost); - var reachbound = bound != null ? succbound - successor.Cost(1.0 - targetEdge.Fraction, bound) : 0.0; /// bound(successor, 1 - target.Fraction) : 0.0; - if (this.Logger.IsEnabled(LogLevel.Debug)) - { - this.Logger.LogDebug("reached target {0} with successor edge {1} and fraction {2} with {3} cost", - targetEdge, successor.Id, targetEdge.Fraction, reachcost); - } - - var reach = new Mark(successor, current.MarkedEdge, reachcost, reachbound); - reaches.Add(reach, targetEdge); - priorities.Enqueue(reach); - } - } - - if (!entries.ContainsKey(successor)) - { - if (this.Logger.IsEnabled(LogLevel.Debug)) - { - this.Logger.LogDebug("added successor edge {0} with {1} cost", successor.Id, succcost); - } - Mark mark = new Mark(successor, current.MarkedEdge, succcost, succbound); - entries.Add(successor, mark); - priorities.Enqueue(mark); - } - } - } - - var paths = new Dictionary)>(); - - foreach (P targetPoint in targets) - { - if (finishs.ContainsKey(targetPoint)) - { - var path = new List(); - var iterator = finishs[targetPoint]; - Mark start = null; - while (iterator != null) - { - path.Add(iterator.MarkedEdge); - start = iterator; - iterator = iterator.PredecessorEdge != null ? entries.GetOrNull(iterator.PredecessorEdge) : null; - } - path.Reverse(); - var tp = (starts[start], path); - paths.Add(targetPoint, tp); - } - } - - /* - entries.Clear(); - finishs.Clear(); - reaches.Clear(); - priorities.Clear(); - */ +} - return paths; - } - } -} diff --git a/test/Sandwych.MapMatchingKit.Tests/Topology/Models.cs b/test/Sandwych.MapMatchingKit.Tests/Topology/Models.cs index 823b0a4..967b142 100644 --- a/test/Sandwych.MapMatchingKit.Tests/Topology/Models.cs +++ b/test/Sandwych.MapMatchingKit.Tests/Topology/Models.cs @@ -26,7 +26,7 @@ public Graph(IEnumerable roads) : base(roads) } } - public readonly struct RoadPoint : IEdgePoint + public readonly struct RoadPoint : IEdgePoint, IEquatable { public Road Edge { get; } public double Fraction { get; } @@ -39,5 +39,8 @@ public RoadPoint(Road road, double fraction) public override int GetHashCode() => (this.Edge, this.Fraction).GetHashCode(); + + public bool Equals(RoadPoint other) => + this.Edge == other.Edge && Math.Abs(this.Fraction - other.Fraction) < 10E-6; } } From e99ec4dc8c2744ca5c9e237ec78de6d2a523c559 Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Thu, 22 Feb 2018 18:39:51 +0800 Subject: [PATCH 05/37] refactor KState --- src/Sandwych.MapMatchingKit/Markov/KState.cs | 86 ++++++++++--------- .../Matching/MatcherSample.cs | 2 +- .../Markov/FilterTest.cs | 2 +- .../Markov/KStateTest.cs | 6 +- .../Markov/MockSample.cs | 2 +- 5 files changed, 53 insertions(+), 45 deletions(-) diff --git a/src/Sandwych.MapMatchingKit/Markov/KState.cs b/src/Sandwych.MapMatchingKit/Markov/KState.cs index 1fbfba2..850339c 100644 --- a/src/Sandwych.MapMatchingKit/Markov/KState.cs +++ b/src/Sandwych.MapMatchingKit/Markov/KState.cs @@ -19,36 +19,43 @@ public class KState : where TCandidate : class, IStateCandidate where TSample : ISample { - private readonly int _k; - private readonly long _t; - private readonly Deque<(ICollection, TSample, TCandidate)> _sequence; + private readonly struct SequenceEntry + { + public ICollection Candidates { get; } + public TSample Sample { get; } + public TCandidate Estimated { get; } + + public SequenceEntry(ICollection candidates, in TSample sample, in TCandidate estimated) + { + this.Candidates = candidates; + this.Sample = sample; + this.Estimated = estimated; + } + } + + private readonly int _k = -1; + private readonly TimeSpan _t = TimeSpan.MaxValue; + private readonly Deque _sequence; private readonly IDictionary _counters; ///

- /// Creates empty {@link KState} object with default parameters, i.e. capacity is unbounded. + /// Creates empty object with default parameters, i.e. capacity is unbounded. /// - public KState() + public KState() : this(-1, TimeSpan.MaxValue) { - this._k = -1; - this._t = -1; - this._sequence = new Deque<(ICollection, TSample, TCandidate)>(); - this._counters = new Dictionary(); } - /* - * Creates an empty {@link KState} object and sets κ and τ parameters. - * - * @param k κ parameter bounds the length of the state sequence to at most - * κ+1 states, if κ ≥ 0. - * @param t τ parameter bounds length of the state sequence to contain only states - * for the past τ milliseconds. - */ - public KState(int k, long t) + /// + /// Creates an empty object and sets κ and τ parameters. + /// + /// κ parameter bounds the length of the state sequence to at most κ+1 states, if κ ≥ 0. + /// τ parameter bounds length of the state sequence to contain only states for the past τ milliseconds. + public KState(int k, TimeSpan t) { this._k = k; this._t = t; - this._sequence = new Deque<(ICollection, TSample, TCandidate)>(); + this._sequence = new Deque(); this._counters = new Dictionary(); } @@ -66,7 +73,7 @@ public TSample Sample } else { - return _sequence.PeekLast().Item2; + return _sequence.PeekLast().Sample; } } } @@ -94,7 +101,7 @@ public IEnumerable Samples() { foreach (var element in _sequence) { - yield return element.Item2; + yield return element.Sample; } } @@ -105,7 +112,7 @@ public void Update(ICollection vector, in TSample sample) return; } - if (_sequence.Count > 0 && _sequence.PeekLast().Item2.Time > sample.Time) + if (_sequence.Count > 0 && _sequence.PeekLast().Sample.Time > sample.Time) { throw new InvalidOperationException("out-of-order state update is prohibited"); } @@ -116,7 +123,7 @@ public void Update(ICollection vector, in TSample sample) _counters[candidate] = 0; if (candidate.Predecessor != null) { - if (!_counters.ContainsKey(candidate.Predecessor) || !_sequence.PeekLast().Item1.Contains(candidate.Predecessor)) + if (!_counters.ContainsKey(candidate.Predecessor) || !_sequence.PeekLast().Candidates.Contains(candidate.Predecessor)) { throw new InvalidOperationException("Inconsistent update vector."); } @@ -133,7 +140,7 @@ public void Update(ICollection vector, in TSample sample) var last = _sequence.PeekLast(); var deletes = new List(); - foreach (TCandidate candidate in last.Item1) + foreach (TCandidate candidate in last.Candidates) { if (_counters[candidate] == 0) { @@ -141,23 +148,23 @@ public void Update(ICollection vector, in TSample sample) } } - var size = _sequence.PeekLast().Item1.Count; + var size = _sequence.PeekLast().Candidates.Count; foreach (TCandidate candidate in deletes) { - if (deletes.Count != size || candidate != last.Item3) + if (deletes.Count != size || candidate != last.Estimated) { this.Remove(candidate, _sequence.Count - 1); } } } - _sequence.AddToBack((vector, sample, kestimate)); + _sequence.AddToBack(new SequenceEntry(vector, sample, kestimate)); - while ((_t > 0 && (sample.Time - _sequence.PeekFirst().Item2.Time).TotalMilliseconds > _t) + while ((_t != TimeSpan.MaxValue && (sample.Time - _sequence.PeekFirst().Sample.Time) > _t) || (_k >= 0 && _sequence.Count > _k + 1)) { - var deletes = _sequence.PeekFirst().Item1; + var deletes = _sequence.PeekFirst().Candidates; _sequence.RemoveFromFront(); foreach (TCandidate candidate in deletes) @@ -165,7 +172,7 @@ public void Update(ICollection vector, in TSample sample) _counters.Remove(candidate); } - foreach (TCandidate candidate in _sequence.PeekFirst().Item1) + foreach (TCandidate candidate in _sequence.PeekFirst().Candidates) { candidate.Predecessor = null; } @@ -180,12 +187,12 @@ public void Update(ICollection vector, in TSample sample) protected void Remove(in TCandidate candidate, int index) { - if (_sequence[index].Item3 == candidate) + if (_sequence[index].Estimated == candidate) { return; } - var vector = _sequence[index].Item1; + var vector = _sequence[index].Candidates; _counters.Remove(candidate); vector.Remove(candidate); @@ -208,7 +215,7 @@ public ICollection Vector() } else { - return _sequence[_sequence.Count - 1].Item1; + return _sequence[_sequence.Count - 1].Candidates; } } @@ -220,7 +227,7 @@ public TCandidate Estimate() } TCandidate estimate = null; - foreach (TCandidate candidate in _sequence.PeekLast().Item1) + foreach (TCandidate candidate in _sequence.PeekLast().Candidates) { if (estimate == null || candidate.Filtprob > estimate.Filtprob) { @@ -238,25 +245,26 @@ public TCandidate Estimate() /// List of the most likely sequence of state candidates. public IEnumerable Sequence() { - var ksequence = new Deque(_sequence.Count); + var ksequence = new List(_sequence.Count); if (_sequence.Count > 0) { - TCandidate kestimate = _sequence.PeekLast().Item3; + var kestimate = _sequence.PeekLast().Estimated; for (int i = _sequence.Count - 1; i >= 0; --i) { if (kestimate != null) { - ksequence.AddToFront(kestimate); + ksequence.Add(kestimate); kestimate = kestimate.Predecessor; } else { - ksequence.AddToFront(_sequence[i].Item3); - kestimate = _sequence[i].Item3.Predecessor; + ksequence.Add(_sequence[i].Estimated); + kestimate = _sequence[i].Estimated.Predecessor; } } } + ksequence.Reverse(); return ksequence; } diff --git a/src/Sandwych.MapMatchingKit/Matching/MatcherSample.cs b/src/Sandwych.MapMatchingKit/Matching/MatcherSample.cs index 2b1edde..4d99192 100644 --- a/src/Sandwych.MapMatchingKit/Matching/MatcherSample.cs +++ b/src/Sandwych.MapMatchingKit/Matching/MatcherSample.cs @@ -12,7 +12,7 @@ namespace Sandwych.MapMatchingKit.Matching /// Measurement sample for Hidden Markov Model (HMM) map matching which is a position measurement, /// e.g. measured with a GPS device. ///
- public sealed class MatcherSample : ISample + public readonly struct MatcherSample : ISample { public long Id { get; } public DateTimeOffset Time { get; } diff --git a/test/Sandwych.MapMatchingKit.Tests/Markov/FilterTest.cs b/test/Sandwych.MapMatchingKit.Tests/Markov/FilterTest.cs index 918d9c0..32bb8d9 100644 --- a/test/Sandwych.MapMatchingKit.Tests/Markov/FilterTest.cs +++ b/test/Sandwych.MapMatchingKit.Tests/Markov/FilterTest.cs @@ -21,7 +21,7 @@ public MockElement(MockSample sample, int id) : base(sample) this.Id = id; } - public MockElement(int id, double filtprob, double seqprob) : this(null, id) + public MockElement(int id, double filtprob, double seqprob) : this(default, id) { this.Filtprob = filtprob; this.Seqprob = seqprob; diff --git a/test/Sandwych.MapMatchingKit.Tests/Markov/KStateTest.cs b/test/Sandwych.MapMatchingKit.Tests/Markov/KStateTest.cs index a2cf217..8f4ee44 100644 --- a/test/Sandwych.MapMatchingKit.Tests/Markov/KStateTest.cs +++ b/test/Sandwych.MapMatchingKit.Tests/Markov/KStateTest.cs @@ -17,7 +17,7 @@ private class MockElem : AbstractStateCandidate(1, -1); + var state = new KState(1, TimeSpan.MaxValue); { var vector = new HashSet() { elements[0], elements[1], elements[2] @@ -299,7 +299,7 @@ public void TestTState() elements.Add(1, new MockElem(1, Math.Log10(0.2), 0.2, null)); elements.Add(2, new MockElem(2, Math.Log10(0.5), 0.5, null)); - var state = new KState(-1, 1); + var state = new KState(-1, TimeSpan.FromMilliseconds(1)); { var vector = new HashSet() { elements[0], elements[1], elements[2] }; diff --git a/test/Sandwych.MapMatchingKit.Tests/Markov/MockSample.cs b/test/Sandwych.MapMatchingKit.Tests/Markov/MockSample.cs index 32a4e3b..73b27d5 100644 --- a/test/Sandwych.MapMatchingKit.Tests/Markov/MockSample.cs +++ b/test/Sandwych.MapMatchingKit.Tests/Markov/MockSample.cs @@ -5,7 +5,7 @@ namespace Sandwych.MapMatchingKit.Tests.Markov { - public sealed class MockSample : ISample + public readonly struct MockSample : ISample { public DateTimeOffset Time { get; } From cb07c977f47186c81cf4ebd063088adc8e9b9499 Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Thu, 22 Feb 2018 18:42:06 +0800 Subject: [PATCH 06/37] refactor KState --- src/Sandwych.MapMatchingKit/Markov/KState.cs | 14 +++++++++++--- 1 file changed, 11 insertions(+), 3 deletions(-) diff --git a/src/Sandwych.MapMatchingKit/Markov/KState.cs b/src/Sandwych.MapMatchingKit/Markov/KState.cs index 850339c..9ca7b3a 100644 --- a/src/Sandwych.MapMatchingKit/Markov/KState.cs +++ b/src/Sandwych.MapMatchingKit/Markov/KState.cs @@ -245,9 +245,9 @@ public TCandidate Estimate() /// List of the most likely sequence of state candidates. public IEnumerable Sequence() { - var ksequence = new List(_sequence.Count); if (_sequence.Count > 0) { + var ksequence = new List(_sequence.Count); var kestimate = _sequence.PeekLast().Estimated; for (int i = _sequence.Count - 1; i >= 0; --i) @@ -263,9 +263,17 @@ public IEnumerable Sequence() kestimate = _sequence[i].Estimated.Predecessor; } } + + if (ksequence.Count > 1) + { + ksequence.Reverse(); + } + return ksequence; + } + else + { + return new TCandidate[] { }; } - ksequence.Reverse(); - return ksequence; } } From 9b40efa400553b3b982dbda6fe2a573f8791aff7 Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Thu, 22 Feb 2018 22:14:34 +0800 Subject: [PATCH 07/37] clean code --- src/Sandwych.MapMatchingKit/Markov/AbstractFilter.cs | 8 ++------ 1 file changed, 2 insertions(+), 6 deletions(-) diff --git a/src/Sandwych.MapMatchingKit/Markov/AbstractFilter.cs b/src/Sandwych.MapMatchingKit/Markov/AbstractFilter.cs index 709d11c..f73ad95 100644 --- a/src/Sandwych.MapMatchingKit/Markov/AbstractFilter.cs +++ b/src/Sandwych.MapMatchingKit/Markov/AbstractFilter.cs @@ -116,11 +116,7 @@ public virtual ICollection Execute(IEnumerable predecess if (predecessors.Count() > 0) { - var states = new HashSet(); - foreach (var candidate in candidates) - { - states.Add(candidate.Candidate); - } + var states = candidates.Select(c => c.Candidate).Distinct(); var transitions = this.ComputeTransitions((previous, predecessors), (sample, states)); @@ -139,7 +135,7 @@ public virtual ICollection Execute(IEnumerable predecess continue; } - candidate_.Filtprob = candidate_.Filtprob + (transition.Probability * predecessor.Filtprob); + candidate_.Filtprob += transition.Probability * predecessor.Filtprob; var seqprob = predecessor.Seqprob + Math.Log10(transition.Probability) + Math.Log10(candidate.Probability); From 4405f594eae205ae02732ba2a3b2280a16e97b6e Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Fri, 23 Feb 2018 13:07:59 +0800 Subject: [PATCH 08/37] refactor KState --- src/Sandwych.MapMatchingKit/Markov/KState.cs | 52 +++++++++---------- .../Markov/KStateTest.cs | 4 +- 2 files changed, 28 insertions(+), 28 deletions(-) diff --git a/src/Sandwych.MapMatchingKit/Markov/KState.cs b/src/Sandwych.MapMatchingKit/Markov/KState.cs index 9ca7b3a..f0341ff 100644 --- a/src/Sandwych.MapMatchingKit/Markov/KState.cs +++ b/src/Sandwych.MapMatchingKit/Markov/KState.cs @@ -23,28 +23,30 @@ private readonly struct SequenceEntry { public ICollection Candidates { get; } public TSample Sample { get; } - public TCandidate Estimated { get; } + public TCandidate EstimatedCandidate { get; } public SequenceEntry(ICollection candidates, in TSample sample, in TCandidate estimated) { this.Candidates = candidates; this.Sample = sample; - this.Estimated = estimated; + this.EstimatedCandidate = estimated; } } - private readonly int _k = -1; - private readonly TimeSpan _t = TimeSpan.MaxValue; private readonly Deque _sequence; private readonly IDictionary _counters; + public int SequenceSizeBound { get; } = -1; + public TimeSpan SequenceIntervalBound { get; } = TimeSpan.MinValue; + /// /// Creates empty object with default parameters, i.e. capacity is unbounded. /// - public KState() : this(-1, TimeSpan.MaxValue) - { - } + public KState() : this(-1, TimeSpan.MinValue) { } + public KState(int k) : this(k, TimeSpan.MinValue) { } + + public KState(TimeSpan t) : this(-1, t) { } /// /// Creates an empty object and sets κ and τ parameters. @@ -53,8 +55,8 @@ public KState() : this(-1, TimeSpan.MaxValue) /// τ parameter bounds length of the state sequence to contain only states for the past τ milliseconds. public KState(int k, TimeSpan t) { - this._k = k; - this._t = t; + this.SequenceSizeBound = k; + this.SequenceIntervalBound = t; this._sequence = new Deque(); this._counters = new Dictionary(); } @@ -152,7 +154,7 @@ public void Update(ICollection vector, in TSample sample) foreach (TCandidate candidate in deletes) { - if (deletes.Count != size || candidate != last.Estimated) + if (deletes.Count != size || candidate != last.EstimatedCandidate) { this.Remove(candidate, _sequence.Count - 1); } @@ -161,8 +163,8 @@ public void Update(ICollection vector, in TSample sample) _sequence.AddToBack(new SequenceEntry(vector, sample, kestimate)); - while ((_t != TimeSpan.MaxValue && (sample.Time - _sequence.PeekFirst().Sample.Time) > _t) - || (_k >= 0 && _sequence.Count > _k + 1)) + while ((SequenceIntervalBound >= TimeSpan.Zero && (sample.Time - _sequence.PeekFirst().Sample.Time) > SequenceIntervalBound) + || (SequenceSizeBound >= 0 && _sequence.Count > SequenceSizeBound + 1)) { var deletes = _sequence.PeekFirst().Candidates; _sequence.RemoveFromFront(); @@ -178,7 +180,7 @@ public void Update(ICollection vector, in TSample sample) } } - bool assert = (_k < 0 || _sequence.Count <= _k + 1); + bool assert = (SequenceSizeBound < 0 || _sequence.Count <= SequenceSizeBound + 1); if (!assert) { throw new InvalidOperationException(); @@ -187,7 +189,7 @@ public void Update(ICollection vector, in TSample sample) protected void Remove(in TCandidate candidate, int index) { - if (_sequence[index].Estimated == candidate) + if (_sequence[index].EstimatedCandidate == candidate) { return; } @@ -245,30 +247,28 @@ public TCandidate Estimate() /// List of the most likely sequence of state candidates. public IEnumerable Sequence() { - if (_sequence.Count > 0) + IEnumerable EnumerateSequenceBackward() { - var ksequence = new List(_sequence.Count); - var kestimate = _sequence.PeekLast().Estimated; + var kestimate = _sequence.PeekLast().EstimatedCandidate; - for (int i = _sequence.Count - 1; i >= 0; --i) + foreach (var entry in _sequence.Reverse()) { if (kestimate != null) { - ksequence.Add(kestimate); + yield return kestimate; kestimate = kestimate.Predecessor; } else { - ksequence.Add(_sequence[i].Estimated); - kestimate = _sequence[i].Estimated.Predecessor; + yield return entry.EstimatedCandidate; + kestimate = entry.EstimatedCandidate.Predecessor; } } + } - if (ksequence.Count > 1) - { - ksequence.Reverse(); - } - return ksequence; + if (_sequence.Count > 0) + { + return EnumerateSequenceBackward().Reverse(); } else { diff --git a/test/Sandwych.MapMatchingKit.Tests/Markov/KStateTest.cs b/test/Sandwych.MapMatchingKit.Tests/Markov/KStateTest.cs index 8f4ee44..7eb8917 100644 --- a/test/Sandwych.MapMatchingKit.Tests/Markov/KStateTest.cs +++ b/test/Sandwych.MapMatchingKit.Tests/Markov/KStateTest.cs @@ -201,7 +201,7 @@ public void TestKState() elements.Add(1, new MockElem(1, Math.Log10(0.2), 0.2, null)); elements.Add(2, new MockElem(2, Math.Log10(0.5), 0.5, null)); - var state = new KState(1, TimeSpan.MaxValue); + var state = new KState(1); { var vector = new HashSet() { elements[0], elements[1], elements[2] @@ -299,7 +299,7 @@ public void TestTState() elements.Add(1, new MockElem(1, Math.Log10(0.2), 0.2, null)); elements.Add(2, new MockElem(2, Math.Log10(0.5), 0.5, null)); - var state = new KState(-1, TimeSpan.FromMilliseconds(1)); + var state = new KState(-1, TimeSpan.FromMilliseconds(1.0)); { var vector = new HashSet() { elements[0], elements[1], elements[2] }; From 2b23cf4eb214b75c0d026a8f9348bf74d310b9b7 Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Sun, 4 Mar 2018 12:14:08 +0800 Subject: [PATCH 09/37] Add UBODT(aka Precomputed Dijkstra) implementation --- Sandwych.MapMatchingKit.sln | 10 +- .../Program.cs | 8 +- src/Sandwych.MapMatchingKit/Roads/RoadMap.cs | 4 +- .../Roads/RoadMapBuilder.cs | 2 +- .../Sandwych.MapMatchingKit.csproj | 3 +- .../Topology/AbstractGraph.cs | 14 ++- .../Topology/DijkstraRouter.cs | 89 +++----------- .../Topology/IGraph.cs | 4 +- .../Topology/IGraphEdge.cs | 12 +- .../BoundedDijkstraShortestPathAlgorithm.cs | 60 ++++++++++ .../OutOfRadiusException.cs | 13 +++ .../PrecomputedDijkstraRouter.cs | 63 ++++++++++ .../PrecomputedDijkstraTable.cs | 79 +++++++++++++ .../PrecomputedDijkstraTableGenerator.cs | 63 ++++++++++ .../PrecomputedDijkstraTableRow.cs | 32 +++++ .../Topology/RouteMark.cs | 70 +++++++++++ .../Topology/Ubodt/UbodTable.cs | 10 -- .../Topology/Ubodt/UbodtRouter.cs | 37 ------ .../Topology/Ubodt/UbodtRow.cs | 16 --- .../Matching/MatcherTest.cs | 2 +- .../Sandwych.MapMatchingKit.Tests.csproj | 1 + .../Topology/AbstractRouterTest.cs | 40 +++---- .../Topology/PrecomputedDijkstra/MyGraph.cs | 110 ++++++++++++++++++ .../PrecomputedDijkstraTableTest.cs | 40 +++++++ .../Topology/UbodtRouterTest.cs | 3 +- 25 files changed, 593 insertions(+), 192 deletions(-) create mode 100644 src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/BoundedDijkstraShortestPathAlgorithm.cs create mode 100644 src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/OutOfRadiusException.cs create mode 100644 src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouter.cs create mode 100644 src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTable.cs create mode 100644 src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTableGenerator.cs create mode 100644 src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTableRow.cs create mode 100644 src/Sandwych.MapMatchingKit/Topology/RouteMark.cs delete mode 100644 src/Sandwych.MapMatchingKit/Topology/Ubodt/UbodTable.cs delete mode 100644 src/Sandwych.MapMatchingKit/Topology/Ubodt/UbodtRouter.cs delete mode 100644 src/Sandwych.MapMatchingKit/Topology/Ubodt/UbodtRow.cs create mode 100644 test/Sandwych.MapMatchingKit.Tests/Topology/PrecomputedDijkstra/MyGraph.cs create mode 100644 test/Sandwych.MapMatchingKit.Tests/Topology/PrecomputedDijkstra/PrecomputedDijkstraTableTest.cs diff --git a/Sandwych.MapMatchingKit.sln b/Sandwych.MapMatchingKit.sln index 657084f..982355a 100644 --- a/Sandwych.MapMatchingKit.sln +++ b/Sandwych.MapMatchingKit.sln @@ -17,10 +17,9 @@ Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Examples", "Examples", "{DF EndProject Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Sandwych.MapMatchingKit.Examples.HelloWorldApp", "examples\Sandwych.MapMatchingKit.Examples.HelloWorldApp\Sandwych.MapMatchingKit.Examples.HelloWorldApp.csproj", "{2CCF3F1B-FFF3-4153-952D-4564BEB4C11A}" EndProject +Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Source", "Source", "{CCB5D40B-40A8-43C2-B0E2-F2B6F5D73917}" +EndProject Global - GlobalSection(Performance) = preSolution - HasPerformanceSessions = true - EndGlobalSection GlobalSection(SolutionConfigurationPlatforms) = preSolution Debug|Any CPU = Debug|Any CPU Release|Any CPU = Release|Any CPU @@ -51,7 +50,9 @@ Global HideSolutionNode = FALSE EndGlobalSection GlobalSection(NestedProjects) = preSolution + {13A3865C-37AB-49B6-9687-CA285DF2EB04} = {CCB5D40B-40A8-43C2-B0E2-F2B6F5D73917} {0F1F7B8D-A56F-4028-9701-7636482404E9} = {5F02380C-9094-411E-9CB8-40B6259F79D8} + {B8F22581-A63E-4F9C-AF6B-A2115F00FD9C} = {CCB5D40B-40A8-43C2-B0E2-F2B6F5D73917} {6B856AA6-C7E4-4F3D-8D18-35871BAED45F} = {5F02380C-9094-411E-9CB8-40B6259F79D8} {2CCF3F1B-FFF3-4153-952D-4564BEB4C11A} = {DF6975B6-10B3-49EA-966D-0F623BB27BE9} EndGlobalSection @@ -67,4 +68,7 @@ Global GlobalSection(Performance) = preSolution HasPerformanceSessions = true EndGlobalSection + GlobalSection(Performance) = preSolution + HasPerformanceSessions = true + EndGlobalSection EndGlobal diff --git a/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs b/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs index e1ebe88..59d43d9 100644 --- a/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs +++ b/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs @@ -16,7 +16,7 @@ namespace Sandwych.MapMatchingKit.Examples.HelloWorldApp { class Program { - private static readonly string s_dataDir = Path.GetFullPath(Path.Combine(Directory.GetCurrentDirectory(), "..", "..", "data")); + private static readonly string s_dataDir = System.IO.Path.GetFullPath(System.IO.Path.Combine(Directory.GetCurrentDirectory(), "..", "..", "data")); static void Main(string[] args) { @@ -100,7 +100,7 @@ private static void OfflineMatch(Matcher matcher, IReadOnlyList s } } - var csvFile = Path.Combine(s_dataDir, "samples.output.csv"); + var csvFile = System.IO.Path.Combine(s_dataDir, "samples.output.csv"); Console.WriteLine("Writing output file: {0}", csvFile); File.WriteAllLines(csvFile, csvLines); } @@ -108,7 +108,7 @@ private static void OfflineMatch(Matcher matcher, IReadOnlyList s private static IEnumerable ReadSamples() { - var json = File.ReadAllText(Path.Combine(s_dataDir, @"samples.geojson")); + var json = File.ReadAllText(System.IO.Path.Combine(s_dataDir, @"samples.geojson")); var reader = new GeoJsonReader(); var fc = reader.Read(json); var timeFormat = "yyyy-MM-dd-HH.mm.ss"; @@ -127,7 +127,7 @@ private static IEnumerable ReadSamples() private static IEnumerable ReadRoads(ISpatialOperation spatial) { - var json = File.ReadAllText(Path.Combine(s_dataDir, @"osm-kunming-roads-network.geojson")); + var json = File.ReadAllText(System.IO.Path.Combine(s_dataDir, @"osm-kunming-roads-network.geojson")); var reader = new GeoJsonReader(); var fc = reader.Read(json); foreach (var feature in fc.Features) diff --git a/src/Sandwych.MapMatchingKit/Roads/RoadMap.cs b/src/Sandwych.MapMatchingKit/Roads/RoadMap.cs index 75b28a4..a480ffb 100644 --- a/src/Sandwych.MapMatchingKit/Roads/RoadMap.cs +++ b/src/Sandwych.MapMatchingKit/Roads/RoadMap.cs @@ -45,10 +45,10 @@ private IEnumerable Split(IEnumerable<(RoadInfo road, double fraction */ foreach (var point in points) { - yield return new RoadPoint(this.Edges[point.road.Id * 2], point.fraction, _spatial); + yield return new RoadPoint(this.EdgeMap[point.road.Id * 2], point.fraction, _spatial); var backwardRoadId = point.road.Id * 2 + 1; - if (this.Edges.TryGetValue(backwardRoadId, out var road)) + if (this.EdgeMap.TryGetValue(backwardRoadId, out var road)) { yield return new RoadPoint(road, 1.0 - point.fraction, _spatial); } diff --git a/src/Sandwych.MapMatchingKit/Roads/RoadMapBuilder.cs b/src/Sandwych.MapMatchingKit/Roads/RoadMapBuilder.cs index 93ac16a..7ecf0e0 100644 --- a/src/Sandwych.MapMatchingKit/Roads/RoadMapBuilder.cs +++ b/src/Sandwych.MapMatchingKit/Roads/RoadMapBuilder.cs @@ -58,7 +58,7 @@ private static RoadMap ConstructEdges(RoadMap graph) { var map = new Dictionary>(); - foreach (var edge in graph.Edges.Values) + foreach (var edge in graph.EdgeMap.Values) { if (!map.ContainsKey(edge.Source)) { diff --git a/src/Sandwych.MapMatchingKit/Sandwych.MapMatchingKit.csproj b/src/Sandwych.MapMatchingKit/Sandwych.MapMatchingKit.csproj index 09261c5..44b89c0 100644 --- a/src/Sandwych.MapMatchingKit/Sandwych.MapMatchingKit.csproj +++ b/src/Sandwych.MapMatchingKit/Sandwych.MapMatchingKit.csproj @@ -10,8 +10,9 @@ - + + diff --git a/src/Sandwych.MapMatchingKit/Topology/AbstractGraph.cs b/src/Sandwych.MapMatchingKit/Topology/AbstractGraph.cs index e53d632..7c3284c 100644 --- a/src/Sandwych.MapMatchingKit/Topology/AbstractGraph.cs +++ b/src/Sandwych.MapMatchingKit/Topology/AbstractGraph.cs @@ -6,11 +6,11 @@ namespace Sandwych.MapMatchingKit.Topology { - public abstract class AbstractGraph : IGraph + public abstract class AbstractGraph : QuickGraph.AdjacencyGraph, IGraph where TEdge : AbstractGraphEdge { private bool _constructed = false; - private readonly Dictionary _edges = new Dictionary(); + private readonly Dictionary _edgeMap = new Dictionary(); public AbstractGraph(IEnumerable edges) { @@ -18,17 +18,19 @@ public AbstractGraph(IEnumerable edges) { throw new ArgumentNullException(nameof(edges)); } + + this.AddVerticesAndEdgeRange(edges); foreach (var e in edges) { - _edges.Add(e.Id, e); + _edgeMap.Add(e.Id, e); } this.Construct(); } - public TEdge GetEdge(long id) => _edges[id]; + public TEdge GetEdge(long id) => _edgeMap[id]; - public IReadOnlyDictionary Edges => _edges; + public IReadOnlyDictionary EdgeMap => _edgeMap; protected virtual void Construct() { @@ -39,7 +41,7 @@ protected virtual void Construct() var map = new Dictionary>(); - foreach (var edge in this.Edges.Values) + foreach (var edge in this.EdgeMap.Values) { if (!map.ContainsKey(edge.Source)) { diff --git a/src/Sandwych.MapMatchingKit/Topology/DijkstraRouter.cs b/src/Sandwych.MapMatchingKit/Topology/DijkstraRouter.cs index 948edd6..900037e 100644 --- a/src/Sandwych.MapMatchingKit/Topology/DijkstraRouter.cs +++ b/src/Sandwych.MapMatchingKit/Topology/DijkstraRouter.cs @@ -20,69 +20,6 @@ public class DijkstraRouter : IGraphRouter { public ILogger Logger { get; set; } = NullLogger.Instance; - /// - /// Route mark representation. - /// - private readonly struct Mark : IComparable, IEquatable - { - public TEdge MarkedEdge { get; } - public TEdge PredecessorEdge { get; } - public double Cost { get; } - public double BoundingCost { get; } - - private readonly static Mark s_empty = new Mark(null, null, double.NaN, double.NaN); - public static ref readonly Mark Empty => ref s_empty; - public bool IsEmpty => double.IsNaN(this.Cost); - - /// - /// Constructor of an entry. - /// - /// {@link AbstractEdge} defining the route mark. - /// Predecessor {@link AbstractEdge}. - /// Cost value to this route mark. - /// Bounding cost value to this route mark. - public Mark(TEdge markedEdge, TEdge predecessorEdge, Double cost, Double boundingCost) - { - this.MarkedEdge = markedEdge; - this.PredecessorEdge = predecessorEdge; - this.Cost = cost; - this.BoundingCost = boundingCost; - } - - public int CompareTo(Mark other) - { - if (this.IsEmpty || other.IsEmpty) - { - throw new InvalidOperationException(); - } - - if (this.Cost < other.Cost) - { - return -1; - } - else if (this.Cost > other.Cost) - { - return 1; - } - else - { - return 0; - } - } - - public override int GetHashCode() => - (this.MarkedEdge, this.PredecessorEdge, this.Cost, this.BoundingCost).GetHashCode(); - - public bool Equals(Mark other) - { - if (this.IsEmpty || other.IsEmpty) - { - throw new InvalidOperationException(); - } - return this.CompareTo(other) == 0; - } - } - public IDictionary> Route(P source, IEnumerable

targets, Func cost, Func bound = null, double max = double.NaN) => Ssmt(source, targets, cost, bound, max); @@ -135,11 +72,11 @@ private IDictionary> Ssmt(P source, IEnumerable

targets /* * Setup data structures */ - var priorities = new PriorityQueue(); - var entries = new Dictionary(); - var finishs = new Dictionary(); - var reaches = new Dictionary(); - var starts = new Dictionary(); + var priorities = new PriorityQueue>(); + var entries = new Dictionary>(); + var finishs = new Dictionary>(); + var reaches = new Dictionary, P>(); + var starts = new Dictionary, P>(); /* * Initialize map of edges with start points @@ -175,7 +112,7 @@ private IDictionary> Ssmt(P source, IEnumerable

targets target, source.Edge.Id, source.Fraction, target.Fraction, reachcost); } - var reach = new Mark(source.Edge, null, reachcost, reachbound); + var reach = new RouteMark(source.Edge, null, reachcost, reachbound); reaches.Add(reach, target); starts.Add(reach, source); priorities.Enqueue(reach); @@ -189,7 +126,7 @@ private IDictionary> Ssmt(P source, IEnumerable

targets this.Logger.LogDebug("add source {0} with start edge {1} and fraction {2} with {3} cost", source, source.Edge.Id, source.Fraction, startcost); } - start = new Mark(source.Edge, null, startcost, startbound); + start = new RouteMark(source.Edge, null, startcost, startbound); entries[source.Edge] = start; starts[start] = source; priorities.Enqueue(start); @@ -203,7 +140,7 @@ private IDictionary> Ssmt(P source, IEnumerable

targets this.Logger.LogDebug("update source {0} with start edge {1} and fraction {2} with {3} cost", source, source.Edge.Id, source.Fraction, startcost); } - start = new Mark(source.Edge, null, startcost, startbound); + start = new RouteMark(source.Edge, null, startcost, startbound); entries[source.Edge] = start; starts[start] = source; priorities.Remove(start); @@ -294,7 +231,7 @@ private IDictionary> Ssmt(P source, IEnumerable

targets targetEdge, successor.Id, targetEdge.Fraction, reachcost); } - var reach = new Mark(successor, current.MarkedEdge, reachcost, reachbound); + var reach = new RouteMark(successor, current.MarkedEdge, reachcost, reachbound); reaches.Add(reach, targetEdge); priorities.Enqueue(reach); } @@ -306,7 +243,7 @@ private IDictionary> Ssmt(P source, IEnumerable

targets { this.Logger.LogDebug("added successor edge {0} with {1} cost", successor.Id, succcost); } - var mark = new Mark(successor, current.MarkedEdge, succcost, succbound); + var mark = new RouteMark(successor, current.MarkedEdge, succcost, succbound); entries.Add(successor, mark); priorities.Enqueue(mark); } @@ -321,7 +258,7 @@ private IDictionary> Ssmt(P source, IEnumerable

targets { var path = new List(); var iterator = finishs[targetPoint]; - var start = Mark.Empty; + var start = RouteMark.Empty; while (!iterator.IsEmpty) { path.Add(iterator.MarkedEdge); @@ -334,12 +271,12 @@ private IDictionary> Ssmt(P source, IEnumerable

targets } else { - iterator = Mark.Empty; + iterator = RouteMark.Empty; } } else { - iterator = Mark.Empty; + iterator = RouteMark.Empty; } } path.Reverse(); diff --git a/src/Sandwych.MapMatchingKit/Topology/IGraph.cs b/src/Sandwych.MapMatchingKit/Topology/IGraph.cs index 0b516f3..8cda033 100644 --- a/src/Sandwych.MapMatchingKit/Topology/IGraph.cs +++ b/src/Sandwych.MapMatchingKit/Topology/IGraph.cs @@ -4,10 +4,10 @@ namespace Sandwych.MapMatchingKit.Topology { - public interface IGraph + public interface IGraph : QuickGraph.IVertexAndEdgeListGraph where TEdge : IGraphEdge { TEdge GetEdge(long id); - IReadOnlyDictionary Edges { get; } + IReadOnlyDictionary EdgeMap { get; } } } diff --git a/src/Sandwych.MapMatchingKit/Topology/IGraphEdge.cs b/src/Sandwych.MapMatchingKit/Topology/IGraphEdge.cs index 23d5d9c..304d8cb 100644 --- a/src/Sandwych.MapMatchingKit/Topology/IGraphEdge.cs +++ b/src/Sandwych.MapMatchingKit/Topology/IGraphEdge.cs @@ -10,7 +10,7 @@ namespace Sandwych.MapMatchingKit.Topology /// Implementation of in a directed graph. /// (Use the curiously recurring template pattern (CRTP) for type-safe use of customized edge type.) /// - public interface IGraphEdge : IEquatable + public interface IGraphEdge : QuickGraph.IEdge, IEquatable where T : IGraphEdge { ///

@@ -18,16 +18,6 @@ public interface IGraphEdge : IEquatable /// long Id { get; } - /// - /// Gets the edge's source vertex. - /// - long Source { get; } - - /// - /// Gets the edge's target vertex. - /// - long Target { get; } - /// /// Gets the edge's neighbor. /// diff --git a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/BoundedDijkstraShortestPathAlgorithm.cs b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/BoundedDijkstraShortestPathAlgorithm.cs new file mode 100644 index 0000000..23f5047 --- /dev/null +++ b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/BoundedDijkstraShortestPathAlgorithm.cs @@ -0,0 +1,60 @@ +using System; +using System.Collections.Generic; +using System.Text; +using QuickGraph; +using QuickGraph.Algorithms.ShortestPath; + +namespace Sandwych.MapMatchingKit.Topology.PrecomputedDijkstra +{ + + public class BoundedDijkstraShortestPathAlgorithm + where TVertex : IEquatable + where TEdge : IEdge + { + private readonly HashSet _visitedVertices = new HashSet(); + private readonly Dictionary _vertexPredecessors = new Dictionary(); + + public DijkstraShortestPathAlgorithm Algorithm { get; } + public double MaxRadius { get; } + public IEnumerable VisitedVertices => _visitedVertices; + public IReadOnlyDictionary Predecessors => _vertexPredecessors; + + public BoundedDijkstraShortestPathAlgorithm(IVertexAndEdgeListGraph graph, Func cost, double maxRadius) + { + this.Algorithm = new DijkstraShortestPathAlgorithm(graph, cost); + this.Algorithm.ExamineVertex += this.ExamineVertex; + this.Algorithm.TreeEdge += this.OnTreeEdge; + this.MaxRadius = maxRadius; + } + + public void Compute(TVertex rootVertex) + { + _vertexPredecessors.Clear(); + _visitedVertices.Clear(); + this.Algorithm.Compute(rootVertex); + } + + public double GetDistance(TVertex vertex) => + this.Algorithm.Distances[vertex]; + + public bool TryGetDistance(TVertex vertex, out double distance) => + this.Algorithm.TryGetDistance(vertex, out distance); + + private void ExamineVertex(TVertex vertex) + { + if (this.Algorithm.Distances[vertex] > this.MaxRadius) + { + throw new OutOfRadiusException(); + } + + this._visitedVertices.Add(vertex); + } + + private void OnTreeEdge(TEdge e) => + _vertexPredecessors[e.Target] = e; + + public bool TryGetPath(TVertex vertex, out IEnumerable path) => + this._vertexPredecessors.TryGetPath(vertex, out path); + + } +} diff --git a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/OutOfRadiusException.cs b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/OutOfRadiusException.cs new file mode 100644 index 0000000..01a65a6 --- /dev/null +++ b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/OutOfRadiusException.cs @@ -0,0 +1,13 @@ +using System; +using System.Collections.Generic; +using System.Text; + +namespace Sandwych.MapMatchingKit.Topology.PrecomputedDijkstra +{ + + public class OutOfRadiusException : Exception + { + + } + +} diff --git a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouter.cs b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouter.cs new file mode 100644 index 0000000..5a4f268 --- /dev/null +++ b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouter.cs @@ -0,0 +1,63 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using Microsoft.Extensions.Logging; +using QuickGraph.Algorithms; +using QuickGraph.Algorithms.Observers; +using QuickGraph.Algorithms.ShortestPath; +using Sandwych.MapMatchingKit.Roads; +using Sandwych.MapMatchingKit.Utility; + +namespace Sandwych.MapMatchingKit.Topology.PrecomputedDijkstra +{ + public class PrecomputedDijkstraRouter : IGraphRouter + where TEdge : class, IGraphEdge + where P : IEdgePoint, IEquatable

+ { + public ILogger Logger { get; set; } = NullLogger.Instance; + + private readonly IGraph _graph; + private readonly Lazy> _ubodt; + private readonly Func _edgeCost; + private readonly Func _bound; + private readonly double _maxRadius; + + public PrecomputedDijkstraRouter(IGraph graph, Func cost, Func bound, double max) + { + _graph = graph; + _edgeCost = cost; + _bound = bound; + _maxRadius = max; + _ubodt = new Lazy>(() => CreateTable(), true); + } + + public IDictionary> Route(P source, IEnumerable

targets, Func cost, + Func bound = null, double max = double.NaN) + { + throw new NotImplementedException(); + } + + public IDictionary)> Route(IEnumerable

sources, IEnumerable

targets, Func cost = null, + Func bound = null, double max = double.NaN) + { + throw new NotImplementedException(); + } + + public IEnumerable Route(P source, P target, Func cost, Func bound = null, double max = double.NaN) + { + throw new NotImplementedException(); + } + + private PrecomputedDijkstraTable CreateTable() + { + var generator = new PrecomputedDijkstraTableGenerator(); + var rows = generator.ComputeRows(_graph, _edgeCost, _maxRadius); + return new PrecomputedDijkstraTable(rows); + } + } + +} + + + diff --git a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTable.cs b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTable.cs new file mode 100644 index 0000000..9aa6e5c --- /dev/null +++ b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTable.cs @@ -0,0 +1,79 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using QuickGraph; +using System.Text; + +namespace Sandwych.MapMatchingKit.Topology.PrecomputedDijkstra +{ + + public sealed class PrecomputedDijkstraTable : Dictionary<(TVertex, TVertex), PrecomputedDijkstraTableRow> + where TEdge : class, IEdge + where TVertex : IEquatable + { + public PrecomputedDijkstraTable() : base() + { + + } + + public PrecomputedDijkstraTable(IEnumerable> rows) : + this(rows.Count()) + { + foreach (var row in rows) + { + var pair = row.ToKeyValuePair(); + this.Add(pair.Key, pair.Value); + } + } + + public PrecomputedDijkstraTable(int capacity) : base(capacity) + { + } + + public IEnumerable GetPathByEdge(TEdge sourceEdge, TEdge targetEdge) + { + if (sourceEdge == targetEdge) + { + yield break; + } + else if (sourceEdge.Target.Equals(targetEdge.Source)) + { + yield return sourceEdge; + yield return targetEdge; + yield break; + } + else + { + var sourceVertex = sourceEdge.Target; + var targetVertex = targetEdge.Source; + var path = this.GetPathByVertex(sourceVertex, targetVertex); + foreach (var edge in path) + { + yield return edge; + } + } + } + + public IEnumerable GetPathByVertex(TVertex sourceVertex, TVertex targetVertex) + { + if (this.TryGetValue((sourceVertex, targetVertex), out var row)) + { + //now we got the first edge, then we started from the next row + yield return row.SourceEdge; + var currentStart = row.NextVertex; + + while (!currentStart.Equals(targetVertex)) + { + row = this[(currentStart, targetVertex)]; + yield return row.SourceEdge; + currentStart = row.NextVertex; + } + } + else + { + yield break; + } + } + + } +} diff --git a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTableGenerator.cs b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTableGenerator.cs new file mode 100644 index 0000000..b46ea60 --- /dev/null +++ b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTableGenerator.cs @@ -0,0 +1,63 @@ +using System; +using System.Collections.Generic; +using QuickGraph; + +namespace Sandwych.MapMatchingKit.Topology.PrecomputedDijkstra +{ + public class PrecomputedDijkstraTableGenerator + where TEdge : class, IEdge + where TVertex : IEquatable + + { + + public IEnumerable> ComputeRows( + IVertexAndEdgeListGraph graph, + Func cost, double maxRadius) + { + var dijkstra = new BoundedDijkstraShortestPathAlgorithm(graph, cost, maxRadius); + + foreach (var rootVertex in graph.Vertices) + { + var rows = this.ComputeRowsSingleSource(graph, dijkstra, rootVertex); + foreach (var row in rows) + { + yield return row; + } + } + } + + public IEnumerable> ComputeRowsSingleSource( + IVertexAndEdgeListGraph graph, + BoundedDijkstraShortestPathAlgorithm dijkstra, + TVertex sourceVertex) + { + + try + { + dijkstra.Compute(sourceVertex); + } + catch (OutOfRadiusException) + { + } + + var pred = dijkstra.Predecessors; + foreach (var u in dijkstra.VisitedVertices) + { + if (u.Equals(sourceVertex)) + { + continue; + } + + var v = u; + while (!pred[v].Source.Equals(sourceVertex)) + { + v = pred[v].Source; + } + graph.TryGetEdge(sourceVertex, v, out var sourceEdge); + var targetEdge = pred[u]; + var row = new PrecomputedDijkstraTableRow(sourceEdge, targetEdge, dijkstra.GetDistance(u)); + yield return row; + } + } + } +} diff --git a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTableRow.cs b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTableRow.cs new file mode 100644 index 0000000..f775dc7 --- /dev/null +++ b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTableRow.cs @@ -0,0 +1,32 @@ +using QuickGraph; +using System; +using System.Collections.Generic; +using System.Text; + +namespace Sandwych.MapMatchingKit.Topology.PrecomputedDijkstra +{ + public class PrecomputedDijkstraTableRow + where TVertex : IEquatable + where TEdge : class, IEdge + { + public TEdge SourceEdge { get; } + public TEdge TargetEdge { get; } + public double Distance { get; } + + public TVertex SourceVertex => this.SourceEdge.Source; + public TVertex TargetVertex => this.TargetEdge.Target; + public TVertex NextVertex => this.SourceEdge.Target; + + public PrecomputedDijkstraTableRow(TEdge s, TEdge t, double distance) + { + this.SourceEdge = s ?? throw new ArgumentNullException(nameof(s)); + this.TargetEdge = t ?? throw new ArgumentNullException(nameof(t)); + this.Distance = distance; + } + + public KeyValuePair<(TVertex, TVertex), PrecomputedDijkstraTableRow> ToKeyValuePair() => + new KeyValuePair<(TVertex, TVertex), PrecomputedDijkstraTableRow>((this.SourceVertex, this.TargetVertex), this); + } + + +} diff --git a/src/Sandwych.MapMatchingKit/Topology/RouteMark.cs b/src/Sandwych.MapMatchingKit/Topology/RouteMark.cs new file mode 100644 index 0000000..61a6abb --- /dev/null +++ b/src/Sandwych.MapMatchingKit/Topology/RouteMark.cs @@ -0,0 +1,70 @@ +using System; +using System.Collections.Generic; +using System.Text; + +namespace Sandwych.MapMatchingKit.Topology +{ + ///

+ /// Route mark representation. + /// + internal readonly struct RouteMark : IComparable>, IEquatable> + where TEdge : class, IGraphEdge + { + public TEdge MarkedEdge { get; } + public TEdge PredecessorEdge { get; } + public double Cost { get; } + public double BoundingCost { get; } + + private readonly static RouteMark s_empty = new RouteMark(null, null, double.NaN, double.NaN); + public static ref readonly RouteMark Empty => ref s_empty; + public bool IsEmpty => double.IsNaN(this.Cost); + + /// + /// Constructor of an entry. + /// + /// {@link AbstractEdge} defining the route mark. + /// Predecessor {@link AbstractEdge}. + /// Cost value to this route mark. + /// Bounding cost value to this route mark. + public RouteMark(TEdge markedEdge, TEdge predecessorEdge, Double cost, Double boundingCost) + { + this.MarkedEdge = markedEdge; + this.PredecessorEdge = predecessorEdge; + this.Cost = cost; + this.BoundingCost = boundingCost; + } + + public int CompareTo(RouteMark other) + { + if (this.IsEmpty || other.IsEmpty) + { + throw new InvalidOperationException(); + } + + if (this.Cost < other.Cost) + { + return -1; + } + else if (this.Cost > other.Cost) + { + return 1; + } + else + { + return 0; + } + } + + public override int GetHashCode() => + (this.MarkedEdge, this.PredecessorEdge, this.Cost, this.BoundingCost).GetHashCode(); + + public bool Equals(RouteMark other) + { + if (this.IsEmpty || other.IsEmpty) + { + throw new InvalidOperationException(); + } + return this.CompareTo(other) == 0; + } + } +} diff --git a/src/Sandwych.MapMatchingKit/Topology/Ubodt/UbodTable.cs b/src/Sandwych.MapMatchingKit/Topology/Ubodt/UbodTable.cs deleted file mode 100644 index 2b69617..0000000 --- a/src/Sandwych.MapMatchingKit/Topology/Ubodt/UbodTable.cs +++ /dev/null @@ -1,10 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Text; - -namespace Sandwych.MapMatchingKit.Topology -{ - public sealed class UbodTable - { - } -} diff --git a/src/Sandwych.MapMatchingKit/Topology/Ubodt/UbodtRouter.cs b/src/Sandwych.MapMatchingKit/Topology/Ubodt/UbodtRouter.cs deleted file mode 100644 index 9c5e9d5..0000000 --- a/src/Sandwych.MapMatchingKit/Topology/Ubodt/UbodtRouter.cs +++ /dev/null @@ -1,37 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Text; -using Microsoft.Extensions.Logging; -using Sandwych.MapMatchingKit.Roads; -using Sandwych.MapMatchingKit.Utility; - -namespace Sandwych.MapMatchingKit.Topology -{ - public class UbodtRouter : IGraphRouter - where TEdge : class, IGraphEdge - where P : IEdgePoint, IEquatable

- { - public ILogger Logger { get; set; } = NullLogger.Instance; - - public IDictionary> Route(P source, IEnumerable

targets, Func cost, - Func bound = null, double max = double.NaN) - { - throw new NotImplementedException(); - } - - public IDictionary)> Route(IEnumerable

sources, IEnumerable

targets, Func cost = null, - Func bound = null, double max = double.NaN) - { - throw new NotImplementedException(); - } - - public IEnumerable Route(P source, P target, Func cost, Func bound = null, double max = double.NaN) - { - throw new NotImplementedException(); - } - } - -} - - - diff --git a/src/Sandwych.MapMatchingKit/Topology/Ubodt/UbodtRow.cs b/src/Sandwych.MapMatchingKit/Topology/Ubodt/UbodtRow.cs deleted file mode 100644 index f60dc65..0000000 --- a/src/Sandwych.MapMatchingKit/Topology/Ubodt/UbodtRow.cs +++ /dev/null @@ -1,16 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Text; - -namespace Sandwych.MapMatchingKit.Topology -{ - public readonly struct UbodtRow - { - public long Source { get; } - public long Target { get; } - public long NextNode { get; } - public long PrevNode { get; } - public long NextEdge { get; } - public double Cost { get; } - } -} diff --git a/test/Sandwych.MapMatchingKit.Tests/Matching/MatcherTest.cs b/test/Sandwych.MapMatchingKit.Tests/Matching/MatcherTest.cs index ec30279..bc5159d 100644 --- a/test/Sandwych.MapMatchingKit.Tests/Matching/MatcherTest.cs +++ b/test/Sandwych.MapMatchingKit.Tests/Matching/MatcherTest.cs @@ -95,7 +95,7 @@ private void AssertTransition(in TransitionProbability transi private ISet RefSet(Coordinate2D sample, double radius) { var refset = new HashSet(); - foreach (var road in _map.Edges.Values) + foreach (var road in _map.EdgeMap.Values) { double f = _spatial.Intercept(road.Geometry, sample); var i = _spatial.Interpolate(road.Geometry, f); diff --git a/test/Sandwych.MapMatchingKit.Tests/Sandwych.MapMatchingKit.Tests.csproj b/test/Sandwych.MapMatchingKit.Tests/Sandwych.MapMatchingKit.Tests.csproj index cb2f4e3..9a0949c 100644 --- a/test/Sandwych.MapMatchingKit.Tests/Sandwych.MapMatchingKit.Tests.csproj +++ b/test/Sandwych.MapMatchingKit.Tests/Sandwych.MapMatchingKit.Tests.csproj @@ -5,6 +5,7 @@ Library latest + Sandwych.MapMatchingKit.Tests diff --git a/test/Sandwych.MapMatchingKit.Tests/Topology/AbstractRouterTest.cs b/test/Sandwych.MapMatchingKit.Tests/Topology/AbstractRouterTest.cs index 82b8496..3162399 100644 --- a/test/Sandwych.MapMatchingKit.Tests/Topology/AbstractRouterTest.cs +++ b/test/Sandwych.MapMatchingKit.Tests/Topology/AbstractRouterTest.cs @@ -57,23 +57,23 @@ public void TestSameRoad() AssertSinglePath( expectedPath: new long[] { 0L }, - sources: new RoadPoint[] { new RoadPoint(map.Edges[0L], 0.3) }, - targets: new RoadPoint[] { new RoadPoint(map.Edges[0L], 0.3) }); + sources: new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.3) }, + targets: new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.3) }); AssertSinglePath( expectedPath: new long[] { 0L }, - sources: new RoadPoint[] { new RoadPoint(map.Edges[0L], 0.3) }, - targets: new RoadPoint[] { new RoadPoint(map.Edges[0L], 0.7) }); + sources: new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.3) }, + targets: new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.7) }); AssertSinglePath( expectedPath: new long[] { 0L, 1L, 0L }, - sources: new RoadPoint[] { new RoadPoint(map.Edges[0L], 0.7) }, - targets: new RoadPoint[] { new RoadPoint(map.Edges[0L], 0.3) }); + sources: new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.7) }, + targets: new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.3) }); AssertSinglePath( expectedPath: new long[] { 1L, 0L }, - sources: new RoadPoint[] { new RoadPoint(map.Edges[0], 0.8), new RoadPoint(map.Edges[1L], 0.2) }, - targets: new RoadPoint[] { new RoadPoint(map.Edges[0L], 0.7) }); + sources: new RoadPoint[] { new RoadPoint(map.EdgeMap[0], 0.8), new RoadPoint(map.EdgeMap[1L], 0.2) }, + targets: new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.7) }); } [Fact] @@ -87,23 +87,23 @@ public void TestSelfLoop() AssertSinglePath( expectedPath: new long[] { 0L }, - sources: new RoadPoint[] { new RoadPoint(map.Edges[0L], 0.3) }, - targets: new RoadPoint[] { new RoadPoint(map.Edges[0L], 0.7) }); + sources: new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.3) }, + targets: new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.7) }); AssertSinglePath( expectedPath: new long[] { 0L, 0L }, - sources: new RoadPoint[] { new RoadPoint(map.Edges[0L], 0.7) }, - targets: new RoadPoint[] { new RoadPoint(map.Edges[0L], 0.3) }); + sources: new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.7) }, + targets: new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.3) }); AssertSinglePath( expectedPath: new long[] { 0L, 0L }, - sources: new RoadPoint[] { new RoadPoint(map.Edges[0L], 0.8), new RoadPoint(map.Edges[1L], 0.2) }, - targets: new RoadPoint[] { new RoadPoint(map.Edges[0L], 0.2) }); + sources: new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.8), new RoadPoint(map.EdgeMap[1L], 0.2) }, + targets: new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.2) }); AssertSinglePath( expectedPath: new long[] { 1L, 0L }, - sources: new RoadPoint[] { new RoadPoint(map.Edges[0L], 0.4), new RoadPoint(map.Edges[1L], 0.6) }, - targets: new RoadPoint[] { new RoadPoint(map.Edges[0L], 0.3) }); + sources: new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.4), new RoadPoint(map.EdgeMap[1L], 0.6) }, + targets: new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.3) }); } [Fact] @@ -138,8 +138,8 @@ public void TestShortestPath() }; AssertMultiplePaths( expectedPaths: paths, - sources: new RoadPoint[] { new RoadPoint(map.Edges[0], 0.3), new RoadPoint(map.Edges[1], 0.7) }, - targets: new RoadPoint[] { new RoadPoint(map.Edges[14], 0.3), new RoadPoint(map.Edges[15], 0.7) }); + sources: new RoadPoint[] { new RoadPoint(map.EdgeMap[0], 0.3), new RoadPoint(map.EdgeMap[1], 0.7) }, + targets: new RoadPoint[] { new RoadPoint(map.EdgeMap[14], 0.3), new RoadPoint(map.EdgeMap[15], 0.7) }); } { // (0.7, 100) + 50 + 100 + (0.1, 200) = 240 @@ -149,8 +149,8 @@ public void TestShortestPath() }; AssertMultiplePaths( expectedPaths: paths, - sources: new RoadPoint[] { new RoadPoint(map.Edges[0], 0.3), new RoadPoint(map.Edges[1], 0.7) }, - targets: new RoadPoint[] { new RoadPoint(map.Edges[14], 0.1), new RoadPoint(map.Edges[15], 0.9) }); + sources: new RoadPoint[] { new RoadPoint(map.EdgeMap[0], 0.3), new RoadPoint(map.EdgeMap[1], 0.7) }, + targets: new RoadPoint[] { new RoadPoint(map.EdgeMap[14], 0.1), new RoadPoint(map.EdgeMap[15], 0.9) }); } var router = new DijkstraRouter(); diff --git a/test/Sandwych.MapMatchingKit.Tests/Topology/PrecomputedDijkstra/MyGraph.cs b/test/Sandwych.MapMatchingKit.Tests/Topology/PrecomputedDijkstra/MyGraph.cs new file mode 100644 index 0000000..c842b47 --- /dev/null +++ b/test/Sandwych.MapMatchingKit.Tests/Topology/PrecomputedDijkstra/MyGraph.cs @@ -0,0 +1,110 @@ +using System; +using System.Collections.Generic; +using System.Text; +using QuickGraph; + +namespace Sandwych.MapMatchingKit.Tests.Topology.PrecomputedDijkstra +{ + public static class MyGraph + { + private static readonly AdjacencyGraph> graph; + private static readonly Dictionary, double> edgeCost; + + public static AdjacencyGraph> GraphInstance => graph; + public static IReadOnlyDictionary, double> EdgeCosts => edgeCost; + + static MyGraph() + { + graph = new AdjacencyGraph>(); + + // Add some vertices to the graph + graph.AddVertex("A"); + graph.AddVertex("B"); + graph.AddVertex("C"); + graph.AddVertex("D"); + graph.AddVertex("E"); + graph.AddVertex("F"); + graph.AddVertex("G"); + graph.AddVertex("H"); + graph.AddVertex("I"); + graph.AddVertex("J"); + + // Create the edges + Edge a_b = new Edge("A", "B"); + Edge a_d = new Edge("A", "D"); + Edge b_a = new Edge("B", "A"); + Edge b_c = new Edge("B", "C"); + Edge b_e = new Edge("B", "E"); + Edge c_b = new Edge("C", "B"); + Edge c_f = new Edge("C", "F"); + Edge c_j = new Edge("C", "J"); + Edge d_e = new Edge("D", "E"); + Edge d_g = new Edge("D", "G"); + Edge e_d = new Edge("E", "D"); + Edge e_f = new Edge("E", "F"); + Edge e_h = new Edge("E", "H"); + Edge f_i = new Edge("F", "I"); + Edge f_j = new Edge("F", "J"); + Edge g_d = new Edge("G", "D"); + Edge g_h = new Edge("G", "H"); + Edge h_g = new Edge("H", "G"); + Edge h_i = new Edge("H", "I"); + Edge i_f = new Edge("I", "F"); + Edge i_j = new Edge("I", "J"); + Edge i_h = new Edge("I", "H"); + Edge j_f = new Edge("J", "F"); + + // Add the edges + graph.AddEdge(a_b); + graph.AddEdge(a_d); + graph.AddEdge(b_a); + graph.AddEdge(b_c); + graph.AddEdge(b_e); + graph.AddEdge(c_b); + graph.AddEdge(c_f); + graph.AddEdge(c_j); + graph.AddEdge(d_e); + graph.AddEdge(d_g); + graph.AddEdge(e_d); + graph.AddEdge(e_f); + graph.AddEdge(e_h); + graph.AddEdge(f_i); + graph.AddEdge(f_j); + graph.AddEdge(g_d); + graph.AddEdge(g_h); + graph.AddEdge(h_g); + graph.AddEdge(h_i); + graph.AddEdge(i_f); + graph.AddEdge(i_h); + graph.AddEdge(i_j); + graph.AddEdge(j_f); + + // Define some weights to the edges + edgeCost = new Dictionary, double>(graph.EdgeCount); + edgeCost.Add(a_b, 4); + edgeCost.Add(a_d, 1); + edgeCost.Add(b_a, 74); + edgeCost.Add(b_c, 2); + edgeCost.Add(b_e, 12); + edgeCost.Add(c_b, 12); + edgeCost.Add(c_f, 74); + edgeCost.Add(c_j, 12); + edgeCost.Add(d_e, 32); + edgeCost.Add(d_g, 22); + edgeCost.Add(e_d, 66); + edgeCost.Add(e_f, 76); + edgeCost.Add(e_h, 33); + edgeCost.Add(f_i, 11); + edgeCost.Add(f_j, 21); + edgeCost.Add(g_d, 12); + edgeCost.Add(g_h, 10); + edgeCost.Add(h_g, 2); + edgeCost.Add(h_i, 72); + edgeCost.Add(i_f, 31); + edgeCost.Add(i_h, 18); + edgeCost.Add(i_j, 7); + edgeCost.Add(j_f, 8); + } + + } +} diff --git a/test/Sandwych.MapMatchingKit.Tests/Topology/PrecomputedDijkstra/PrecomputedDijkstraTableTest.cs b/test/Sandwych.MapMatchingKit.Tests/Topology/PrecomputedDijkstra/PrecomputedDijkstraTableTest.cs new file mode 100644 index 0000000..b2d1bc1 --- /dev/null +++ b/test/Sandwych.MapMatchingKit.Tests/Topology/PrecomputedDijkstra/PrecomputedDijkstraTableTest.cs @@ -0,0 +1,40 @@ +using System; +using System.Collections.Generic; +using System.Text; +using System.Linq; +using QuickGraph; +using Xunit; +using Sandwych.MapMatchingKit.Topology.PrecomputedDijkstra; + +namespace Sandwych.MapMatchingKit.Tests.Topology.PrecomputedDijkstra +{ + public class PrecomputedDijkstraTableTest + { + [Theory] + [InlineData("A", "B")] + [InlineData("A", "J")] + [InlineData("C", "E")] + public void TestGetPathByVertex(string sourceVertex, string targetVertex) + { + var maxRadius = 500D; + + var naiveDijkstra = new BoundedDijkstraShortestPathAlgorithm>( + MyGraph.GraphInstance, e => MyGraph.EdgeCosts[e], maxRadius); + naiveDijkstra.Compute(sourceVertex); + + var generator = new PrecomputedDijkstraTableGenerator>(); + var rows = generator.ComputeRows(MyGraph.GraphInstance, e => MyGraph.EdgeCosts[e], maxRadius); + + var table = new PrecomputedDijkstraTable>(rows); + var actualPath = table.GetPathByVertex(sourceVertex, targetVertex); + var actualDistance = actualPath.Sum(e => MyGraph.EdgeCosts[e]); + + Assert.True(naiveDijkstra.TryGetPath(targetVertex, out var expectedPath)); + Assert.NotNull(actualPath); + Assert.NotEmpty(actualPath); + var expectedDistance = expectedPath.Sum(e => MyGraph.EdgeCosts[e]); + Assert.Equal(expectedPath, actualPath); + Assert.Equal(expectedDistance, actualDistance, 8); + } + } +} diff --git a/test/Sandwych.MapMatchingKit.Tests/Topology/UbodtRouterTest.cs b/test/Sandwych.MapMatchingKit.Tests/Topology/UbodtRouterTest.cs index 1e1d7f6..cd79a79 100644 --- a/test/Sandwych.MapMatchingKit.Tests/Topology/UbodtRouterTest.cs +++ b/test/Sandwych.MapMatchingKit.Tests/Topology/UbodtRouterTest.cs @@ -5,8 +5,7 @@ namespace Sandwych.MapMatchingKit.Tests.Topology { - public class UbodtRouterTest : AbstractRouterTest + public class UbodtRouterTest : TestBase { - protected override IGraphRouter CreateRouter() => new UbodtRouter(); } } From a3a890fac2542bad6120af07e5895430db1be207 Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Sun, 4 Mar 2018 23:54:46 +0800 Subject: [PATCH 10/37] more ubodt implementation --- .../Program.cs | 11 +- .../Matching/Matcher.cs | 6 +- .../Topology/DijkstraRouter.cs | 8 +- .../Topology/IGraphRouter.cs | 4 +- .../BoundedDijkstraShortestPathAlgorithm.cs | 40 +++- .../PrecomputedDijkstraRouter.cs | 102 +++++++-- .../PrecomputedDijkstraTable.cs | 48 ++++- .../PrecomputedDijkstraTableGenerator.cs | 6 +- .../Matching/MatcherTest.cs | 4 +- .../Topology/AbstractRouterTest.cs | 109 ++++------ .../Topology/DijkstraRouterTest.cs | 6 +- .../PrecomputedDijkstraRouterTest.cs | 15 ++ .../PrecomputedDijkstraTableTest.cs | 5 +- .../Topology/RouterTestData.cs | 195 ++++++++++++++++++ .../Topology/UbodtRouterTest.cs | 11 - 15 files changed, 443 insertions(+), 127 deletions(-) create mode 100644 test/Sandwych.MapMatchingKit.Tests/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouterTest.cs create mode 100644 test/Sandwych.MapMatchingKit.Tests/Topology/RouterTestData.cs delete mode 100644 test/Sandwych.MapMatchingKit.Tests/Topology/UbodtRouterTest.cs diff --git a/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs b/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs index 59d43d9..a98faf4 100644 --- a/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs +++ b/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs @@ -28,7 +28,8 @@ static void Main(string[] args) var map = mapBuilder.AddRoads(roads).Build(); Console.WriteLine("The road map has been loaded"); - var matcher = new Matcher(map, new DijkstraRouter(), Costs.TimePriorityCost, spatial); + var matcher = new Matcher( + map, new DijkstraRouter(), Costs.TimePriorityCost, spatial); matcher.MaxDistance = 1000; // set maximum searching distance between two GPS points to 1000 meters. matcher.MaxRadius = 200.0; // sets maximum radius for candidate selection to 200 meters @@ -48,7 +49,9 @@ static void Main(string[] args) Console.ReadKey(); } - private static void OnlineMatch(Matcher matcher, IReadOnlyList samples) + private static void OnlineMatch( + Matcher matcher, + IReadOnlyList samples) { // Create initial (empty) state memory var kstate = new MatcherKState(); @@ -67,7 +70,9 @@ private static void OnlineMatch(Matcher matcher, IReadOnlyList sa } } - private static void OfflineMatch(Matcher matcher, IReadOnlyList samples) + private static void OfflineMatch( + Matcher matcher, + IReadOnlyList samples) { var kstate = new MatcherKState(); diff --git a/src/Sandwych.MapMatchingKit/Matching/Matcher.cs b/src/Sandwych.MapMatchingKit/Matching/Matcher.cs index 9df7b8a..5fb65f0 100644 --- a/src/Sandwych.MapMatchingKit/Matching/Matcher.cs +++ b/src/Sandwych.MapMatchingKit/Matching/Matcher.cs @@ -17,7 +17,11 @@ namespace Sandwych.MapMatchingKit.Matching /// Matcher filter for Hidden Markov Model (HMM) map matching. It is a HMM filter () /// and determines emission and transition probabilities for map matching with HMM. ///

- public class Matcher : AbstractFilter + /// Candidate inherits from {@link StateCandidate}. + /// Transition inherits from {@link StateTransition}. + /// Sample inherits from {@link Sample}. + public class Matcher : AbstractFilter + where TCandidate : IStateCandidate { private readonly RoadMap _map; private readonly IGraphRouter _router; diff --git a/src/Sandwych.MapMatchingKit/Topology/DijkstraRouter.cs b/src/Sandwych.MapMatchingKit/Topology/DijkstraRouter.cs index 900037e..fd76be0 100644 --- a/src/Sandwych.MapMatchingKit/Topology/DijkstraRouter.cs +++ b/src/Sandwych.MapMatchingKit/Topology/DijkstraRouter.cs @@ -20,11 +20,11 @@ public class DijkstraRouter : IGraphRouter { public ILogger Logger { get; set; } = NullLogger.Instance; - public IDictionary> Route(P source, IEnumerable

targets, + public IReadOnlyDictionary> Route(P source, IEnumerable

targets, Func cost, Func bound = null, double max = double.NaN) => Ssmt(source, targets, cost, bound, max); - public IDictionary)> Route(IEnumerable

sources, IEnumerable

targets, + public IReadOnlyDictionary)> Route(IEnumerable

sources, IEnumerable

targets, Func cost, Func bound = null, double max = double.NaN) => Msmt(sources, targets, cost, bound, max); @@ -32,7 +32,7 @@ public IEnumerable Route(P source, P target, Func cost, Func bound = null, double max = double.NaN) => Ssmt(source, new P[] { target }, cost, bound, max)[target]; - private IDictionary> Ssmt(P source, IEnumerable

targets, Func cost, Func bound, double max = double.NaN) + private IReadOnlyDictionary> Ssmt(P source, IEnumerable

targets, Func cost, Func bound, double max = double.NaN) { var sources = new P[1] { source }; var map = Msmt(sources, targets, cost, bound, max); @@ -44,7 +44,7 @@ private IDictionary> Ssmt(P source, IEnumerable

targets return result; } - private IDictionary)> Msmt(IEnumerable

sources, IEnumerable

targets, Func cost, + private IReadOnlyDictionary)> Msmt(IEnumerable

sources, IEnumerable

targets, Func cost, Func bound, double max) { /* diff --git a/src/Sandwych.MapMatchingKit/Topology/IGraphRouter.cs b/src/Sandwych.MapMatchingKit/Topology/IGraphRouter.cs index 1681155..3028854 100644 --- a/src/Sandwych.MapMatchingKit/Topology/IGraphRouter.cs +++ b/src/Sandwych.MapMatchingKit/Topology/IGraphRouter.cs @@ -13,10 +13,10 @@ public interface IGraphRouter IEnumerable Route(P source, P target, Func cost, Func bound = null, double max = double.NaN); - IDictionary> Route(P source, IEnumerable

targets, + IReadOnlyDictionary> Route(P source, IEnumerable

targets, Func cost, Func bound = null, double max = double.NaN); - IDictionary)> Route(IEnumerable

sources, IEnumerable

targets, + IReadOnlyDictionary)> Route(IEnumerable

sources, IEnumerable

targets, Func cost, Func bound = null, double max = double.NaN); } diff --git a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/BoundedDijkstraShortestPathAlgorithm.cs b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/BoundedDijkstraShortestPathAlgorithm.cs index 23f5047..c417a14 100644 --- a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/BoundedDijkstraShortestPathAlgorithm.cs +++ b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/BoundedDijkstraShortestPathAlgorithm.cs @@ -1,5 +1,6 @@ using System; using System.Collections.Generic; +using System.Linq; using System.Text; using QuickGraph; using QuickGraph.Algorithms.ShortestPath; @@ -11,26 +12,46 @@ public class BoundedDijkstraShortestPathAlgorithm where TVertex : IEquatable where TEdge : IEdge { - private readonly HashSet _visitedVertices = new HashSet(); - private readonly Dictionary _vertexPredecessors = new Dictionary(); + private readonly HashSet _visitedVertices; + private readonly Dictionary _vertexPredecessors; + public Func BoundingCost { get; } public DijkstraShortestPathAlgorithm Algorithm { get; } public double MaxRadius { get; } public IEnumerable VisitedVertices => _visitedVertices; public IReadOnlyDictionary Predecessors => _vertexPredecessors; - public BoundedDijkstraShortestPathAlgorithm(IVertexAndEdgeListGraph graph, Func cost, double maxRadius) + public BoundedDijkstraShortestPathAlgorithm( + IVertexAndEdgeListGraph graph, Func cost, + Func bound, double maxRadius) { + if (maxRadius < 0D) + { + throw new ArgumentOutOfRangeException(nameof(maxRadius)); + } + + var nVertices = graph.VertexCount; + + _visitedVertices = new HashSet(); + _vertexPredecessors = new Dictionary(nVertices); + this.Algorithm = new DijkstraShortestPathAlgorithm(graph, cost); this.Algorithm.ExamineVertex += this.ExamineVertex; this.Algorithm.TreeEdge += this.OnTreeEdge; + this.BoundingCost = bound; this.MaxRadius = maxRadius; } - public void Compute(TVertex rootVertex) + private void Initialize() { _vertexPredecessors.Clear(); _visitedVertices.Clear(); + } + + public void Compute(TVertex rootVertex) + { + this.Initialize(); + this.Algorithm.Compute(rootVertex); } @@ -42,16 +63,21 @@ public bool TryGetDistance(TVertex vertex, out double distance) => private void ExamineVertex(TVertex vertex) { - if (this.Algorithm.Distances[vertex] > this.MaxRadius) + if (this.BoundingCost != null && !double.IsNaN(this.MaxRadius)) { - throw new OutOfRadiusException(); + if (this.TryGetPath(vertex, out var path) && path.Sum(this.BoundingCost) > this.MaxRadius) + { + throw new OutOfRadiusException(); + } } this._visitedVertices.Add(vertex); } - private void OnTreeEdge(TEdge e) => + private void OnTreeEdge(TEdge e) + { _vertexPredecessors[e.Target] = e; + } public bool TryGetPath(TVertex vertex, out IEnumerable path) => this._vertexPredecessors.TryGetPath(vertex, out path); diff --git a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouter.cs b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouter.cs index 5a4f268..949a106 100644 --- a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouter.cs +++ b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouter.cs @@ -3,58 +3,126 @@ using System.Linq; using System.Text; using Microsoft.Extensions.Logging; -using QuickGraph.Algorithms; -using QuickGraph.Algorithms.Observers; -using QuickGraph.Algorithms.ShortestPath; using Sandwych.MapMatchingKit.Roads; using Sandwych.MapMatchingKit.Utility; namespace Sandwych.MapMatchingKit.Topology.PrecomputedDijkstra { public class PrecomputedDijkstraRouter : IGraphRouter - where TEdge : class, IGraphEdge + where TEdge : class, IGraphEdge, IEquatable where P : IEdgePoint, IEquatable

{ + private static readonly TEdge[] EmptyPath = new TEdge[] { }; public ILogger Logger { get; set; } = NullLogger.Instance; private readonly IGraph _graph; - private readonly Lazy> _ubodt; - private readonly Func _edgeCost; - private readonly Func _bound; + private readonly PrecomputedDijkstraTable _ubodt; + private readonly Func _cost; + private readonly Func _boundingCost; private readonly double _maxRadius; - public PrecomputedDijkstraRouter(IGraph graph, Func cost, Func bound, double max) + public PrecomputedDijkstraRouter(IGraph graph, Func cost, Func boundingCost, double max) { _graph = graph; - _edgeCost = cost; - _bound = bound; + _cost = cost; + _boundingCost = boundingCost; _maxRadius = max; - _ubodt = new Lazy>(() => CreateTable(), true); + _ubodt = this.CreateTable(); } - public IDictionary> Route(P source, IEnumerable

targets, Func cost, + public IReadOnlyDictionary> Route(P source, IEnumerable

targets, Func cost, Func bound = null, double max = double.NaN) { - throw new NotImplementedException(); + var dict = new Dictionary>(targets.Count()); + foreach (var target in targets) + { + var path = this.Route(source, target, cost, bound, max); + if (path != null && path.Count() > 0) + { + dict.Add(target, path); + } + } + return dict; } - public IDictionary)> Route(IEnumerable

sources, IEnumerable

targets, Func cost = null, + public IReadOnlyDictionary)> Route(IEnumerable

sources, IEnumerable

targets, Func cost = null, Func bound = null, double max = double.NaN) { - throw new NotImplementedException(); + var result = new Dictionary)>(); + foreach (var source in sources) + { + var ssmtResult = this.Route(source, targets, cost, bound, max); + foreach (var r in ssmtResult) + { + result.Add(r.Key, (source, r.Value)); + } + } + return result; } public IEnumerable Route(P source, P target, Func cost, Func bound = null, double max = double.NaN) { - throw new NotImplementedException(); + var edges = RouteInternal(source, target, cost, bound, max); + if (bound != null && !double.IsNaN(max)) + { + var boundingDistance = edges.Sum(bound); + boundingDistance -= source.Edge.Cost(source.Fraction, bound); + boundingDistance -= target.Edge.Cost(1D - target.Fraction, bound); + if (boundingDistance > max) + { + return EmptyPath; + } + } + return edges; + } + + private IEnumerable RouteInternal( + P source, P target, Func cost, Func bound = null, double max = Double.NaN) + { + //On Same Road and forward + if (source.Edge.Equals(target.Edge) && source.Fraction <= target.Fraction) + { + yield return source.Edge; + yield break; + } + else if (source.Edge.Target.Equals(target.Edge.Source)) //is neighborhood + { + yield return source.Edge; + yield return target.Edge; + yield break; + } + + var edges = _ubodt.GetPathByEdge(source.Edge, target.Edge); + if (this.CheckPathBoundingCost(edges, bound, max)) + { + foreach (var e in edges) + { + yield return e; + } + yield break; + } + } + + private bool CheckPathBoundingCost(IEnumerable path, Func bound = null, double max = double.NaN) + { + if (bound != null && !double.IsNaN(max)) + { + var bounding = path.Sum(this._boundingCost); + return (bounding <= max); + } + else + { + return true; + } } private PrecomputedDijkstraTable CreateTable() { var generator = new PrecomputedDijkstraTableGenerator(); - var rows = generator.ComputeRows(_graph, _edgeCost, _maxRadius); + var rows = generator.ComputeRows(_graph, _cost, _boundingCost, _maxRadius); return new PrecomputedDijkstraTable(rows); } + } } diff --git a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTable.cs b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTable.cs index 9aa6e5c..6541729 100644 --- a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTable.cs +++ b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTable.cs @@ -30,13 +30,41 @@ public PrecomputedDijkstraTable(int capacity) : base(capacity) { } + public bool HasPathByVertex(TVertex sourceVertex, TVertex targetVertex) + { + if (IsSameVertex(sourceVertex, targetVertex)) + { + return false; + } + else + { + return this.ContainsKey((sourceVertex, targetVertex)); + } + } + + public bool HasPathByEdge(TEdge sourceEdge, TEdge targetEdge) + { + if (IsSameEdge(sourceEdge, targetEdge)) + { + throw new InvalidOperationException(); + } + else if (IsNeighbor(sourceEdge, targetEdge)) + { + return true; + } + else + { + return this.HasPathByVertex(sourceEdge.Target, targetEdge.Source); + } + } + public IEnumerable GetPathByEdge(TEdge sourceEdge, TEdge targetEdge) { - if (sourceEdge == targetEdge) + if (IsSameEdge(sourceEdge, targetEdge)) { - yield break; + throw new InvalidOperationException(); } - else if (sourceEdge.Target.Equals(targetEdge.Source)) + else if (IsNeighbor(sourceEdge, targetEdge)) { yield return sourceEdge; yield return targetEdge; @@ -56,6 +84,11 @@ public IEnumerable GetPathByEdge(TEdge sourceEdge, TEdge targetEdge) public IEnumerable GetPathByVertex(TVertex sourceVertex, TVertex targetVertex) { + if (IsSameVertex(sourceVertex, targetVertex)) + { + throw new InvalidOperationException(); + } + if (this.TryGetValue((sourceVertex, targetVertex), out var row)) { //now we got the first edge, then we started from the next row @@ -75,5 +108,14 @@ public IEnumerable GetPathByVertex(TVertex sourceVertex, TVertex targetVe } } + private static bool IsSameVertex(TVertex sourceVertex, TVertex targetVertex) => + sourceVertex.Equals(targetVertex); + + private static bool IsNeighbor(TEdge sourceEdge, TEdge targetEdge) => + sourceEdge.Target.Equals(targetEdge.Source); + + private static bool IsSameEdge(TEdge sourceEdge, TEdge targetEdge) => + sourceEdge.Source.Equals(targetEdge.Source) && sourceEdge.Target.Equals(targetEdge.Target); + } } diff --git a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTableGenerator.cs b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTableGenerator.cs index b46ea60..3251112 100644 --- a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTableGenerator.cs +++ b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTableGenerator.cs @@ -12,9 +12,9 @@ public class PrecomputedDijkstraTableGenerator public IEnumerable> ComputeRows( IVertexAndEdgeListGraph graph, - Func cost, double maxRadius) + Func cost, Func bound, double maxRadius) { - var dijkstra = new BoundedDijkstraShortestPathAlgorithm(graph, cost, maxRadius); + var dijkstra = new BoundedDijkstraShortestPathAlgorithm(graph, cost, bound, maxRadius); foreach (var rootVertex in graph.Vertices) { @@ -26,7 +26,7 @@ public IEnumerable> ComputeRows( } } - public IEnumerable> ComputeRowsSingleSource( + private IEnumerable> ComputeRowsSingleSource( IVertexAndEdgeListGraph graph, BoundedDijkstraShortestPathAlgorithm dijkstra, TVertex sourceVertex) diff --git a/test/Sandwych.MapMatchingKit.Tests/Matching/MatcherTest.cs b/test/Sandwych.MapMatchingKit.Tests/Matching/MatcherTest.cs index bc5159d..9fe5923 100644 --- a/test/Sandwych.MapMatchingKit.Tests/Matching/MatcherTest.cs +++ b/test/Sandwych.MapMatchingKit.Tests/Matching/MatcherTest.cs @@ -112,7 +112,7 @@ private ISet RefSet(Coordinate2D sample, double radius) [Fact] public void TestCandidates() { - var filter = new Matcher(_map, _router, _cost, _spatial); + var filter = new Matcher(_map, _router, _cost, _spatial); { filter.MaxRadius = 100D; var sample = new Coordinate2D(11.001, 48.001); @@ -152,7 +152,7 @@ void assertCandidate(double radius, Coordinate2D sample, IEnumerable refse [Fact] public void TestTransitions() { - var filter = new Matcher(_map, _router, _cost, _spatial); + var filter = new Matcher(_map, _router, _cost, _spatial); filter.MaxRadius = 200D; { MatcherSample sample1 = new MatcherSample(0, 0, new Coordinate2D(11.001, 48.001)); diff --git a/test/Sandwych.MapMatchingKit.Tests/Topology/AbstractRouterTest.cs b/test/Sandwych.MapMatchingKit.Tests/Topology/AbstractRouterTest.cs index 3162399..dabafd5 100644 --- a/test/Sandwych.MapMatchingKit.Tests/Topology/AbstractRouterTest.cs +++ b/test/Sandwych.MapMatchingKit.Tests/Topology/AbstractRouterTest.cs @@ -9,25 +9,26 @@ namespace Sandwych.MapMatchingKit.Tests.Topology { public abstract class AbstractRouterTest : TestBase { - protected abstract IGraphRouter CreateRouter(); + protected abstract IGraphRouter CreateRouter(Graph graph, Func cost, Func bound, double max); - protected void AssertSinglePath(IEnumerable expectedPath, IEnumerable sources, IEnumerable targets) + protected void AssertSinglePath( + IEnumerable expectedPath, + IEnumerable sources, + IEnumerable targets, + IReadOnlyDictionary)> routes) { - var router = this.CreateRouter(); - var routes = router.Route(sources, targets, e => e.Weight, null, double.NaN); + Assert.Equal(1, routes.Count); var route = routes[targets.First()]; Assert.Equal(expectedPath.First(), route.Item1.Edge.Id); Assert.Equal(expectedPath, route.Item2.Select(r => r.Id)); } - protected void AssertMultiplePaths(IReadOnlyDictionary> expectedPaths, - IEnumerable sources, IEnumerable targets, - Func bound = null, double max = double.NaN) + protected void AssertMultiplePathsTest( + IReadOnlyDictionary)> routes, + IReadOnlyDictionary> expectedPaths, + IEnumerable sources, IEnumerable targets) { - var router = this.CreateRouter(); - var routes = router.Route(sources, targets, e => e.Weight, bound, max); - Assert.Equal(expectedPaths.Count(), routes.Count()); foreach (var pair in routes) @@ -42,70 +43,34 @@ protected void AssertMultiplePaths(IReadOnlyDictionary> } } - - [Fact] - public void TestSameRoad() + [Theory] + [ClassData(typeof(RouterTestData_SameRoad))] + public void TestSameRoad( + Graph graph, + IEnumerable expectedPath, IEnumerable sources, IEnumerable targets, + Func cost, Func bound, double max) { - var roads = new Road[] { - new Road(0, 0, 1, 100), - new Road(1, 1, 0, 20), - new Road(2, 0, 2, 100), - new Road(3, 1, 2, 100), - new Road(4, 1, 3, 100) - }; - var map = new Graph(roads); - - AssertSinglePath( - expectedPath: new long[] { 0L }, - sources: new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.3) }, - targets: new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.3) }); - - AssertSinglePath( - expectedPath: new long[] { 0L }, - sources: new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.3) }, - targets: new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.7) }); - - AssertSinglePath( - expectedPath: new long[] { 0L, 1L, 0L }, - sources: new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.7) }, - targets: new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.3) }); - - AssertSinglePath( - expectedPath: new long[] { 1L, 0L }, - sources: new RoadPoint[] { new RoadPoint(map.EdgeMap[0], 0.8), new RoadPoint(map.EdgeMap[1L], 0.2) }, - targets: new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.7) }); + var route = this.CreateRouter(graph, cost, bound, max); + var routes = route.Route(sources, targets, cost, bound, max); + this.AssertSinglePath(expectedPath, sources, targets, routes); } - [Fact] - public void TestSelfLoop() + /* + [Theory] + [ClassData(typeof(RouterTestData_SelfLoop))] + public void TestSelfLoop( + Graph graph, + IEnumerable expectedPath, IEnumerable sources, IEnumerable targets, + Func cost, Func bound, double max) { - var roads = new Road[] { - new Road(0, 0, 0, 100), - new Road(1, 0, 0, 100), - }; - var map = new Graph(roads); - - AssertSinglePath( - expectedPath: new long[] { 0L }, - sources: new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.3) }, - targets: new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.7) }); - - AssertSinglePath( - expectedPath: new long[] { 0L, 0L }, - sources: new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.7) }, - targets: new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.3) }); - - AssertSinglePath( - expectedPath: new long[] { 0L, 0L }, - sources: new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.8), new RoadPoint(map.EdgeMap[1L], 0.2) }, - targets: new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.2) }); - - AssertSinglePath( - expectedPath: new long[] { 1L, 0L }, - sources: new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.4), new RoadPoint(map.EdgeMap[1L], 0.6) }, - targets: new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.3) }); + var route = this.CreateRouter(graph, cost, bound, max); + var routes = route.Route(sources, targets, cost, bound, max); + this.AssertSinglePath(expectedPath, sources, targets, routes); } + */ + + /* [Fact] public void TestShortestPath() { @@ -132,29 +97,33 @@ public void TestShortestPath() var map = new Graph(roads); { // (0.7, 100) + 50 + 40 + 60 + (0.3, 200) = 280 + var router = this.CreateRouter(); var paths = new Dictionary>() { { 14L, new long[] { 0L, 4L, 8L, 14L } }, { 15L, new long[] { 0L, 4L, 10L, 16L, 15L } }, }; AssertMultiplePaths( + router, expectedPaths: paths, sources: new RoadPoint[] { new RoadPoint(map.EdgeMap[0], 0.3), new RoadPoint(map.EdgeMap[1], 0.7) }, targets: new RoadPoint[] { new RoadPoint(map.EdgeMap[14], 0.3), new RoadPoint(map.EdgeMap[15], 0.7) }); } { // (0.7, 100) + 50 + 100 + (0.1, 200) = 240 + var router = this.CreateRouter(); var paths = new Dictionary>() { { 14L, new long[] { 0L, 4L, 8L, 14L } }, { 15L, new long[] { 0L, 4L, 10L, 16L, 15L } }, }; AssertMultiplePaths( + router, expectedPaths: paths, sources: new RoadPoint[] { new RoadPoint(map.EdgeMap[0], 0.3), new RoadPoint(map.EdgeMap[1], 0.7) }, targets: new RoadPoint[] { new RoadPoint(map.EdgeMap[14], 0.1), new RoadPoint(map.EdgeMap[15], 0.9) }); } - var router = new DijkstraRouter(); { + var router = CreateRouter(); // (0.7, 100) + 50 + 100 + (0.1, 200) = 240 var sources = new RoadPoint[] { new RoadPoint(map.GetEdge(0), 0.3), }; var targets = new RoadPoint[] { new RoadPoint(map.GetEdge(14), 0.1), }; @@ -164,6 +133,7 @@ public void TestShortestPath() Assert.Empty(route); } { + var router = CreateRouter(); // (0.7, 100) + 50 + 100 + (0.1, 200) = 240 // (0.7, 100) + 50 + 100 + (0.8, 200) = 380 @@ -199,6 +169,7 @@ public void TestShortestPath() } } } + */ } } diff --git a/test/Sandwych.MapMatchingKit.Tests/Topology/DijkstraRouterTest.cs b/test/Sandwych.MapMatchingKit.Tests/Topology/DijkstraRouterTest.cs index 543a3bb..107d0f9 100644 --- a/test/Sandwych.MapMatchingKit.Tests/Topology/DijkstraRouterTest.cs +++ b/test/Sandwych.MapMatchingKit.Tests/Topology/DijkstraRouterTest.cs @@ -9,9 +9,9 @@ namespace Sandwych.MapMatchingKit.Tests.Topology { public class DijkstraRouterTest : AbstractRouterTest { - protected override IGraphRouter CreateRouter() => new DijkstraRouter(); - - + protected override IGraphRouter CreateRouter( + Graph graph, Func cost, Func bound, double max) => + new DijkstraRouter(); } } diff --git a/test/Sandwych.MapMatchingKit.Tests/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouterTest.cs b/test/Sandwych.MapMatchingKit.Tests/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouterTest.cs new file mode 100644 index 0000000..095c7e7 --- /dev/null +++ b/test/Sandwych.MapMatchingKit.Tests/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouterTest.cs @@ -0,0 +1,15 @@ +using System; +using System.Collections.Generic; +using System.Text; +using Sandwych.MapMatchingKit.Topology; +using Sandwych.MapMatchingKit.Topology.PrecomputedDijkstra; + +namespace Sandwych.MapMatchingKit.Tests.Topology.PrecomputedDijkstra +{ + public class PrecomputedDijkstraRouterTest : AbstractRouterTest + { + protected override IGraphRouter CreateRouter( + Graph graph, Func cost, Func bound, double max) => + new PrecomputedDijkstraRouter(graph, cost, bound, max); + } +} diff --git a/test/Sandwych.MapMatchingKit.Tests/Topology/PrecomputedDijkstra/PrecomputedDijkstraTableTest.cs b/test/Sandwych.MapMatchingKit.Tests/Topology/PrecomputedDijkstra/PrecomputedDijkstraTableTest.cs index b2d1bc1..21c8d95 100644 --- a/test/Sandwych.MapMatchingKit.Tests/Topology/PrecomputedDijkstra/PrecomputedDijkstraTableTest.cs +++ b/test/Sandwych.MapMatchingKit.Tests/Topology/PrecomputedDijkstra/PrecomputedDijkstraTableTest.cs @@ -12,6 +12,7 @@ public class PrecomputedDijkstraTableTest { [Theory] [InlineData("A", "B")] + [InlineData("A", "D")] [InlineData("A", "J")] [InlineData("C", "E")] public void TestGetPathByVertex(string sourceVertex, string targetVertex) @@ -19,11 +20,11 @@ public void TestGetPathByVertex(string sourceVertex, string targetVertex) var maxRadius = 500D; var naiveDijkstra = new BoundedDijkstraShortestPathAlgorithm>( - MyGraph.GraphInstance, e => MyGraph.EdgeCosts[e], maxRadius); + MyGraph.GraphInstance, e => MyGraph.EdgeCosts[e], e => MyGraph.EdgeCosts[e], maxRadius); naiveDijkstra.Compute(sourceVertex); var generator = new PrecomputedDijkstraTableGenerator>(); - var rows = generator.ComputeRows(MyGraph.GraphInstance, e => MyGraph.EdgeCosts[e], maxRadius); + var rows = generator.ComputeRows(MyGraph.GraphInstance, e => MyGraph.EdgeCosts[e], e => MyGraph.EdgeCosts[e], maxRadius); var table = new PrecomputedDijkstraTable>(rows); var actualPath = table.GetPathByVertex(sourceVertex, targetVertex); diff --git a/test/Sandwych.MapMatchingKit.Tests/Topology/RouterTestData.cs b/test/Sandwych.MapMatchingKit.Tests/Topology/RouterTestData.cs new file mode 100644 index 0000000..aa8ac00 --- /dev/null +++ b/test/Sandwych.MapMatchingKit.Tests/Topology/RouterTestData.cs @@ -0,0 +1,195 @@ +using System; +using System.Collections; +using System.Collections.Generic; +using System.Text; + +namespace Sandwych.MapMatchingKit.Tests.Topology +{ + public class RouterTestData_SameRoad : IEnumerable + { + private readonly List _data; + + public IEnumerator GetEnumerator() => _data.GetEnumerator(); + IEnumerator IEnumerable.GetEnumerator() => GetEnumerator(); + + public RouterTestData_SameRoad() + { + var roads = new Road[] { + new Road(0, 0, 1, 100), + new Road(1, 1, 0, 20), + new Road(2, 0, 2, 100), + new Road(3, 1, 2, 100), + new Road(4, 1, 3, 100) + }; + var map = new Graph(roads); + Func cost = e => e.Weight; + + + _data = new List() + { + new object[] { + map, + new long[] { 0L }, + new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.3) }, + new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.3) }, + cost, null, double.NaN + }, + + new object[] { + map, + new long[] { 0L }, + new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.3) }, + new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.7) }, + cost, null, double.NaN + }, + + new object[] { + map, + new long[] { 0L, 1L, 0L }, + new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.7) }, + new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.3) }, + cost, null, double.NaN + }, + + new object[] { + map, + new long[] { 1L, 0L }, + new RoadPoint[] { new RoadPoint(map.EdgeMap[0], 0.8), new RoadPoint(map.EdgeMap[1L], 0.2) }, + new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.7) }, + cost, null, double.NaN + }, + }; + } + + } + + + public class RouterTestData_SelfLoop : IEnumerable + { + private readonly List _data; + + public IEnumerator GetEnumerator() => _data.GetEnumerator(); + IEnumerator IEnumerable.GetEnumerator() => GetEnumerator(); + + public RouterTestData_SelfLoop() + { + var roads = new Road[] { + new Road(0, 0, 0, 100), + new Road(1, 0, 0, 100), + }; + var map = new Graph(roads); + Func cost = e => e.Weight; + + _data = new List() + { + new object[] { + map, + new long[] { 0L }, + new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.3) }, + new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.7) }, + cost, null, double.NaN + }, + + new object[] { + map, + new long[] { 0L, 0L }, + new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.7) }, + new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.3) }, + cost, null, double.NaN + }, + + new object[] { + map, + new long[] { 0L, 0L }, + new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.8), new RoadPoint(map.EdgeMap[1L], 0.2) }, + new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.2) }, + cost, null, double.NaN + }, + + new object[] { + map, + new long[] { 1L, 0L }, + new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.4), new RoadPoint(map.EdgeMap[1L], 0.6) }, + new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.3) }, + cost, null, double.NaN + }, + + }; + } + + } + + + public class RouterTestData_ShortestPath : IEnumerable + { + private readonly List _data; + + public IEnumerator GetEnumerator() => _data.GetEnumerator(); + IEnumerator IEnumerable.GetEnumerator() => GetEnumerator(); + + public RouterTestData_ShortestPath() + { + var roads = new Road[] { + new Road(0, 0, 1, 100), + new Road(1, 1, 0, 100), + new Road(2, 0, 2, 160), + new Road(3, 2, 0, 160), + new Road(4, 1, 2, 50), + new Road(5, 2, 1, 50), + new Road(6, 1, 3, 200), + new Road(7, 3, 1, 200), + new Road(8, 2, 3, 100), + new Road(9, 3, 2, 100), + new Road(10, 2, 4, 40), + new Road(11, 4, 2, 40), + new Road(12, 3, 4, 100), + new Road(13, 4, 3, 100), + new Road(14, 3, 5, 200), + new Road(15, 5, 3, 200), + new Road(16, 4, 5, 60), + new Road(17, 5, 4, 60), + }; + var map = new Graph(roads); + Func cost = e => e.Weight; + + _data = new List() + { + new object[] { + map, + new long[] { 0L }, + new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.3) }, + new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.7) }, + cost, null, double.NaN + }, + + new object[] { + map, + new long[] { 0L, 0L }, + new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.7) }, + new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.3) }, + cost, null, double.NaN + }, + + new object[] { + map, + new long[] { 0L, 0L }, + new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.8), new RoadPoint(map.EdgeMap[1L], 0.2) }, + new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.2) }, + cost, null, double.NaN + }, + + new object[] { + map, + new long[] { 1L, 0L }, + new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.4), new RoadPoint(map.EdgeMap[1L], 0.6) }, + new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.3) }, + cost, null, double.NaN + }, + + }; + } + + } + + +} diff --git a/test/Sandwych.MapMatchingKit.Tests/Topology/UbodtRouterTest.cs b/test/Sandwych.MapMatchingKit.Tests/Topology/UbodtRouterTest.cs deleted file mode 100644 index cd79a79..0000000 --- a/test/Sandwych.MapMatchingKit.Tests/Topology/UbodtRouterTest.cs +++ /dev/null @@ -1,11 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Text; -using Sandwych.MapMatchingKit.Topology; - -namespace Sandwych.MapMatchingKit.Tests.Topology -{ - public class UbodtRouterTest : TestBase - { - } -} From 8422b686a190394e76c91837709f89b1fb75946f Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Mon, 5 Mar 2018 02:07:39 +0800 Subject: [PATCH 11/37] more unit tests --- .../PrecomputedDijkstraRouter.cs | 30 +++++----- .../Topology/AbstractRouterTest.cs | 2 - .../PrecomputedDijkstraRouterTest.cs | 55 +++++++++++++++++-- .../Topology/RouterTestData.cs | 6 +- 4 files changed, 72 insertions(+), 21 deletions(-) diff --git a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouter.cs b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouter.cs index 949a106..ae713d1 100644 --- a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouter.cs +++ b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouter.cs @@ -16,7 +16,7 @@ public class PrecomputedDijkstraRouter : IGraphRouter public ILogger Logger { get; set; } = NullLogger.Instance; private readonly IGraph _graph; - private readonly PrecomputedDijkstraTable _ubodt; + private readonly PrecomputedDijkstraTable _precomputedTable; private readonly Func _cost; private readonly Func _boundingCost; private readonly double _maxRadius; @@ -27,7 +27,7 @@ public PrecomputedDijkstraRouter(IGraph graph, Func cost, _cost = cost; _boundingCost = boundingCost; _maxRadius = max; - _ubodt = this.CreateTable(); + _precomputedTable = this.CreateTable(); } public IReadOnlyDictionary> Route(P source, IEnumerable

targets, Func cost, @@ -48,16 +48,7 @@ public IReadOnlyDictionary> Route(P source, IEnumerable

public IReadOnlyDictionary)> Route(IEnumerable

sources, IEnumerable

targets, Func cost = null, Func bound = null, double max = double.NaN) { - var result = new Dictionary)>(); - foreach (var source in sources) - { - var ssmtResult = this.Route(source, targets, cost, bound, max); - foreach (var r in ssmtResult) - { - result.Add(r.Key, (source, r.Value)); - } - } - return result; + throw new NotSupportedException(); } public IEnumerable Route(P source, P target, Func cost, Func bound = null, double max = double.NaN) @@ -79,7 +70,7 @@ public IEnumerable Route(P source, P target, Func cost, Fu private IEnumerable RouteInternal( P source, P target, Func cost, Func bound = null, double max = Double.NaN) { - //On Same Road and forward + //On same road && forward if (source.Edge.Equals(target.Edge) && source.Fraction <= target.Fraction) { yield return source.Edge; @@ -92,7 +83,18 @@ private IEnumerable RouteInternal( yield break; } - var edges = _ubodt.GetPathByEdge(source.Edge, target.Edge); + IEnumerable GetPath() + { + yield return source.Edge; + foreach (var edge in _precomputedTable.GetPathByVertex(source.Edge.Target, target.Edge.Source)) + { + yield return edge; + } + yield return target.Edge; + } + + var edges = GetPath(); + if (this.CheckPathBoundingCost(edges, bound, max)) { foreach (var e in edges) diff --git a/test/Sandwych.MapMatchingKit.Tests/Topology/AbstractRouterTest.cs b/test/Sandwych.MapMatchingKit.Tests/Topology/AbstractRouterTest.cs index dabafd5..ff153ab 100644 --- a/test/Sandwych.MapMatchingKit.Tests/Topology/AbstractRouterTest.cs +++ b/test/Sandwych.MapMatchingKit.Tests/Topology/AbstractRouterTest.cs @@ -55,7 +55,6 @@ public void TestSameRoad( this.AssertSinglePath(expectedPath, sources, targets, routes); } - /* [Theory] [ClassData(typeof(RouterTestData_SelfLoop))] public void TestSelfLoop( @@ -67,7 +66,6 @@ public void TestSelfLoop( var routes = route.Route(sources, targets, cost, bound, max); this.AssertSinglePath(expectedPath, sources, targets, routes); } - */ /* diff --git a/test/Sandwych.MapMatchingKit.Tests/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouterTest.cs b/test/Sandwych.MapMatchingKit.Tests/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouterTest.cs index 095c7e7..2999f5c 100644 --- a/test/Sandwych.MapMatchingKit.Tests/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouterTest.cs +++ b/test/Sandwych.MapMatchingKit.Tests/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouterTest.cs @@ -1,15 +1,62 @@ using System; +using System.Linq; using System.Collections.Generic; using System.Text; using Sandwych.MapMatchingKit.Topology; using Sandwych.MapMatchingKit.Topology.PrecomputedDijkstra; +using Xunit; namespace Sandwych.MapMatchingKit.Tests.Topology.PrecomputedDijkstra { - public class PrecomputedDijkstraRouterTest : AbstractRouterTest + public class PrecomputedDijkstraRouterTest : TestBase { - protected override IGraphRouter CreateRouter( - Graph graph, Func cost, Func bound, double max) => - new PrecomputedDijkstraRouter(graph, cost, bound, max); + private readonly Graph _map; + + public PrecomputedDijkstraRouterTest() + { + var roads = new Road[] { + new Road(0, 0, 1, 100), + new Road(1, 1, 0, 100), + new Road(2, 0, 2, 160), + new Road(3, 2, 0, 160), + new Road(4, 1, 2, 50), + new Road(5, 2, 1, 50), + new Road(6, 1, 3, 200), + new Road(7, 3, 1, 200), + new Road(8, 2, 3, 100), + new Road(9, 3, 2, 100), + new Road(10, 2, 4, 40), + new Road(11, 4, 2, 40), + new Road(12, 3, 4, 100), + new Road(13, 4, 3, 100), + new Road(14, 3, 5, 200), + new Road(15, 5, 3, 200), + new Road(16, 4, 5, 60), + new Road(17, 5, 4, 60), + }; + _map = new Graph(roads); + } + + [Fact] + public void ShortestPathTest1() + { + var max = 200D; + var start = new RoadPoint(_map.GetEdge(0), 0.3); + var targets = new RoadPoint[] { + new RoadPoint(_map.GetEdge(10), 0.5), + new RoadPoint(_map.GetEdge(17), 0.6), + }; + Func cost = r => r.Weight; + + var dijkstraRouter = new DijkstraRouter(); + var precomputedRouter = new PrecomputedDijkstraRouter(_map, cost, cost, max); + + var expectedPath = dijkstraRouter.Route(start, targets, cost, cost, max); + var actualPath = precomputedRouter.Route(start, targets, cost, cost, max); + + Assert.Single(actualPath); + Assert.Equal(expectedPath, actualPath); + } + } } diff --git a/test/Sandwych.MapMatchingKit.Tests/Topology/RouterTestData.cs b/test/Sandwych.MapMatchingKit.Tests/Topology/RouterTestData.cs index aa8ac00..bfaae57 100644 --- a/test/Sandwych.MapMatchingKit.Tests/Topology/RouterTestData.cs +++ b/test/Sandwych.MapMatchingKit.Tests/Topology/RouterTestData.cs @@ -54,7 +54,11 @@ public RouterTestData_SameRoad() new object[] { map, new long[] { 1L, 0L }, - new RoadPoint[] { new RoadPoint(map.EdgeMap[0], 0.8), new RoadPoint(map.EdgeMap[1L], 0.2) }, + new RoadPoint[] + { + new RoadPoint(map.EdgeMap[0], 0.8), + new RoadPoint(map.EdgeMap[1L], 0.2) + }, new RoadPoint[] { new RoadPoint(map.EdgeMap[0L], 0.7) }, cost, null, double.NaN }, From bd8305bacbfe0ca22e647689a90dbb63c70ebe54 Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Mon, 5 Mar 2018 02:22:06 +0800 Subject: [PATCH 12/37] more unit tests for PrecomputedDijkstraRouter --- .../Program.cs | 2 +- .../PrecomputedDijkstraRouter.cs | 22 ++----------------- .../PrecomputedDijkstraRouterTest.cs | 19 ++++++++++++++++ 3 files changed, 22 insertions(+), 21 deletions(-) diff --git a/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs b/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs index a98faf4..fb33add 100644 --- a/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs +++ b/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs @@ -132,7 +132,7 @@ private static IEnumerable ReadSamples() private static IEnumerable ReadRoads(ISpatialOperation spatial) { - var json = File.ReadAllText(System.IO.Path.Combine(s_dataDir, @"osm-kunming-roads-network.geojson")); + var json = File.ReadAllText(Path.Combine(s_dataDir, @"osm-kunming-roads-network.geojson")); var reader = new GeoJsonReader(); var fc = reader.Read(json); foreach (var feature in fc.Features) diff --git a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouter.cs b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouter.cs index ae713d1..6c0fcd0 100644 --- a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouter.cs +++ b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouter.cs @@ -94,27 +94,9 @@ IEnumerable GetPath() } var edges = GetPath(); - - if (this.CheckPathBoundingCost(edges, bound, max)) - { - foreach (var e in edges) - { - yield return e; - } - yield break; - } - } - - private bool CheckPathBoundingCost(IEnumerable path, Func bound = null, double max = double.NaN) - { - if (bound != null && !double.IsNaN(max)) - { - var bounding = path.Sum(this._boundingCost); - return (bounding <= max); - } - else + foreach (var edge in edges) { - return true; + yield return edge; } } diff --git a/test/Sandwych.MapMatchingKit.Tests/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouterTest.cs b/test/Sandwych.MapMatchingKit.Tests/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouterTest.cs index 2999f5c..f8f7a6e 100644 --- a/test/Sandwych.MapMatchingKit.Tests/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouterTest.cs +++ b/test/Sandwych.MapMatchingKit.Tests/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouterTest.cs @@ -58,5 +58,24 @@ public void ShortestPathTest1() Assert.Equal(expectedPath, actualPath); } + [Fact] + public void SelfLoopTest() + { + var max = 200D; + var start = new RoadPoint(_map.GetEdge(0), 0.3); + var targets = new RoadPoint[] { + new RoadPoint(_map.GetEdge(0), 0.2), + }; + Func cost = r => r.Weight; + + var dijkstraRouter = new DijkstraRouter(); + var precomputedRouter = new PrecomputedDijkstraRouter(_map, cost, cost, max); + + var expectedPath = dijkstraRouter.Route(start, targets, cost, cost, max); + var actualPath = precomputedRouter.Route(start, targets, cost, cost, max); + + Assert.Equal(expectedPath, actualPath); + } + } } From d9b508d4b70e6bf8c00eaf363ccef58e79422bc3 Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Mon, 5 Mar 2018 11:34:44 +0800 Subject: [PATCH 13/37] add benchmark --- Sandwych.MapMatchingKit.sln | 9 ++ .../Program.cs | 14 ++ .../RoutersBenchmark.cs | 137 ++++++++++++++++++ ...andwych.MapMatchingKit.BenchmarkApp.csproj | 17 +++ ...pMatchingKit.Examples.HelloWorldApp.csproj | 2 +- .../Sandwych.Hmm.Tests.csproj | 2 +- .../Matching/MatcherTest.cs | 2 +- .../Sandwych.MapMatchingKit.Tests.csproj | 2 +- .../PrecomputedDijkstraRouterTest.cs | 30 ++-- 9 files changed, 201 insertions(+), 14 deletions(-) create mode 100644 benchmark/Sandwych.MapMatchingKit.BenchmarkApp/Program.cs create mode 100644 benchmark/Sandwych.MapMatchingKit.BenchmarkApp/RoutersBenchmark.cs create mode 100644 benchmark/Sandwych.MapMatchingKit.BenchmarkApp/Sandwych.MapMatchingKit.BenchmarkApp.csproj diff --git a/Sandwych.MapMatchingKit.sln b/Sandwych.MapMatchingKit.sln index 982355a..8d0dc05 100644 --- a/Sandwych.MapMatchingKit.sln +++ b/Sandwych.MapMatchingKit.sln @@ -19,6 +19,10 @@ Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Sandwych.MapMatchingKit.Exa EndProject Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Source", "Source", "{CCB5D40B-40A8-43C2-B0E2-F2B6F5D73917}" EndProject +Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Benchmark", "Benchmark", "{CCEE7207-D1DA-4590-A89A-897FC90D3A87}" +EndProject +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Sandwych.MapMatchingKit.BenchmarkApp", "benchmark\Sandwych.MapMatchingKit.BenchmarkApp\Sandwych.MapMatchingKit.BenchmarkApp.csproj", "{7CB3D4C1-3386-4CAC-8FFA-004CD446EDA5}" +EndProject Global GlobalSection(SolutionConfigurationPlatforms) = preSolution Debug|Any CPU = Debug|Any CPU @@ -45,6 +49,10 @@ Global {2CCF3F1B-FFF3-4153-952D-4564BEB4C11A}.Debug|Any CPU.Build.0 = Debug|Any CPU {2CCF3F1B-FFF3-4153-952D-4564BEB4C11A}.Release|Any CPU.ActiveCfg = Release|Any CPU {2CCF3F1B-FFF3-4153-952D-4564BEB4C11A}.Release|Any CPU.Build.0 = Release|Any CPU + {7CB3D4C1-3386-4CAC-8FFA-004CD446EDA5}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {7CB3D4C1-3386-4CAC-8FFA-004CD446EDA5}.Debug|Any CPU.Build.0 = Debug|Any CPU + {7CB3D4C1-3386-4CAC-8FFA-004CD446EDA5}.Release|Any CPU.ActiveCfg = Release|Any CPU + {7CB3D4C1-3386-4CAC-8FFA-004CD446EDA5}.Release|Any CPU.Build.0 = Release|Any CPU EndGlobalSection GlobalSection(SolutionProperties) = preSolution HideSolutionNode = FALSE @@ -55,6 +63,7 @@ Global {B8F22581-A63E-4F9C-AF6B-A2115F00FD9C} = {CCB5D40B-40A8-43C2-B0E2-F2B6F5D73917} {6B856AA6-C7E4-4F3D-8D18-35871BAED45F} = {5F02380C-9094-411E-9CB8-40B6259F79D8} {2CCF3F1B-FFF3-4153-952D-4564BEB4C11A} = {DF6975B6-10B3-49EA-966D-0F623BB27BE9} + {7CB3D4C1-3386-4CAC-8FFA-004CD446EDA5} = {CCEE7207-D1DA-4590-A89A-897FC90D3A87} EndGlobalSection GlobalSection(ExtensibilityGlobals) = postSolution SolutionGuid = {F6CFD619-16DA-4D64-BC25-789DAC1BD83D} diff --git a/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/Program.cs b/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/Program.cs new file mode 100644 index 0000000..8d91827 --- /dev/null +++ b/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/Program.cs @@ -0,0 +1,14 @@ +using BenchmarkDotNet.Running; +using System; +using System.IO; + +namespace Sandwych.MapMatchingKit.BenchmarkApp +{ + public class Program + { + static void Main(string[] args) + { + var summary = BenchmarkRunner.Run(); + } + } +} diff --git a/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/RoutersBenchmark.cs b/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/RoutersBenchmark.cs new file mode 100644 index 0000000..b52a378 --- /dev/null +++ b/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/RoutersBenchmark.cs @@ -0,0 +1,137 @@ +using System; +using System.Collections.Generic; +using System.IO; +using System.Linq; +using System.Text; +using System.Globalization; +using BenchmarkDotNet.Attributes; +using BenchmarkDotNet.Attributes.Columns; +using BenchmarkDotNet.Attributes.Exporters; +using BenchmarkDotNet.Attributes.Jobs; +using BenchmarkDotNet.Running; +using NetTopologySuite.Features; +using NetTopologySuite.IO; +using GeoAPI.Geometries; +using Sandwych.MapMatchingKit.Matching; +using Sandwych.MapMatchingKit.Spatial.Geometries; +using Sandwych.MapMatchingKit.Roads; +using Sandwych.MapMatchingKit.Spatial; +using Sandwych.MapMatchingKit.Topology; +using Sandwych.MapMatchingKit.Topology.PrecomputedDijkstra; + +namespace Sandwych.MapMatchingKit.BenchmarkApp +{ + [RPlotExporter, HtmlExporter, RankColumn] + [MemoryDiagnoser, ShortRunJob] + public class RoutersBenchmark + { + private const double MaxDistance = 1000D; + private const double MaxGpsRadius = 200D; + private string DataDirPath { get; set; } + + private RoadMap _roadMap; + private Matcher _naiveDijkstraMatcher; + private Matcher _precomputedDijkstraMatcher; + + private MatcherSample[] _samples; + + [GlobalSetup] + public void Setup() + { + this.DataDirPath = Path.GetFullPath(Path.Combine(Directory.GetCurrentDirectory(), "../../../../../../../../../", "data")); + + var spatial = new GeographySpatialOperation(); + var roads = this.ReadRoads(spatial); + + var mapBuilder = new RoadMapBuilder(spatial); + _roadMap = mapBuilder.AddRoads(roads).Build(); + + { + var naiveDijkstraRouter = new DijkstraRouter(); + _naiveDijkstraMatcher = new Matcher( + _roadMap, naiveDijkstraRouter, Costs.TimePriorityCost, spatial); + _naiveDijkstraMatcher.MaxDistance = MaxDistance; // set maximum searching distance between two GPS points to 1000 meters. + _naiveDijkstraMatcher.MaxRadius = MaxGpsRadius; // sets maximum radius for candidate selection to 200 meters + } + + { + var precomputedDijkstraRouter = new PrecomputedDijkstraRouter(_roadMap, Costs.TimePriorityCost, Costs.DistanceCost, 1000D); + _precomputedDijkstraMatcher = new Matcher( + _roadMap, precomputedDijkstraRouter, Costs.TimePriorityCost, spatial); + _precomputedDijkstraMatcher.MaxDistance = MaxDistance; // set maximum searching distance between two GPS points to 1000 meters. + _precomputedDijkstraMatcher.MaxRadius = MaxGpsRadius; // sets maximum radius for candidate selection to 200 meters + } + + _samples = ReadSamples().OrderBy(s => s.Time).ToArray(); + } + + [Benchmark(Baseline = true)] + public int NaiveDijkstraMatching() + { + var candidates = this.DoMatching(_naiveDijkstraMatcher); + return candidates.Count(); + } + + [Benchmark] + public int PrecomputedDijkstraMatching() + { + var candidates = this.DoMatching(_precomputedDijkstraMatcher); + return candidates.Count(); + } + + private IEnumerable DoMatching(Matcher matcher) + { + var kstate = new MatcherKState(); + foreach (var sample in _samples) + { + var vector = matcher.Execute(kstate.Vector(), kstate.Sample, sample); + kstate.Update(vector, sample); + } + var candidatesSequence = kstate.Sequence(); + return candidatesSequence; + } + + private IEnumerable ReadSamples() + { + var json = File.ReadAllText(System.IO.Path.Combine(DataDirPath, @"samples.geojson")); + var reader = new GeoJsonReader(); + var fc = reader.Read(json); + var timeFormat = "yyyy-MM-dd-HH.mm.ss"; + var samples = new List(); + foreach (var i in fc.Features) + { + var p = i.Geometry as IPoint; + var coord2D = new Coordinate2D(p.X, p.Y); + var timeStr = i.Attributes["time"].ToString().Substring(0, timeFormat.Length); + var time = DateTimeOffset.ParseExact(timeStr, timeFormat, CultureInfo.InvariantCulture); + var longTime = time.ToUnixTimeMilliseconds(); + yield return new MatcherSample(longTime, time, coord2D); + } + } + + + private IEnumerable ReadRoads(ISpatialOperation spatial) + { + var json = File.ReadAllText(Path.Combine(DataDirPath, @"osm-kunming-roads-network.geojson")); + var reader = new GeoJsonReader(); + var fc = reader.Read(json); + foreach (var feature in fc.Features) + { + var lineGeom = feature.Geometry as ILineString; + yield return new RoadInfo( + Convert.ToInt64(feature.Attributes["gid"]), + Convert.ToInt64(feature.Attributes["source"]), + Convert.ToInt64(feature.Attributes["target"]), + (double)feature.Attributes["reverse"] >= 0D ? false : true, + (short)0, + Convert.ToSingle(feature.Attributes["priority"]), + 120f, + 120f, + Convert.ToSingle(spatial.Length(lineGeom)), + lineGeom); + } + } + + + } +} diff --git a/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/Sandwych.MapMatchingKit.BenchmarkApp.csproj b/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/Sandwych.MapMatchingKit.BenchmarkApp.csproj new file mode 100644 index 0000000..9ca048d --- /dev/null +++ b/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/Sandwych.MapMatchingKit.BenchmarkApp.csproj @@ -0,0 +1,17 @@ + + + + Exe + netcoreapp2.0 + + + + + + + + + + + + diff --git a/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Sandwych.MapMatchingKit.Examples.HelloWorldApp.csproj b/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Sandwych.MapMatchingKit.Examples.HelloWorldApp.csproj index 00ee155..a9e0232 100644 --- a/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Sandwych.MapMatchingKit.Examples.HelloWorldApp.csproj +++ b/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Sandwych.MapMatchingKit.Examples.HelloWorldApp.csproj @@ -10,7 +10,7 @@ - + diff --git a/test/Sandwych.Hmm.Tests/Sandwych.Hmm.Tests.csproj b/test/Sandwych.Hmm.Tests/Sandwych.Hmm.Tests.csproj index ebd6c64..fcc9408 100644 --- a/test/Sandwych.Hmm.Tests/Sandwych.Hmm.Tests.csproj +++ b/test/Sandwych.Hmm.Tests/Sandwych.Hmm.Tests.csproj @@ -10,7 +10,7 @@ - + diff --git a/test/Sandwych.MapMatchingKit.Tests/Matching/MatcherTest.cs b/test/Sandwych.MapMatchingKit.Tests/Matching/MatcherTest.cs index 9fe5923..5f3bc96 100644 --- a/test/Sandwych.MapMatchingKit.Tests/Matching/MatcherTest.cs +++ b/test/Sandwych.MapMatchingKit.Tests/Matching/MatcherTest.cs @@ -19,7 +19,7 @@ public class MatcherTest : TestBase private readonly ISpatialOperation _spatial = new GeographySpatialOperation(); private readonly DijkstraRouter _router = new DijkstraRouter(); private readonly RoadMap _map; - private readonly Func _cost = new Func(Costs.TimeCost); + private readonly Func _cost = Costs.TimeCost; class MockedRoadReader { diff --git a/test/Sandwych.MapMatchingKit.Tests/Sandwych.MapMatchingKit.Tests.csproj b/test/Sandwych.MapMatchingKit.Tests/Sandwych.MapMatchingKit.Tests.csproj index 9a0949c..e892c45 100644 --- a/test/Sandwych.MapMatchingKit.Tests/Sandwych.MapMatchingKit.Tests.csproj +++ b/test/Sandwych.MapMatchingKit.Tests/Sandwych.MapMatchingKit.Tests.csproj @@ -11,7 +11,7 @@ - + diff --git a/test/Sandwych.MapMatchingKit.Tests/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouterTest.cs b/test/Sandwych.MapMatchingKit.Tests/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouterTest.cs index f8f7a6e..0637297 100644 --- a/test/Sandwych.MapMatchingKit.Tests/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouterTest.cs +++ b/test/Sandwych.MapMatchingKit.Tests/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouterTest.cs @@ -5,6 +5,7 @@ using Sandwych.MapMatchingKit.Topology; using Sandwych.MapMatchingKit.Topology.PrecomputedDijkstra; using Xunit; +using Xunit.Extensions; namespace Sandwych.MapMatchingKit.Tests.Topology.PrecomputedDijkstra { @@ -37,10 +38,23 @@ public PrecomputedDijkstraRouterTest() _map = new Graph(roads); } + private (IReadOnlyDictionary> expected, + IReadOnlyDictionary> actual) + FindPaths( + RoadPoint source, IEnumerable targets, + Func cost, Func bound, double maxRadius) + { + var dijkstraRouter = new DijkstraRouter(); + var precomputedRouter = new PrecomputedDijkstraRouter(_map, cost, bound, maxRadius); + var expectedPath = dijkstraRouter.Route(source, targets, cost, bound, maxRadius); + var actualPath = precomputedRouter.Route(source, targets, cost, bound, maxRadius); + return (expectedPath, actualPath); + } + [Fact] - public void ShortestPathTest1() + public void TestSimpleShortestPath() { - var max = 200D; + var maxRadius = 200D; var start = new RoadPoint(_map.GetEdge(0), 0.3); var targets = new RoadPoint[] { new RoadPoint(_map.GetEdge(10), 0.5), @@ -48,18 +62,14 @@ public void ShortestPathTest1() }; Func cost = r => r.Weight; - var dijkstraRouter = new DijkstraRouter(); - var precomputedRouter = new PrecomputedDijkstraRouter(_map, cost, cost, max); + var paths = this.FindPaths(start, targets, cost, cost, maxRadius); - var expectedPath = dijkstraRouter.Route(start, targets, cost, cost, max); - var actualPath = precomputedRouter.Route(start, targets, cost, cost, max); - - Assert.Single(actualPath); - Assert.Equal(expectedPath, actualPath); + Assert.Single(paths.actual); + Assert.Equal(paths.expected, paths.actual); } [Fact] - public void SelfLoopTest() + public void SelfLoopTest1() { var max = 200D; var start = new RoadPoint(_map.GetEdge(0), 0.3); From 7dc3f243a7b284ca3158a10c973a70f9ddde4f81 Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Mon, 5 Mar 2018 12:19:25 +0800 Subject: [PATCH 14/37] fix matching with break transitions --- data/samples.oneday.geojson | 5285 +++++++++++++++++ .../Program.cs | 4 +- .../Markov/AbstractFilter.cs | 2 +- .../Markov/AbstractStateCandidate.cs | 10 +- src/Sandwych.MapMatchingKit/Markov/IFilter.cs | 2 +- .../Markov/IStateCandidate.cs | 4 +- .../Matching/Matcher.cs | 2 +- .../Matching/MatcherCandidate.cs | 9 - .../Markov/FilterTest.cs | 4 +- 9 files changed, 5295 insertions(+), 27 deletions(-) create mode 100644 data/samples.oneday.geojson diff --git a/data/samples.oneday.geojson b/data/samples.oneday.geojson new file mode 100644 index 0000000..30a09fc --- /dev/null +++ b/data/samples.oneday.geojson @@ -0,0 +1,5285 @@ +{ +"type": "FeatureCollection", +"name": "samples", +"crs": { "type": "name", "properties": { "name": "urn:ogc:def:crs:OGC:1.3:CRS84" } }, +"features": [ +{ "type": "Feature", "properties": { "time": "2016-12-14-00.00.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742145, 25.049927 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.01.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742145, 25.049927 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.02.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742145, 25.049927 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.03.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742145, 25.049927 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.03.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742145, 25.049927 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.04.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742145, 25.049927 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.06.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742145, 25.049927 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.02.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742145, 25.049927 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.07.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.09.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.10.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.12.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.12.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.13.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.14.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.14.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.14.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.15.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.15.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.15.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.16.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.18.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.20.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.22.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.23.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.23.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.24.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.26.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.27.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.27.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.28.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.28.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.29.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.29.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.29.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.30.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.31.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742035, 25.04987 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.32.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742035, 25.04987 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.31.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742035, 25.04987 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.32.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742035, 25.04987 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.32.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742035, 25.04987 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.33.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742035, 25.04987 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.34.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742035, 25.04987 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.35.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.36.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.38.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.38.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.40.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.42.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.42.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.43.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.43.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.45.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.45.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.48.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.00.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742145, 25.049927 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.00.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742145, 25.049927 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.01.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742145, 25.049927 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.02.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742145, 25.049927 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.05.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742145, 25.049927 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.06.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742145, 25.049927 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.06.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742145, 25.049927 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.07.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.08.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.09.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.09.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.12.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.13.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.14.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.16.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.16.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.17.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.17.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.19.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.20.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.21.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.21.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.22.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.22.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.23.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.24.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.24.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.26.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.26.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.28.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.30.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742035, 25.04987 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.31.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742035, 25.04987 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.32.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742035, 25.04987 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.34.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742035, 25.04987 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.36.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.38.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.37.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.38.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.39.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.39.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.39.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.41.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.41.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.41.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.43.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.44.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.44.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.44.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.46.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.46.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.47.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.45.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.48.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.50.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.51.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.00.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742145, 25.049927 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.01.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742145, 25.049927 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.04.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742145, 25.049927 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.05.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742145, 25.049927 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.06.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.07.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.08.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.08.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.09.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.10.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.10.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.11.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.11.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.11.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.13.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.15.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.16.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.18.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.17.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.18.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.19.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.19.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.19.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.20.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.20.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.21.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.21.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.22.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.24.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.25.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.25.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.27.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.30.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.30.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.31.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742035, 25.04987 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.33.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742035, 25.04987 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.33.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742035, 25.04987 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.34.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742035, 25.04987 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.34.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742035, 25.04987 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.36.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.36.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.37.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.39.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.40.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.40.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.42.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.42.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.43.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.44.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.46.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.49.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.50.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.51.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.53.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.52.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.01.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742145, 25.049927 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.02.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742145, 25.049927 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.03.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742145, 25.049927 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.03.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742145, 25.049927 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.04.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742145, 25.049927 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.04.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742145, 25.049927 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.05.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742145, 25.049927 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.05.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742145, 25.049927 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.07.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.08.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.11.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.12.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.13.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.10.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74207, 25.05004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.17.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.18.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.23.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.25.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.25.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.26.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.27.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.28.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.29.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742075, 25.049685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.33.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742035, 25.04987 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.35.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742035, 25.04987 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.35.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742117, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.35.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.37.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.37.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.40.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.41.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.45.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.47.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.46.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.47.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.47.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.48.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.49.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.51.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.52.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.52.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.56.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.57.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.58.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742092, 25.050105 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.58.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742092, 25.050105 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.59.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74215, 25.0499 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.00.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74215, 25.0499 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.00.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74215, 25.0499 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.01.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74215, 25.0499 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.55.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.03.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74215, 25.0499 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.06.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74203, 25.049722 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.06.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74203, 25.049722 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.06.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74203, 25.049722 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.07.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74203, 25.049722 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.48.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.49.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.49.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.50.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.50.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.51.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.52.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.53.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.55.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.55.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.56.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.57.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742095, 25.0501 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.57.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742092, 25.050105 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.58.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742092, 25.050105 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.01.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74215, 25.0499 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.02.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74215, 25.0499 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.03.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74215, 25.0499 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.03.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74215, 25.0499 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.05.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74215, 25.0499 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.04.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74215, 25.0499 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.07.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74203, 25.049722 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.06.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74203, 25.049722 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.07.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74203, 25.049722 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.09.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742015, 25.04995 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.10.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741995, 25.049957 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.11.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741995, 25.049957 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.12.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741995, 25.049957 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.13.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741995, 25.049957 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.15.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742132, 25.049765 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.18.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741935, 25.049782 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.17.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741935, 25.049782 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.17.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741935, 25.049782 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.19.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741935, 25.049782 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.20.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74236, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.21.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74236, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.22.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74236, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.22.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74236, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.23.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74236, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.24.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.049775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.24.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.049775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.25.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.049775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.25.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.049775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.26.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.049775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.26.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.049775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.27.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.049775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.27.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741697, 25.049527 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.28.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.04979 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.29.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.04979 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.30.49.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.04979 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.32.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.04979 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.33.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.04979 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.34.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.04979 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.34.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.04979 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.37.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.40.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.54.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.54.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.55.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.56.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.56.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.58.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742092, 25.050105 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.57.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742092, 25.050105 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.59.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74215, 25.0499 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.59.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74215, 25.0499 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.00.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74215, 25.0499 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.01.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74215, 25.0499 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.01.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74215, 25.0499 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.02.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74215, 25.0499 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.02.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74215, 25.0499 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.03.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74215, 25.0499 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.05.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74215, 25.0499 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.05.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74215, 25.0499 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.08.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74203, 25.049722 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.08.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74203, 25.049722 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.08.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74203, 25.049722 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.08.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74203, 25.049722 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.09.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74203, 25.049722 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.11.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741995, 25.049957 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.11.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741995, 25.049957 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.14.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742132, 25.049765 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.14.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742132, 25.049765 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.14.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742132, 25.049765 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.19.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741935, 25.049782 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.20.49.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74236, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.21.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74236, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.22.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74236, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.23.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74236, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.25.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.049775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.27.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.049775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.28.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741697, 25.049527 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.29.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.04979 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.31.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.04979 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.31.34.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.04979 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.35.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.04979 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.35.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.04979 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.35.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.04979 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.36.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.04979 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.37.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.38.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.38.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.38.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.41.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.40.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.41.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.41.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.42.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.44.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.43.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.43.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.45.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.53.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.53.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.54.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.54.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-00.59.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74215, 25.0499 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.00.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74215, 25.0499 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.02.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74215, 25.0499 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.04.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74215, 25.0499 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.04.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74215, 25.0499 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.04.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74215, 25.0499 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.05.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74204, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.09.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741995, 25.049957 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.10.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741995, 25.049957 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.12.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741995, 25.049957 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.12.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741995, 25.049957 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.13.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741995, 25.049957 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.14.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742132, 25.049765 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.15.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741935, 25.049782 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.16.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741935, 25.049782 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.17.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741935, 25.049782 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.18.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741935, 25.049782 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.19.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741935, 25.049782 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.18.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741935, 25.049782 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.20.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74236, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.21.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74236, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.23.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74236, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.26.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.049775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.28.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741697, 25.049527 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.29.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.04979 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.30.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.04979 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.30.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.04979 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.32.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.04979 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.32.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.04979 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.32.34.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.04979 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.33.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.04979 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.33.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.04979 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.33.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.04979 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.34.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.04979 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.35.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.04979 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.36.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.04979 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.38.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.39.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.41.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.42.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.42.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.43.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.44.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.43.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.46.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.47.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.51.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742095, 25.04998 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.51.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742095, 25.04998 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.52.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742095, 25.04998 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.54.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742095, 25.04998 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.53.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742095, 25.04998 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.07.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74203, 25.049722 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.09.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741995, 25.049957 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.10.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741995, 25.049957 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.10.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741995, 25.049957 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.11.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741995, 25.049957 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.12.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741995, 25.049957 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.13.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741995, 25.049957 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.15.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741935, 25.049782 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.15.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742132, 25.049765 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.16.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741935, 25.049782 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.16.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741935, 25.049782 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.16.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741935, 25.049782 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.13.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742137, 25.04978 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.17.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741935, 25.049782 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.18.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741935, 25.049782 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.19.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741935, 25.049782 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.20.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74236, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.21.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74236, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.22.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74236, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.24.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.049775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.23.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74236, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.25.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.049775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.24.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.049775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.26.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.049775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.27.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.049775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.28.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.04979 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.29.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.04979 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.30.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.04979 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.31.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.04979 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.31.49.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.04979 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.34.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.04979 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.36.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.04979 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.37.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.36.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741975, 25.04979 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.37.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.39.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.39.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.39.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.42.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.44.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.45.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.45.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.45.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.47.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.47.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.49.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742095, 25.04998 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.49.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742095, 25.04998 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.53.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742095, 25.04998 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.56.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74208, 25.049875 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.57.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74208, 25.049875 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.57.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74208, 25.049875 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.59.34.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74208, 25.049875 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.00.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74208, 25.049875 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.00.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74208, 25.049875 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.01.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74208, 25.049875 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.40.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.40.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.44.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.46.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.48.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742095, 25.04998 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.48.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742095, 25.04998 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.49.49.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742095, 25.04998 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.50.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742095, 25.04998 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.47.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.50.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742095, 25.04998 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.50.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742095, 25.04998 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.51.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742095, 25.04998 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.52.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742095, 25.04998 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.52.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742095, 25.04998 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.53.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742095, 25.04998 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.53.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742095, 25.04998 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.56.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74208, 25.049875 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.56.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74208, 25.049875 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.57.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74208, 25.049875 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.57.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74208, 25.049875 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.58.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74208, 25.049875 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.59.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74208, 25.049875 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.59.49.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74208, 25.049875 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.00.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74208, 25.049875 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.01.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74214, 25.049922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.03.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74214, 25.049922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.05.34.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74214, 25.049922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.06.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74214, 25.049922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.06.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74214, 25.049922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.07.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74214, 25.049922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.08.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74214, 25.049922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.08.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74214, 25.049922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.09.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74214, 25.049922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.09.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742025, 25.049675 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.12.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742025, 25.049675 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.13.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742025, 25.049675 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.13.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742025, 25.049675 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.14.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742025, 25.049675 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.14.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742025, 25.049675 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.17.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.17.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.17.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.18.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.19.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.19.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.21.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.21.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.22.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.22.49.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.23.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.23.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.25.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.26.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.29.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741992, 25.049655 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.32.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.46.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.46.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7423, 25.050025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.48.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742095, 25.04998 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.48.49.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742095, 25.04998 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.49.34.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742095, 25.04998 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.50.34.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742095, 25.04998 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.51.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742095, 25.04998 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.54.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742095, 25.04998 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.55.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74208, 25.049875 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.55.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74183, 25.049577 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.54.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742185, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.55.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74208, 25.049875 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.59.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74208, 25.049875 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.00.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74208, 25.049875 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.02.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74214, 25.049922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.03.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74214, 25.049922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.06.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74214, 25.049922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.11.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742025, 25.049675 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.11.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742025, 25.049675 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.12.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742025, 25.049675 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.14.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742025, 25.049675 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.15.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.16.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.16.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.17.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.18.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.19.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.20.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.20.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.21.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.22.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.23.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.24.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.24.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.23.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.25.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.25.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.28.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.29.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.29.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741992, 25.049655 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.31.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.31.34.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.32.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.33.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.35.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.36.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.36.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.38.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.40.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.41.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.40.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.40.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.42.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.43.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.43.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.54.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742172, 25.049962 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.55.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742185, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.52.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742095, 25.04998 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.56.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74208, 25.049875 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.58.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74208, 25.049875 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.58.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74208, 25.049875 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-01.58.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74208, 25.049875 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.01.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74214, 25.049922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.01.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74214, 25.049922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.02.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74214, 25.049922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.03.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74214, 25.049922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.03.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74214, 25.049922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.04.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74214, 25.049922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.04.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74214, 25.049922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.05.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74214, 25.049922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.05.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74214, 25.049922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.05.49.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74214, 25.049922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.07.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74214, 25.049922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.07.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74214, 25.049922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.08.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74214, 25.049922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.08.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74214, 25.049922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.10.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742025, 25.049675 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.12.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742025, 25.049675 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.13.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742025, 25.049675 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.15.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.15.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.16.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.18.49.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.20.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.20.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.25.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.26.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.27.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.27.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.30.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741992, 25.049655 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.29.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741992, 25.049655 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.31.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.31.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.32.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.33.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.34.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.30.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.049735 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.36.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.36.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.37.34.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.38.34.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.39.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.41.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.42.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.44.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.44.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.46.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.48.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74201, 25.04984 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.45.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.49.34.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74201, 25.04984 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.02.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74214, 25.049922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.02.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74214, 25.049922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.04.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74214, 25.049922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.04.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74214, 25.049922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.06.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74214, 25.049922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.07.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74214, 25.049922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.09.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742025, 25.049675 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.09.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742025, 25.049675 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.10.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742025, 25.049675 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.11.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742025, 25.049675 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.10.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742025, 25.049675 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.10.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742025, 25.049675 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.11.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742025, 25.049675 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.12.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742025, 25.049675 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.13.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742025, 25.049675 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.14.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742025, 25.049675 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.15.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.16.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.18.34.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.19.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.21.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.22.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.24.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.24.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.26.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.26.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.27.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.27.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.28.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.28.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.28.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742167, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.30.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741992, 25.049655 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.30.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.32.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.33.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.33.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.34.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.34.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.34.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.35.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.35.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.37.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.37.49.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.38.49.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.38.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.39.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.39.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.41.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.42.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.44.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.45.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.46.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.47.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.47.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.49.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74201, 25.04984 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.35.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.37.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.39.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.40.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.41.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.42.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.43.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.43.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.44.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.45.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.45.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.47.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.48.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742012, 25.049835 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.49.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74201, 25.04984 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.50.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74201, 25.04984 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.50.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74201, 25.04984 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.51.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742125, 25.049755 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.52.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742125, 25.049755 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.53.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74289, 25.04959 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.54.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74301, 25.045545 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.54.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742995, 25.046922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.55.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743005, 25.04526 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.56.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743317, 25.03942 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.57.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743635, 25.035335 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.57.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743865, 25.032925 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.58.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741965, 25.02626 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.58.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74153, 25.025075 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.00.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741302, 25.0248 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.01.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741157, 25.02482 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.02.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73883, 25.024207 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.04.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.05.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.06.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.08.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.08.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.10.49.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.11.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.12.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.12.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.15.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735972, 25.02682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.15.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735972, 25.02682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.16.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735972, 25.02682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.18.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735972, 25.02682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.18.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735972, 25.02682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.20.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735972, 25.02682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.21.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735972, 25.02682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.22.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735972, 25.02682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.24.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.24.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.24.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.25.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.25.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.28.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.28.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.29.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.50.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742125, 25.049755 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.51.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742125, 25.049755 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.51.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742125, 25.049755 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.51.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742125, 25.049755 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.53.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742125, 25.049755 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.52.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742125, 25.049755 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.56.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74343, 25.03751 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.57.34.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743635, 25.03036 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.57.49.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742702, 25.028075 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.58.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741302, 25.0248 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.58.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741302, 25.0248 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.59.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741302, 25.0248 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.00.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741302, 25.0248 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.00.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741302, 25.0248 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.02.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.737092, 25.023727 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.03.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735305, 25.026505 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.02.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73547, 25.02555 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.04.49.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.04.34.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.05.34.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.07.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.07.34.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.08.49.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.10.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.11.49.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.11.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.12.49.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.13.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.16.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735972, 25.02682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.17.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735972, 25.02682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.17.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735972, 25.02682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.17.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735972, 25.02682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.19.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735972, 25.02682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.19.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735972, 25.02682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.20.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735972, 25.02682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.21.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735972, 25.02682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.25.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.26.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.27.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.26.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.27.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.29.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.29.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.30.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.30.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.31.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.31.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.33.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.33.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.34.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.36.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.36.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.40.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.41.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.41.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.50.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74201, 25.04984 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.52.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742125, 25.049755 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.52.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742125, 25.049755 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.53.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742212, 25.049792 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.54.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743005, 25.04526 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.55.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743005, 25.04526 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.59.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741302, 25.0248 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.59.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741302, 25.0248 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.59.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741302, 25.0248 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.01.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741302, 25.0248 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.02.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73636, 25.023885 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.03.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.736, 25.026885 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.03.49.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.04.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.05.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.06.49.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.06.34.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.07.49.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.09.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.09.34.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.09.49.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.10.34.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.11.34.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.13.49.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.15.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735972, 25.02682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.16.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735972, 25.02682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.19.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735972, 25.02682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.20.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735972, 25.02682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.22.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735972, 25.02682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.23.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735972, 25.02682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.22.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735972, 25.02682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.23.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.23.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735625, 25.02697 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.25.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.26.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.27.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.29.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.31.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.32.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.34.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.34.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.34.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.35.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.36.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.36.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.37.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.38.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.39.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.40.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.42.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.42.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.42.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.42.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.43.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.44.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.46.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.46.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.48.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.47.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742105, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.48.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74201, 25.04984 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.53.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742957, 25.04851 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.54.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743005, 25.04526 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.55.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743005, 25.04526 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.56.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743125, 25.04321 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.55.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74296, 25.044735 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.56.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743215, 25.041255 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-02.49.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74201, 25.04984 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.01.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741302, 25.0248 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.00.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741302, 25.0248 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.01.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74041, 25.024755 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.03.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735885, 25.026925 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.06.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.05.49.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.07.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.08.34.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.09.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.10.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.12.34.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.13.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.13.34.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.15.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735972, 25.02682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.16.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735972, 25.02682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.17.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735972, 25.02682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.18.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735972, 25.02682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.19.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735972, 25.02682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.18.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735972, 25.02682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.21.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735972, 25.02682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.20.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735972, 25.02682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.21.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735972, 25.02682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.22.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735972, 25.02682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.24.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.23.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.26.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.27.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.28.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.32.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.32.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.33.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.35.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.38.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.39.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.39.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.43.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.44.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.46.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.48.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.48.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.50.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.51.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.52.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.30.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.28.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.30.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.31.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.32.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.33.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.35.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.35.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.37.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.37.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.38.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.37.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.38.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.39.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.40.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.40.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.41.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.41.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.43.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.45.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.46.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.45.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.47.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.49.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.49.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.49.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.51.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.51.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.53.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.54.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.54.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.55.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.57.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.58.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.58.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.59.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.00.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.01.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.03.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.03.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.04.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.04.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.09.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735872, 25.02688 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.08.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735872, 25.02688 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.09.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735872, 25.02688 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.10.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.10.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.11.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.11.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.13.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.14.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.15.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.18.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.20.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.21.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.44.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.43.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.45.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.46.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.47.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.47.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.48.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.49.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.50.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.51.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.52.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.53.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.53.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.55.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.57.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.57.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.58.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.59.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.59.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.00.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.59.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.01.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.02.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.01.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.02.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.04.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735935, 25.02691 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.05.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735935, 25.02691 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.06.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735935, 25.02691 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.07.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735872, 25.02688 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.09.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735872, 25.02688 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.11.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.11.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.12.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.12.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.13.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.13.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.14.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.15.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.17.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.17.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.19.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.20.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.20.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.20.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.21.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.24.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.24.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.26.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.25.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.27.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.29.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.30.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.33.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.35.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.36.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.52.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.54.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.55.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.56.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.56.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.57.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.58.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.01.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.04.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735935, 25.02691 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.05.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735935, 25.02691 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.05.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735935, 25.02691 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.06.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735935, 25.02691 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.06.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735935, 25.02691 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.07.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735872, 25.02688 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.07.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735872, 25.02688 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.07.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735872, 25.02688 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.08.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735872, 25.02688 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.09.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735872, 25.02688 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.10.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.10.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.12.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.14.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.14.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.15.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.16.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.16.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.18.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.19.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.19.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.22.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.21.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.23.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.24.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.22.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.25.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.25.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.28.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.28.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.29.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.30.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.31.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.32.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.33.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.34.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.34.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.35.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.36.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.37.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.37.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.38.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.38.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.39.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.40.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.42.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.44.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.45.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.44.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.46.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.47.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.48.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.50.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.50.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.52.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.53.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.54.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.56.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.55.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-03.56.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.00.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.00.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.02.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.02.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.03.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.03.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735622, 25.026975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.05.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735935, 25.02691 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.06.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735867, 25.02688 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.08.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735872, 25.02688 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.08.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735872, 25.02688 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.13.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.15.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.12.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.16.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.16.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.17.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.17.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.18.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.18.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.19.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.21.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.23.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.26.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.27.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.28.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.28.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.29.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.31.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.31.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.32.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.34.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.35.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.36.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.39.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.38.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.39.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.40.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.40.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.42.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.42.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.45.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.43.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.22.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.22.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.23.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.23.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.24.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.25.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.26.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.26.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.27.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.27.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.29.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.30.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.31.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.30.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.32.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.32.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.33.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.33.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.34.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.35.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.36.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.37.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.37.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.38.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.39.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.40.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.41.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.41.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.43.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.44.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.44.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.45.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.46.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.49.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.50.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.51.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.52.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.53.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.53.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.54.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.54.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.55.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.56.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.57.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.57.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.59.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.00.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.01.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.02.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.02.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.04.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.06.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.06.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.07.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.08.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.41.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.41.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.42.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.43.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.43.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.44.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.46.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.46.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.47.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.48.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.48.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.49.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.49.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.49.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.52.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.51.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.52.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.53.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.54.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.55.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.55.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.56.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.57.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.57.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.58.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.00.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.01.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.02.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.03.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.05.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.05.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.06.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.07.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.08.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.09.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.09.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.10.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.11.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.11.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.13.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.15.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.15.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.16.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.16.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.18.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.19.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.19.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.20.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.21.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.21.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.21.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.22.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.23.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.24.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.24.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.46.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.47.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.48.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.50.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.50.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.52.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.55.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.56.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.58.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.58.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.59.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.59.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.01.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.01.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.02.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.03.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.04.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.05.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.05.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.08.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.09.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.04.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.10.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.11.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.12.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.12.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.14.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.14.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.15.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.15.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.16.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.17.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.17.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.18.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.19.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.20.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.21.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.22.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.22.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.23.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.24.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.26.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.25.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.27.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.28.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.29.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.29.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.33.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.33.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.34.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.35.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.36.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.36.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.37.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.37.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.45.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.45.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.47.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.47.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.48.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.50.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.51.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.51.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.53.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.54.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.56.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.58.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-04.59.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.00.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.00.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.03.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.03.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.04.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.06.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.07.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.07.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.10.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.14.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.13.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.16.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.17.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.18.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.18.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.20.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.23.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.24.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.26.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.27.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.28.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.29.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.30.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.31.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.30.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.32.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.33.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.35.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.35.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.35.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.36.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.41.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.41.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.42.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.42.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.43.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.44.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.44.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.45.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.46.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.48.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.48.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.08.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.09.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.10.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.11.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.12.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.13.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.12.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.13.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.14.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.17.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.19.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.20.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.22.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.23.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.25.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.25.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.26.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.31.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.31.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.31.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.32.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.32.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.34.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.36.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.38.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.39.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.40.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.39.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.41.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.42.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.42.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.45.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.46.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.47.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.49.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.49.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.50.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.50.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.51.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.52.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.54.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.54.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.54.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.56.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.56.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.56.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.56.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.58.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.58.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.00.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.00.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.01.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.02.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.03.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.05.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.25.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.27.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.26.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.27.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.28.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.28.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.29.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.30.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.30.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735837, 25.026837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.32.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.33.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.34.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.34.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.37.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.37.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.38.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.38.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.39.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.39.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.41.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.44.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.46.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.50.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.52.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.52.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.52.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.55.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.57.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.01.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.03.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.04.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.04.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.05.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.05.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.06.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.08.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.08.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.09.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.09.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.10.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735845, 25.026775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.11.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735845, 25.026775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.13.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735845, 25.026775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.12.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735845, 25.026775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.13.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735845, 25.026775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.13.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735845, 25.026775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.14.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735845, 25.026775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.14.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735845, 25.026775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.15.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735845, 25.026775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.15.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735845, 25.026775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.16.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735845, 25.026775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.20.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735947, 25.02681 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.21.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735947, 25.02681 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.22.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.733825, 25.0279 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.24.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.732215, 25.030147 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.23.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.731605, 25.030905 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.38.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.40.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.40.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.40.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.43.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.43.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.44.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.43.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.45.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.46.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.47.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.47.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.48.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.47.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.49.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.50.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.53.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.53.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.54.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.55.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.55.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.57.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.58.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.58.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.59.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.00.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.00.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.01.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.02.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.03.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.04.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.05.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.06.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.09.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.11.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735845, 25.026775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.11.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735845, 25.026775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.12.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735845, 25.026775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.14.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735845, 25.026775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.15.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735845, 25.026775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.15.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735845, 25.026775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.16.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735845, 25.026775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.17.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735845, 25.026775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.17.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735845, 25.026775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.17.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735845, 25.026775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.18.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735875, 25.02678 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.19.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735875, 25.02678 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.20.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735875, 25.02678 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.21.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735155, 25.02635 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.22.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.734685, 25.026795 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.22.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73309, 25.02908 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.24.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.732822, 25.02938 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.24.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.733215, 25.02879 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.25.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735167, 25.026025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.28.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743965, 25.019732 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.30.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.754475, 25.017995 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.06.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.06.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.07.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.08.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.09.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.10.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735845, 25.026775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.12.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735845, 25.026775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.13.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735845, 25.026775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.10.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735845, 25.026775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.16.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735845, 25.026775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.16.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735845, 25.026775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.17.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735845, 25.026775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.18.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735875, 25.02678 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.18.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735875, 25.02678 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.18.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735875, 25.02678 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.19.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735875, 25.02678 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.19.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735875, 25.02678 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.19.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735875, 25.02678 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.20.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735947, 25.02681 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.21.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735947, 25.02681 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.21.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735815, 25.026645 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.23.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.730785, 25.031912 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.24.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.733435, 25.028525 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.25.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735147, 25.02606 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.26.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.736165, 25.024165 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.26.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73646, 25.02377 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.26.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73646, 25.02377 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.27.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73768, 25.02387 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.27.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74066, 25.024895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.28.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742252, 25.02288 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.28.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742787, 25.02046 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.29.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.745685, 25.019695 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.30.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.751495, 25.01871 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.31.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764205, 25.00453 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.31.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.762875, 25.010022 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.32.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764997, 24.996685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.33.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765085, 24.987065 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.33.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765075, 24.980767 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.34.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765175, 24.97399 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.34.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.762555, 24.971172 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.37.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.748495, 24.96084 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.38.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74794, 24.96043 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.39.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74794, 24.96043 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.39.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.745, 24.9578 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.41.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.750135, 24.953755 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.42.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.750115, 24.953815 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.44.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.744412, 24.94986 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.45.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741437, 24.947785 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.45.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741437, 24.947785 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.44.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743197, 24.948997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.46.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740737, 24.946657 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.45.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741005, 24.94746 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.46.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740685, 24.946792 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.46.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740652, 24.946837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.48.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.49.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.45.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.51.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.51.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.51.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.53.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.53.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.55.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.57.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.57.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.59.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.59.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-05.59.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.01.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.02.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.02.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.03.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.04.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.07.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.07.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.07.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.08.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735767, 25.026865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.10.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735845, 25.026775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.11.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735845, 25.026775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.12.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735845, 25.026775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.14.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735845, 25.026775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.20.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735875, 25.02678 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.22.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73212, 25.030285 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.23.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.731265, 25.031345 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.23.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7309, 25.031695 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.24.43.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.733215, 25.02879 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.25.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735167, 25.026025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.29.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.746745, 25.019525 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.30.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76101, 25.013335 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.32.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76506, 24.99042 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.34.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764445, 24.972615 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.35.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.762225, 24.970912 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.36.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.754082, 24.964965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.37.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74794, 24.96043 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.37.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74794, 24.96043 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.38.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74794, 24.96043 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.39.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74732, 24.959925 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.40.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.746877, 24.955615 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.40.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.748622, 24.953717 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.42.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.750135, 24.953755 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.42.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.749432, 24.953355 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.48.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740652, 24.946837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.51.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740652, 24.946837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.51.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740652, 24.946837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.52.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740652, 24.946837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.53.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742375, 24.948365 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.53.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743695, 24.949307 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.54.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.744595, 24.950042 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.25.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.734302, 25.02729 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.26.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735397, 25.02572 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.27.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.736577, 25.02366 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.28.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741835, 25.024935 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.27.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73874, 25.024195 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.29.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74809, 25.019307 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.29.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74952, 25.019072 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.31.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76432, 25.00706 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.32.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765025, 24.993622 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.33.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765095, 24.98371 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.33.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76502, 24.978555 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.35.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.759547, 24.96897 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.36.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.756035, 24.966395 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.35.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.757795, 24.967667 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.38.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74794, 24.96043 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.37.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74794, 24.96043 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.38.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74794, 24.96043 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.40.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.747812, 24.954595 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.41.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.750115, 24.95374 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.42.12.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.750135, 24.953755 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.42.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.749475, 24.953385 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.43.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.749432, 24.953355 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.44.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74197, 24.948132 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.45.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740525, 24.947015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.46.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740652, 24.946837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.47.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740652, 24.946837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.49.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740652, 24.946837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.49.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740652, 24.946837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.47.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740652, 24.946837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.50.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740652, 24.946837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.50.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740652, 24.946837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.51.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740652, 24.946837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.51.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740652, 24.946837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.52.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740652, 24.946837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.52.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740652, 24.946837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.53.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.744927, 24.950177 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.56.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740707, 24.9479 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.57.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740782, 24.9478 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.57.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74084, 24.94795 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.58.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74084, 24.94795 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.59.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740817, 24.947815 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.59.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74073, 24.947682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.00.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74073, 24.947682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.01.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74082, 24.947595 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.06.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73885, 24.933287 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.06.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.737957, 24.9341 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.07.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.08.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.09.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.09.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.09.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.11.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.11.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.12.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.30.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.758137, 25.016452 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.32.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765205, 24.99932 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.31.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76541, 25.002182 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.34.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765065, 24.975947 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.35.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76135, 24.970305 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.36.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.75207, 24.963477 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.36.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.750237, 24.96213 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.39.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.745615, 24.95861 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.40.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.746055, 24.956525 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.41.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.749382, 24.953255 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.41.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.750135, 24.953755 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.43.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.749015, 24.953047 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.43.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.747842, 24.952235 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.44.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.745712, 24.95077 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.43.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.746892, 24.95158 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.47.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740652, 24.946837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.47.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740652, 24.946837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.48.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740652, 24.946837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.48.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740652, 24.946837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.48.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740652, 24.946837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.49.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740652, 24.946837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.49.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740652, 24.946837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.52.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740497, 24.94699 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.53.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741152, 24.947492 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.54.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743265, 24.94907 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.54.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74098, 24.947485 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.55.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74067, 24.947812 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.56.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740707, 24.9479 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.56.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740782, 24.9478 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.59.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74073, 24.947682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.00.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74073, 24.947682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.01.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740572, 24.947015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.01.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740847, 24.947295 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.03.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.744467, 24.941417 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.04.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735542, 24.93476 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.04.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735157, 24.9343 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.06.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.739352, 24.933517 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.04.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.737065, 24.93592 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.07.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.10.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.10.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.10.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.11.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.13.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.13.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.14.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.14.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.14.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.15.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.15.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.16.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.16.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742285, 24.935635 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.17.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.737847, 24.934215 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.19.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73079, 24.93786 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.50.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740652, 24.946837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.50.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740652, 24.946837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.54.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741972, 24.94816 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.55.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740707, 24.9479 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.55.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740707, 24.9479 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.56.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740782, 24.9478 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.57.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74084, 24.94795 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.01.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74067, 24.947825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.00.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74073, 24.947682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.02.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74103, 24.946382 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.02.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741827, 24.945557 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.02.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742867, 24.944435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.03.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742685, 24.940117 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.04.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.739045, 24.937405 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.05.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.736907, 24.935222 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.05.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.736125, 24.935065 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.06.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74071, 24.934315 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.07.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741742, 24.935195 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.08.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.10.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.11.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.08.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.12.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.12.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.14.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.15.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.17.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.739905, 24.933882 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.17.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73883, 24.933295 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.18.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.737262, 24.934945 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.19.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735237, 24.934297 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.19.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.732762, 24.936017 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.20.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.725615, 24.936645 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.23.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.712425, 24.93929 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.23.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.712365, 24.939335 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.25.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.70592, 24.94292 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.26.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.701232, 24.944415 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.27.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69649, 24.946802 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.27.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.697947, 24.945635 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.28.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.694825, 24.949492 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.29.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69297, 24.952637 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.30.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.690882, 24.95412 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.30.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69218, 24.953465 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.32.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.68179, 24.960397 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.34.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.675012, 24.969142 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.35.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.67624, 24.972125 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.37.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.678182, 24.97182 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.36.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.676605, 24.972082 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.36.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.67684, 24.972012 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.38.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.682435, 24.970782 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.38.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.683082, 24.970387 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.39.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.68286, 24.969825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.40.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.68283, 24.969327 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.41.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681195, 24.968857 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.42.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.680337, 24.96889 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.55.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740707, 24.9479 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.57.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74084, 24.94795 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.58.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74084, 24.94795 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.58.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74084, 24.94795 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.58.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74084, 24.94795 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-06.59.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740807, 24.947802 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.00.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74073, 24.947682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.02.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743905, 24.943315 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.03.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.744897, 24.94222 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.03.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74068, 24.93865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.05.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.737152, 24.934955 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.05.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.737285, 24.9348 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.07.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742247, 24.935615 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.08.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.09.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.12.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.13.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.16.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.16.00.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.18.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73701, 24.935205 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.18.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.736747, 24.93546 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.19.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.734335, 24.934597 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.20.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.727315, 24.937875 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.21.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.723505, 24.932287 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.22.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.721027, 24.93343 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.20.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.729565, 24.938945 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.24.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.712365, 24.939335 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.24.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.71089, 24.94067 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.24.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.711985, 24.93957 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.26.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.701375, 24.944365 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.28.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69341, 24.951927 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.30.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.692785, 24.952972 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.32.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.686092, 24.958512 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.33.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.67346, 24.96254 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.35.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.676145, 24.97194 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.35.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.67624, 24.972125 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.37.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.67897, 24.97125 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.38.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.682957, 24.970515 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.38.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.683082, 24.970387 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.40.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.68281, 24.96918 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.42.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.679105, 24.968962 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.44.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.676077, 24.971747 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.45.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.676232, 24.972217 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.46.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.677877, 24.976275 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.45.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.67651, 24.972925 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.47.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.67433, 24.977287 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.48.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.670217, 24.97824 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.48.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.67108, 24.977325 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.49.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.668007, 24.981667 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.48.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.66931, 24.979925 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.52.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.664275, 24.99934 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.53.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.6631, 25.00048 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.55.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.660065, 25.00222 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.58.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.660057, 24.993497 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.13.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.15.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74272, 24.935832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.16.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741352, 24.93489 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.18.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.736387, 24.93516 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.21.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.724515, 24.9351 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.22.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.716825, 24.936452 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.24.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.711505, 24.940175 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.25.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.707755, 24.942085 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.26.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.70267, 24.94387 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.27.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69962, 24.944955 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.28.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.695497, 24.94828 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.29.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.692987, 24.952605 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.28.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.694212, 24.950525 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.29.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69297, 24.952637 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.30.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69297, 24.952637 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.31.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69023, 24.954475 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.27.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.700612, 24.94463 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.31.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.68982, 24.95477 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.31.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.688942, 24.955995 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.31.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.687535, 24.957305 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.32.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.679315, 24.961065 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.33.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.67684, 24.961717 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.33.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.674757, 24.962107 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.33.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.672877, 24.96396 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.34.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.67363, 24.965762 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.34.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.675727, 24.97089 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.36.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.67624, 24.972125 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.37.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681472, 24.97088 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.39.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.682985, 24.969995 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.40.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.682812, 24.96947 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.41.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.682767, 24.968997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.42.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.680877, 24.96885 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.41.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.682125, 24.968705 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.43.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.678087, 24.96903 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.42.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.678402, 24.96901 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.43.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.675405, 24.970027 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.44.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.676077, 24.971747 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.45.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.67711, 24.974405 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.46.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.67834, 24.97742 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.47.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.67543, 24.977497 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.47.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.677252, 24.97799 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.50.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.66004, 24.988965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.50.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.660632, 24.988575 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.51.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.65943, 24.992075 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.52.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.662715, 24.997385 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.51.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.661475, 24.99561 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.52.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.664275, 24.99934 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.53.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.664385, 24.999535 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.54.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.66199, 25.001197 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.56.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.661485, 25.001362 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.57.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.663982, 24.999247 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.57.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.663257, 24.998335 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.58.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.66093, 24.994977 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.17.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.738025, 24.93401 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.20.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.72887, 24.93897 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.21.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.72405, 24.933725 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.21.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.722722, 24.93219 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.22.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.719342, 24.934672 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.22.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.71786, 24.93572 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.23.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.715255, 24.9375 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.23.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.713572, 24.93855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.25.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.70935, 24.941345 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.25.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.704345, 24.94364 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.26.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.701232, 24.944415 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.29.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69297, 24.952637 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.32.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.684145, 24.959665 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.34.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.674365, 24.967545 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.35.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.676202, 24.972077 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.36.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.67647, 24.972127 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.37.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.680235, 24.970902 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.39.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.683022, 24.97004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.39.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.68286, 24.969825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.40.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.68281, 24.969407 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.41.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.682715, 24.968785 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.43.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.675615, 24.969247 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.44.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.675955, 24.971445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.46.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.678212, 24.97709 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.47.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.678485, 24.978005 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.49.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.665062, 24.98508 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.50.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.66192, 24.987802 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.49.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.666495, 24.983527 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.50.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.660632, 24.988575 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.51.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.659252, 24.990052 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.53.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.664275, 24.99934 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.55.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.66064, 25.001992 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.54.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.661302, 25.0016 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.56.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.66083, 25.001735 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.56.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.662822, 25.00056 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.56.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.662115, 25.001 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.57.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.663972, 24.999817 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.59.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.65932, 24.989382 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.59.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.65889, 24.990622 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.59.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.659575, 24.988695 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.01.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.655355, 24.984325 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.03.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.65538, 24.983587 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.05.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.65813, 24.977395 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.06.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.655825, 24.97665 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.07.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.64977, 24.975242 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.09.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.65028, 24.96613 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.09.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.650407, 24.964585 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.11.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.65833, 24.963945 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.11.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.661325, 24.963695 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.12.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.664085, 24.964215 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.15.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.66416, 24.964537 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.15.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.66416, 24.964537 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.17.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.66416, 24.964537 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.17.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.66416, 24.964537 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.43.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.677162, 24.969115 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.44.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.67577, 24.970972 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.45.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.676627, 24.973332 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.46.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.677402, 24.97513 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.48.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.67268, 24.977162 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.49.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.663565, 24.98668 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.51.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.660455, 24.993837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.52.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.663895, 24.99889 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.53.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.66382, 25.00004 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.54.32.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.66199, 25.001197 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.54.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.662195, 25.001045 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.54.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.66199, 25.001197 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.55.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.660067, 25.00233 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.55.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.65996, 25.002305 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.57.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.66242, 24.99724 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.58.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.661675, 24.996207 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.58.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.65917, 24.992022 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.00.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.656575, 24.98716 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.01.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.65538, 24.98421 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.02.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.65538, 24.98421 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.02.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.65538, 24.98421 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.05.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.65741, 24.977917 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.04.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.655887, 24.979185 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.07.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.650095, 24.976275 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.07.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.64973, 24.975955 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.08.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.650005, 24.969535 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.09.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.650115, 24.967887 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.10.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.65519, 24.963715 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.12.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.66416, 24.964537 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.13.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.66416, 24.964537 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.13.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.66416, 24.964537 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.14.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.66416, 24.964537 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.15.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.66416, 24.964537 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.18.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.665782, 24.968165 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.19.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.66696, 24.970905 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.20.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.672442, 24.977125 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.21.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.677995, 24.97655 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.21.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.677267, 24.974862 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.22.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.676545, 24.97306 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.22.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.6753, 24.96981 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.24.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.67533, 24.962877 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.24.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.67533, 24.962877 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.25.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.675295, 24.962432 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.26.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.67499, 24.962087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.27.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.28.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.28.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.29.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.30.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.31.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.32.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.32.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.32.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.32.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-07.59.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.658715, 24.98804 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.00.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.655395, 24.98704 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.00.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.654207, 24.986915 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.01.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.654235, 24.98629 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.03.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.65538, 24.98421 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.03.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.655467, 24.98407 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.05.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.65671, 24.978345 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.05.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.658312, 24.976792 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.06.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.657157, 24.976692 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.06.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.65252, 24.97643 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.07.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.651167, 24.97634 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.08.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.649935, 24.970817 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.10.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.651532, 24.963605 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.09.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.650635, 24.963592 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.11.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.659795, 24.963565 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.11.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.66271, 24.963765 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.12.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.663835, 24.9637 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.13.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.66416, 24.964537 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.14.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.66416, 24.964537 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.14.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.66416, 24.964537 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.14.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.66416, 24.964537 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.15.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.66416, 24.964537 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.16.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.66416, 24.964537 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.16.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.66416, 24.964537 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.20.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.977115 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.21.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.677557, 24.977935 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.20.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.675452, 24.97739 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.22.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.67454, 24.96795 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.23.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.67337, 24.962605 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.25.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.67533, 24.962877 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.24.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.67533, 24.962877 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.26.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.67505, 24.962092 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.27.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.26.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.674222, 24.962222 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.28.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.29.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.30.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.30.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.31.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.31.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.33.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.35.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.37.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.37.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.39.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.674925, 24.968907 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.41.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681425, 24.97896 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.38.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.43.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.43.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.44.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.45.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.45.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.46.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.47.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.00.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.657645, 24.98748 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.01.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.65485, 24.985332 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.02.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.65538, 24.98421 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.02.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.65538, 24.98421 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.03.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.655467, 24.98407 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.04.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.655355, 24.9824 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.04.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.65542, 24.98024 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.04.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.655557, 24.981342 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.06.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.654162, 24.976537 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.08.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.64982, 24.973945 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.08.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.649877, 24.972375 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.10.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.65679, 24.96374 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.10.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.653295, 24.963725 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.12.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.66416, 24.964537 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.13.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.66416, 24.964537 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.16.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.66416, 24.964537 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.16.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.66416, 24.964537 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.17.43.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.66416, 24.964537 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.17.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.66416, 24.964537 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.18.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.6646, 24.965455 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.19.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.668762, 24.974787 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.19.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.667922, 24.973085 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.20.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.671127, 24.97725 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.21.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.67842, 24.977737 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.23.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.67403, 24.962175 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.24.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.67523, 24.962092 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.25.08.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.67533, 24.962877 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.25.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.67533, 24.962877 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.27.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.29.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.30.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.34.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.36.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.36.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.34.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.36.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.38.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673352, 24.962665 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.39.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.6742, 24.967115 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.39.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.675447, 24.970075 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.40.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.675962, 24.971515 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.41.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.678825, 24.978197 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.42.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.42.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.42.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.44.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.46.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.46.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.46.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.47.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.48.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.50.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.51.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.50.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.51.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.17.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.66416, 24.964537 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.18.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.665207, 24.966842 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.18.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.666325, 24.96942 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.19.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.669985, 24.97668 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.22.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.675965, 24.971505 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.23.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673662, 24.965775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.23.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.67287, 24.96386 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.25.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.67533, 24.962877 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.26.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673795, 24.96244 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.27.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.28.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.29.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.31.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.33.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.35.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.35.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.37.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.41.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.67837, 24.977462 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.40.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.67784, 24.976142 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.43.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.43.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.44.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.47.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.47.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.49.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.50.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.51.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.52.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.53.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.55.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.56.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.57.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.686062, 24.98018 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.58.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.687857, 24.980715 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.59.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.68992, 24.98122 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.58.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.689755, 24.981185 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.00.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.693125, 24.98173 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.00.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69628, 24.981815 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.01.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.697777, 24.98197 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.04.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703625, 24.980525 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.04.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703625, 24.980525 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.06.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703655, 24.980342 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.07.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703655, 24.980342 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.07.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703655, 24.980342 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.08.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703655, 24.980342 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.09.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703655, 24.980342 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.08.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703655, 24.980342 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.09.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703655, 24.980342 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.10.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703655, 24.980342 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.12.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.70372, 24.979555 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.12.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703797, 24.97696 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.13.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.705445, 24.976135 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.13.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.707512, 24.976405 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.17.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.709497, 24.981025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.17.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.709657, 24.982015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.18.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.71039, 24.98241 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.33.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.33.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.34.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.34.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.35.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.36.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.37.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.38.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673685, 24.962567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.38.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.672835, 24.963772 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.39.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.673477, 24.96538 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.40.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.676602, 24.973182 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.40.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.677215, 24.974645 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.41.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.680112, 24.9786 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.42.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.68185, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.44.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.45.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.45.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.48.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.48.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.49.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.52.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.51.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.53.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.53.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.54.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.55.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.57.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.685925, 24.980135 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.57.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.686062, 24.98018 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.58.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.6863, 24.98026 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.59.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69129, 24.981515 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.59.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.690157, 24.981275 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.00.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.694795, 24.981767 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.00.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69571, 24.981792 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.01.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.699085, 24.98203 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.02.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703455, 24.981935 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.03.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703625, 24.980525 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.03.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703625, 24.980525 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.04.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703625, 24.980525 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.04.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703625, 24.980525 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.05.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703655, 24.980342 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.06.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703655, 24.980342 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.07.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703655, 24.980342 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.10.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703655, 24.980342 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.11.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703655, 24.980342 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.12.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703732, 24.978547 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.13.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.70421, 24.97605 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.14.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.708735, 24.9765 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.15.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.709155, 24.97893 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.18.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.711577, 24.98249 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.20.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.71844, 24.985955 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.22.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.719745, 24.993175 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.23.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.719997, 24.99493 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.25.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7209, 25.00197 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.27.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.720882, 25.0024 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.27.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.720882, 25.0024 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.48.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.49.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.49.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.50.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.52.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.52.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.54.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.55.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.54.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.55.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.56.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.682707, 24.97928 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.56.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.68443, 24.979737 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.57.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.686062, 24.98018 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.01.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.700205, 24.982142 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.03.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703615, 24.980587 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.05.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703655, 24.980342 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.06.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703655, 24.980342 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.06.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703655, 24.980342 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.07.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703655, 24.980342 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.08.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703655, 24.980342 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.08.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703655, 24.980342 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.09.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703655, 24.980342 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.11.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703655, 24.980342 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.12.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703712, 24.980285 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.13.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.706562, 24.976332 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.14.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.708935, 24.9778 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.15.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.709052, 24.978205 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.16.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.709322, 24.980005 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.16.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.709365, 24.98023 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.16.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.709375, 24.98039 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.16.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.709375, 24.98039 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.17.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.709442, 24.98076 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.18.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.714432, 24.982532 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.19.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.716785, 24.982562 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.19.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.71569, 24.98258 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.20.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.718235, 24.984995 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.20.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.718695, 24.98715 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.21.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.718792, 24.987497 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.19.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.71791, 24.98345 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.21.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.718995, 24.98862 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.23.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.719997, 24.99493 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.23.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.720217, 24.996242 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.24.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.720602, 24.99926 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.24.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.721007, 25.001955 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.25.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.721017, 25.002052 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.26.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.720857, 25.00207 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.26.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.720892, 25.001965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.26.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.720882, 25.0024 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.27.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.720882, 25.0024 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.28.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.720882, 25.0024 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.34.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.720427, 25.005912 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.36.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.720137, 25.007167 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.36.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.720045, 25.007647 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.37.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.720002, 25.007925 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.53.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.54.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.56.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.681915, 24.979015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.58.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.686062, 24.98018 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-08.59.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.68992, 24.98122 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.01.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.696915, 24.981895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.02.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.701785, 24.982122 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.02.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.70296, 24.98215 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.02.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703595, 24.981265 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.03.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703625, 24.980525 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.05.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703625, 24.980525 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.05.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703625, 24.980525 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.09.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703655, 24.980342 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.10.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703655, 24.980342 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.10.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703655, 24.980342 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.11.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703655, 24.980342 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.11.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703655, 24.980342 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.14.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.708335, 24.97636 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.14.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.70883, 24.97717 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.15.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.709225, 24.979455 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.15.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.709282, 24.979742 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.17.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.709525, 24.981295 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.18.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.712867, 24.982535 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.19.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.71752, 24.982665 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.21.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.718857, 24.98792 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.21.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.719185, 24.98975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.22.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.719877, 24.994222 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.23.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.719995, 24.99508 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.25.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.721017, 25.002052 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.34.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.72046, 25.00569 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.35.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.72038, 25.006165 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.35.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.72028, 25.006555 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.37.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.720025, 25.00778 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.39.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.719742, 25.009255 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.39.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.719817, 25.0088 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.39.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.719705, 25.009485 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.40.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.719657, 25.00976 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.41.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.71941, 25.011295 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.42.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.715142, 25.01845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.42.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.716247, 25.016645 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.43.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.71747, 25.021325 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.44.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.718955, 25.021495 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.40.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.719627, 25.00997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.04.00.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741725, 25.014905 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.35.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.70932, 25.062365 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.36.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.70299, 25.060725 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.38.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.700377, 25.058925 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.39.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.694452, 25.056452 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.39.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.691275, 25.054345 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.40.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.690655, 25.054062 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.41.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69289, 25.050707 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.42.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69303, 25.047315 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.44.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69303, 25.0458 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.45.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.693025, 25.044717 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.38.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.719897, 25.008315 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.37.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.719932, 25.008175 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.38.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.719835, 25.008675 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.38.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.719845, 25.00862 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.40.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.71969, 25.00957 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.41.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.717995, 25.015132 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.42.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.714447, 25.0199 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.43.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.716055, 25.021195 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.44.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.718955, 25.021495 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.44.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.719182, 25.02158 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.45.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.719842, 25.020145 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.45.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.719842, 25.020145 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.46.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.71959, 25.020095 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.45.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.719842, 25.020145 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.45.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.719842, 25.020145 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.51.48.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.718157, 25.0241 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.24.13.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73043, 25.083485 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.36.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.704572, 25.061927 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.35.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.70479, 25.062085 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.39.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.693427, 25.055922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.39.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69201, 25.05495 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.40.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69149, 25.05304 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.41.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.692445, 25.05172 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.41.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69293, 25.050155 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.42.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.692965, 25.050115 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.41.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69293, 25.050155 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.42.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.693032, 25.0474 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.43.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.693067, 25.046302 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.44.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.693032, 25.045502 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.44.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69304, 25.045277 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.46.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.693025, 25.044717 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.47.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.693075, 25.043962 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.48.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.693195, 25.043367 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.37.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926025, 25.098637 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.38.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92526, 25.0992 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.38.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.925735, 25.09884 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.40.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921605, 25.093965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.40.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92272, 25.093165 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.41.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.918412, 25.09043 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.41.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.91718, 25.090992 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.42.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.91561, 25.092125 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.43.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.912765, 25.089605 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.45.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913547, 25.0883 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.45.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913547, 25.0883 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.46.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913547, 25.0883 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.47.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913547, 25.0883 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.47.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913547, 25.0883 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.48.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913197, 25.088685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.49.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913197, 25.088685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.50.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913197, 25.088685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.50.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913197, 25.088685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.51.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913197, 25.088685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.52.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913197, 25.088685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.53.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913197, 25.088685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.21.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.718792, 24.987497 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.21.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.718792, 24.987497 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.20.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.718792, 24.987497 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.24.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.72086, 25.000785 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.24.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.72039, 24.997815 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.25.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.721017, 25.002052 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.26.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.720882, 25.0024 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.27.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.720882, 25.0024 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.28.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.720882, 25.0024 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.28.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.720975, 25.002775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.36.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.720195, 25.006885 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.35.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.720215, 25.00683 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.38.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.719895, 25.008345 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.39.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.71978, 25.00904 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.41.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.71957, 25.0105 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.41.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.719005, 25.013167 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.43.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.714865, 25.02113 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.43.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.71879, 25.021465 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.03.23.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742195, 25.015165 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.34.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.713205, 25.059952 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.35.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.71117, 25.061235 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.35.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.70672, 25.06316 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.37.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.702295, 25.059875 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.36.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.702365, 25.059975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.37.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.701517, 25.05933 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.38.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.695357, 25.056855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.40.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.691057, 25.05422 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.40.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.6908, 25.053695 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.42.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.692982, 25.04908 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.43.07.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69303, 25.047315 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.43.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.693065, 25.047195 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.43.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69303, 25.047315 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.45.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69305, 25.04493 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.46.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.693025, 25.044717 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.47.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.693072, 25.043962 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.35.30.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92743, 25.09808 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.36.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92626, 25.098182 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.37.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926165, 25.098455 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.38.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.925585, 25.098967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.39.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92284, 25.09974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.39.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921595, 25.09572 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.40.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920885, 25.092842 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.41.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.919525, 25.091637 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.42.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.91474, 25.091925 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.43.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913547, 25.0883 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.44.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913547, 25.0883 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.45.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913547, 25.0883 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.46.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913547, 25.0883 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.48.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913215, 25.088785 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.49.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913197, 25.088685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.52.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913197, 25.088685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.52.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913197, 25.088685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.56.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.918695, 25.07887 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.56.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.919645, 25.078162 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.35.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.72029, 25.00652 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.36.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.720097, 25.007377 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.37.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.719995, 25.007965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.40.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7196, 25.010255 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.42.52.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.714282, 25.021007 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.44.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.719845, 25.021525 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.45.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.720005, 25.020435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-09.45.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.719842, 25.020145 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.23.39.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73043, 25.083485 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.34.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.712595, 25.060367 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.36.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.70399, 25.06151 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.37.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.702295, 25.059875 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.37.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.70218, 25.059725 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.38.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.696697, 25.057452 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.38.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69855, 25.058242 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.44.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69305, 25.045907 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.45.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.693042, 25.045052 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.45.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.693025, 25.044717 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.47.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.693035, 25.043985 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.46.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.693042, 25.044045 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.48.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.693925, 25.04245 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.48.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.694705, 25.04147 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.48.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.695335, 25.040675 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.59.49.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.707155, 25.015827 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.37.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92626, 25.098182 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.38.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.924502, 25.099855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.43.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913182, 25.088712 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.44.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913547, 25.0883 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.43.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913785, 25.09084 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.45.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913547, 25.0883 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.47.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913547, 25.0883 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.47.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.91339, 25.088555 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.48.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913215, 25.088785 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.50.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913197, 25.088685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.51.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913197, 25.088685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.50.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913197, 25.088685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.51.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913197, 25.088685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.52.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913197, 25.088685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.53.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.91447, 25.08728 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.54.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913675, 25.08502 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.55.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.914295, 25.081877 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.56.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.91782, 25.079502 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.55.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.916847, 25.080205 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.57.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.917387, 25.074717 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.58.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.91116, 25.071675 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.59.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.908, 25.070252 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.59.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.909447, 25.0709 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.02.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.899085, 25.063677 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.02.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.898167, 25.062565 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.03.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.894145, 25.060835 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.03.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.895552, 25.061282 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.09.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.884665, 25.051302 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.09.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.884665, 25.051302 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.10.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.884665, 25.051302 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.45.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.693025, 25.044717 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.46.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.693035, 25.043985 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.47.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.693075, 25.043962 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-10.49.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.695367, 25.040637 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.36.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92626, 25.098182 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.37.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.925995, 25.09865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.39.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921552, 25.097702 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.39.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921252, 25.09486 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.40.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921812, 25.093565 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.41.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.918602, 25.0906 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.42.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.915557, 25.092165 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.42.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.915557, 25.092165 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.44.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913547, 25.0883 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.44.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913547, 25.0883 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.46.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913547, 25.0883 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.46.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913547, 25.0883 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.48.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913215, 25.088785 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.49.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913197, 25.088685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.49.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913197, 25.088685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.51.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913197, 25.088685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.55.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.91316, 25.082565 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.53.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.91381, 25.08804 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.55.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.91567, 25.081027 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.57.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.9186, 25.07605 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.58.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.914542, 25.073225 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.59.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.906165, 25.06943 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.59.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.905052, 25.068912 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.00.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.903095, 25.068035 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.00.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.901917, 25.067192 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.02.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.898805, 25.063337 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.04.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.891365, 25.05977 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.05.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88643, 25.05603 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.05.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.887182, 25.05761 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.06.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.885135, 25.05231 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.06.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88506, 25.052077 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.07.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88506, 25.052077 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.08.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.884862, 25.051635 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.08.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88466, 25.051305 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.10.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.884665, 25.051302 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.11.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.13.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.14.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.15.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.20.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.20.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.21.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.22.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.22.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.23.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.23.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.25.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.25.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.26.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.26.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.53.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913455, 25.088442 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.54.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.91415, 25.086175 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.54.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.91234, 25.08315 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.54.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.912832, 25.083845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.56.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.919847, 25.077457 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.57.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.916692, 25.074397 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.58.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.91286, 25.07244 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.00.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.902217, 25.067472 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.01.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.900515, 25.065357 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.01.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.89955, 25.064197 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.03.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.89782, 25.06216 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.02.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.89914, 25.063735 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.04.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.892795, 25.060305 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.04.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.888627, 25.05874 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.04.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.890077, 25.05929 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.05.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.885625, 25.053735 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.05.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88596, 25.05466 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.06.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88506, 25.052077 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.06.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88538, 25.053025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.07.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88506, 25.052077 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.07.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88506, 25.052077 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.07.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88506, 25.052077 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.08.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88505, 25.052005 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.10.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.884665, 25.051302 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.11.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88513, 25.050905 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.11.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.12.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.13.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.13.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.14.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.15.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.16.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.16.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.17.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.17.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.18.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.18.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.20.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.22.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.23.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.23.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.24.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.24.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.25.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.30.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8874, 25.05112 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.31.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.890812, 25.051385 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.32.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.890937, 25.05142 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.34.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.890937, 25.05142 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.35.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.890877, 25.051787 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.41.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889435, 25.051482 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.43.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889435, 25.051482 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.43.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889435, 25.051482 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.45.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889435, 25.051482 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.45.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889435, 25.051482 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.12.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.12.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.13.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.14.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.16.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.17.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.19.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.16.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.20.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.21.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.21.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.22.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.25.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.21.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.27.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.27.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.28.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.29.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.885882, 25.05085 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.31.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.888717, 25.051285 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.31.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.890292, 25.051545 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.34.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.890937, 25.05142 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.34.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.890937, 25.05142 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.36.53.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88974, 25.051437 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.38.14.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88974, 25.051437 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.38.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88974, 25.051437 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.38.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88974, 25.051437 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.38.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88974, 25.051437 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.44.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889435, 25.051482 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.45.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889435, 25.051482 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.46.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889435, 25.051482 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.47.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889435, 25.051482 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.48.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88957, 25.051355 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.53.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889607, 25.051385 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.55.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889607, 25.051385 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.56.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889607, 25.051385 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.56.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889607, 25.051385 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.57.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889607, 25.051385 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.57.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889607, 25.051385 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.57.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889607, 25.051385 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.58.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889565, 25.051407 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.59.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889565, 25.051407 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.59.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889565, 25.051407 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.02.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.888257, 25.051225 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.03.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.887025, 25.050985 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.04.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88622, 25.05082 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.06.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.884207, 25.050835 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.06.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.882395, 25.049942 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.07.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.882445, 25.054437 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.09.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.87391, 25.054987 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.09.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.87681, 25.05667 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.11.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.862337, 25.046385 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.12.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.850755, 25.04051 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.14.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.821005, 25.034135 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.14.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.81793, 25.033592 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.57.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.9165, 25.074125 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-11.58.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.915755, 25.07377 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.00.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.90456, 25.068705 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.01.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.90163, 25.066735 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.01.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.901355, 25.066412 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.03.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.896942, 25.061657 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.08.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88495, 25.05182 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.09.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.884665, 25.051302 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.09.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.884665, 25.051302 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.11.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8856, 25.050862 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.12.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.10.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88466, 25.051085 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.14.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.15.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.15.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.17.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.18.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.18.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.19.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.19.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.19.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.24.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.24.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.26.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.26.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.27.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.28.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.27.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.28.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.28.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.29.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.29.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.30.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.888247, 25.05121 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.40.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889435, 25.051482 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.40.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889435, 25.051482 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.40.29.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889435, 25.051482 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.44.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889435, 25.051482 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.46.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889435, 25.051482 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.47.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889435, 25.051482 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.47.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889435, 25.051482 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.52.45.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889607, 25.051385 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.52.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889607, 25.051385 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.54.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889607, 25.051385 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.54.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889607, 25.051385 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.54.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889607, 25.051385 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.57.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889607, 25.051385 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.01.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889565, 25.051407 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.02.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.888842, 25.05131 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.05.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.885307, 25.050812 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.08.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.878615, 25.057587 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.12.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.847855, 25.039115 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.15.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.80768, 25.03842 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.17.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.78264, 25.03861 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.18.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77932, 25.03863 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.29.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8858, 25.05087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.30.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.886732, 25.051052 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.30.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88621, 25.05092 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.31.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88949, 25.051425 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.34.02.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.890937, 25.05142 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.34.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.890937, 25.05142 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.41.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889435, 25.051482 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.43.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889435, 25.051482 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.43.11.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889435, 25.051482 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.44.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889435, 25.051482 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.45.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889435, 25.051482 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.47.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889435, 25.051482 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.44.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889435, 25.051482 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.50.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88957, 25.051355 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.50.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88957, 25.051355 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.50.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88957, 25.051355 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.53.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889607, 25.051385 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.55.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889607, 25.051385 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.56.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889607, 25.051385 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.56.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889607, 25.051385 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.58.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889565, 25.051407 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.59.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889565, 25.051407 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.02.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889565, 25.051407 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.01.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889565, 25.051407 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.03.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.887812, 25.051115 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.03.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.886705, 25.050935 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.04.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.885797, 25.05079 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.06.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88373, 25.050425 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.06.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.883072, 25.050055 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.08.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.881847, 25.056425 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.08.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.880322, 25.05747 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.09.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.87681, 25.05667 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.10.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.867175, 25.050062 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.10.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.87146, 25.053447 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.10.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.869265, 25.051785 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.10.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.86493, 25.048222 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.11.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.853512, 25.041837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.12.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.84489, 25.037692 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.13.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8297, 25.03373 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.13.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.832732, 25.033612 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.14.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.826762, 25.034137 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.15.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.815035, 25.033675 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.15.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.810165, 25.03697 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.16.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.80475, 25.03897 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.16.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.795545, 25.039965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.17.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.79262, 25.039225 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.16.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.798595, 25.039755 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.17.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.78605, 25.038575 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.19.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.75839, 25.038735 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.20.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.754492, 25.041025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.20.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.750527, 25.043425 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.21.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74514, 25.044767 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.29.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.717355, 25.057315 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.33.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.704412, 25.06182 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.46.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889435, 25.051482 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.46.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889435, 25.051482 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.48.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889435, 25.051482 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.48.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889435, 25.051482 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.53.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889607, 25.051385 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.53.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889607, 25.051385 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.54.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889607, 25.051385 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.55.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889607, 25.051385 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.55.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889607, 25.051385 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.58.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889607, 25.051385 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.58.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889565, 25.051407 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-12.59.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889565, 25.051407 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.02.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889467, 25.051357 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.03.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88736, 25.051062 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.04.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.886705, 25.050935 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.04.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.886705, 25.050935 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.04.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.885532, 25.0508 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.05.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.884982, 25.050935 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.05.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.884747, 25.05105 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.05.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88448, 25.051157 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.07.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.882337, 25.051072 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.07.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88235, 25.05218 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.07.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.882402, 25.05279 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.08.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.877175, 25.056892 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.09.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.875942, 25.056145 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.11.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.85935, 25.044667 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.11.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.856265, 25.043165 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.12.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.842045, 25.036315 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.13.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.836005, 25.03402 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.13.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.83912, 25.03497 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.15.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.812297, 25.034932 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.16.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.80176, 25.03935 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.17.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.789592, 25.038572 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.18.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.775902, 25.03862 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.18.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76926, 25.038647 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.20.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.755835, 25.039272 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.21.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.748185, 25.044187 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.21.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74681, 25.044732 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.31.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.712955, 25.060047 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.32.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.709662, 25.062042 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.32.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.705925, 25.062857 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.33.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703887, 25.06146 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.35.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.70059, 25.059005 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.34.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.702272, 25.05984 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.37.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.692917, 25.058555 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.36.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69349, 25.057215 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.36.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.693217, 25.057822 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.37.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69273, 25.059217 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.40.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69115, 25.066152 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.39.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.691095, 25.06602 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.42.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.691295, 25.066657 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.42.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69145, 25.06673 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.43.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.692507, 25.066445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.43.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.693135, 25.066317 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.19.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76624, 25.038895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.19.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76373, 25.03928 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.19.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.761065, 25.039217 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.14.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.823905, 25.034345 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.30.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.715032, 25.05874 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.30.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.713595, 25.059645 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.32.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.710937, 25.061305 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.35.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.696065, 25.05716 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.38.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.690882, 25.063042 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.39.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.691095, 25.06602 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.40.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69115, 25.066152 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.40.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69115, 25.066237 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.41.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.691295, 25.066657 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.41.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.691295, 25.066657 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.44.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69804, 25.065802 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.45.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.700377, 25.06579 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.45.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.703195, 25.065302 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.47.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.711992, 25.060705 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.48.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.713177, 25.060315 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.46.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.706222, 25.06447 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.48.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.713822, 25.062502 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.49.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.714725, 25.063917 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.50.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.716212, 25.06857 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.50.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.71651, 25.069305 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.54.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.721917, 25.069065 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.56.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.729485, 25.065445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.57.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.729767, 25.065167 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.57.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.730592, 25.064547 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.57.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.732522, 25.062885 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.58.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.734557, 25.061195 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.58.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73461, 25.060892 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.01.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7357, 25.055847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.02.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.737165, 25.05401 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.02.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73872, 25.05182 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.03.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.738932, 25.051042 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.03.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.738932, 25.051042 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.03.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.738932, 25.051042 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.05.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7409, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.05.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7409, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.59.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73327, 25.059565 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.06.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740997, 25.051145 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.07.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741002, 25.051737 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.07.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741002, 25.051737 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.07.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741002, 25.051737 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.08.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741012, 25.052062 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.09.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74098, 25.052222 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.09.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74098, 25.052222 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.09.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74101, 25.051865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.10.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74099, 25.050307 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.11.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74201, 25.049815 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.11.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742255, 25.04985 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.12.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74297, 25.048212 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.12.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74299, 25.04646 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.13.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743045, 25.045545 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.18.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77256, 25.038632 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.20.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.753065, 25.042877 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.21.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.745895, 25.044715 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.30.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.716225, 25.057942 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.30.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.71343, 25.05976 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.31.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.71343, 25.05976 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.31.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.71343, 25.05976 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.31.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.71194, 25.060725 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.32.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.707985, 25.063135 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.33.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.704325, 25.061765 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.35.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69897, 25.058415 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.36.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.693727, 25.056575 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.38.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69069, 25.06451 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.38.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.690807, 25.065755 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.39.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.691095, 25.06602 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.38.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.690925, 25.065895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.40.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69115, 25.066152 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.41.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.691295, 25.066657 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.41.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.691295, 25.066657 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.42.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.691295, 25.066657 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.43.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.694367, 25.066045 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.43.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.695982, 25.06567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.44.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.696947, 25.06567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.47.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7105, 25.061435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.49.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.715175, 25.064752 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.51.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.716515, 25.069317 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.50.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.715872, 25.06747 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.51.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.716515, 25.069317 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.51.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.716515, 25.069317 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.52.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.716965, 25.070205 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.53.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.720295, 25.069612 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.53.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.720952, 25.069375 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.54.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.721905, 25.069065 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.55.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.725225, 25.068075 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.56.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.727777, 25.06684 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.59.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73275, 25.058485 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.00.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.733895, 25.057457 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.00.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.734632, 25.056805 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.01.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7357, 25.055847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.04.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73901, 25.050665 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.04.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740577, 25.049725 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.05.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7409, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.04.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.739822, 25.049837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.06.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74104, 25.049847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.06.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74102, 25.050537 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.07.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740962, 25.051535 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.08.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741002, 25.051737 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.08.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74098, 25.052222 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.10.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740982, 25.050672 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.10.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74099, 25.050305 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.13.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743045, 25.045545 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.13.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743045, 25.045545 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.13.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743045, 25.045545 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.14.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743145, 25.043605 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.33.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.70289, 25.06061 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.34.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.702277, 25.05984 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.34.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.701802, 25.059465 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.34.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.702272, 25.05984 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.35.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.697375, 25.05774 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.36.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69446, 25.056462 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.37.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.692232, 25.0607 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.37.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.691485, 25.06209 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.39.16.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.691095, 25.06602 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.39.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.691095, 25.06602 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.42.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.691295, 25.066657 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.44.28.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.697857, 25.06575 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.44.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.699265, 25.06591 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.45.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.700085, 25.065835 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.46.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.704832, 25.065017 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.46.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.707682, 25.063397 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.46.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.708905, 25.06228 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.47.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.71264, 25.060295 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.47.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.71284, 25.060185 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.51.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.716515, 25.069317 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.51.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.716647, 25.069717 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.52.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.717877, 25.070025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.52.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.719187, 25.06975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.54.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.721917, 25.069065 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.56.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.72664, 25.06767 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.57.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.731552, 25.063795 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.58.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.733965, 25.061725 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.58.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.733387, 25.062245 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.59.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73403, 25.060305 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.01.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.736417, 25.055065 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.02.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.738317, 25.05243 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.02.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.737845, 25.053015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.04.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.739147, 25.04994 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.08.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74098, 25.052222 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.10.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740985, 25.051365 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.11.43.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74201, 25.049815 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.12.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743045, 25.045545 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.14.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74317, 25.042385 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.15.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743322, 25.038842 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.18.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74819, 25.019347 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.18.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.750342, 25.018935 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.19.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.755975, 25.017535 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.19.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.75954, 25.015285 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.22.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76515, 25.002925 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.23.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765385, 25.0024 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.24.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765362, 25.001525 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.24.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765245, 25.001035 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.25.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765152, 25.000565 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.25.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765022, 24.999745 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.26.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764952, 24.99732 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.27.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765045, 24.988395 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.29.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76509, 24.981665 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.30.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765065, 24.98059 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.31.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765092, 24.976157 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.44.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.69784, 25.06575 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.45.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.70151, 25.065597 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.48.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.71332, 25.06101 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.48.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.713535, 25.0618 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.49.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.714112, 25.063175 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.49.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.71537, 25.06551 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.50.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.715597, 25.06648 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.52.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.719107, 25.069747 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.53.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.719187, 25.06975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.53.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.71932, 25.069947 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.54.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.721917, 25.069065 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.55.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.721917, 25.069065 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.55.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.723927, 25.068437 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.55.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.722457, 25.06882 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.56.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.72873, 25.066115 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-13.59.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.732605, 25.05891 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.00.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.733347, 25.05795 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.00.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735477, 25.05609 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.01.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.055725 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.03.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73892, 25.051142 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.05.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7409, 25.04974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.06.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741055, 25.04987 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.09.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74098, 25.052222 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.11.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741585, 25.049845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.11.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740977, 25.04998 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.12.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742897, 25.049675 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.14.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74307, 25.045525 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.14.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743102, 25.044665 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.16.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742347, 25.02733 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.17.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74367, 25.019572 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.18.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.745885, 25.019695 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.20.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.763005, 25.009725 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.22.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765365, 25.002465 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.24.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765255, 25.001067 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.25.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765065, 25.000095 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.29.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765092, 24.98166 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.30.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765092, 24.98166 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.31.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765057, 24.979437 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.33.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.759967, 24.969422 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.33.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.756885, 24.967162 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.34.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.75035, 24.9623 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.36.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.748082, 24.9606 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.37.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.748082, 24.9606 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.39.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.744942, 24.95838 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.41.15.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741912, 24.957787 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.41.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741912, 24.957787 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.41.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741292, 24.9583 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.41.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741805, 24.95786 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.42.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741167, 24.960145 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.43.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742675, 24.960902 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.46.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742675, 24.960902 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.49.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742675, 24.960902 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.49.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74264, 24.960495 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.48.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742675, 24.960902 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.15.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743245, 25.04062 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.15.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74364, 25.03543 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.16.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74383, 25.033152 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.16.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743785, 25.031105 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.16.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74317, 25.029257 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.17.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741742, 25.02535 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.17.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74212, 25.02313 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.21.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76435, 25.006455 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.19.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.757602, 25.016785 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.23.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765385, 25.0024 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.24.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7654, 25.002315 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.26.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764945, 24.995132 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.27.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76502, 24.990675 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.27.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76506, 24.986312 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.27.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765065, 24.984515 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.28.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765075, 24.98299 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.30.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765092, 24.98166 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.30.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76511, 24.981315 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.32.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.763115, 24.9717 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.32.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764637, 24.972897 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.32.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765217, 24.973832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.33.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.755415, 24.966077 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.34.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.75316, 24.964415 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.35.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.749045, 24.961317 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.35.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.748082, 24.9606 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.36.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.748082, 24.9606 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.36.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.748082, 24.9606 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.37.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.748082, 24.9606 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.39.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.744942, 24.95838 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.42.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742675, 24.960902 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.43.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742675, 24.960902 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.43.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742675, 24.960902 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.43.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742675, 24.960902 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.44.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742675, 24.960902 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.44.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742675, 24.960902 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.45.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742675, 24.960902 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.46.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742675, 24.960902 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.45.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742675, 24.960902 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.47.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742675, 24.960902 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.51.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74409, 24.958865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.46.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742675, 24.960902 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.52.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74409, 24.958865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.54.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74431, 24.95854 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.54.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74431, 24.95854 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.00.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76208, 24.970865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.01.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.763932, 24.972152 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.01.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.762202, 24.970952 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.02.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764675, 24.97265 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.02.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76481, 24.97274 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.03.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76481, 24.97274 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.04.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76481, 24.97274 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.05.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76567, 24.974135 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.06.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765695, 24.975055 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.06.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76562, 24.97718 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.15.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743452, 25.037145 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.17.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74261, 25.0209 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.18.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.752127, 25.01852 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.19.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.754045, 25.01807 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.20.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760977, 25.013417 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.20.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76212, 25.011335 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.20.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.763857, 25.00811 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.21.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76502, 25.003097 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.21.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76418, 25.004895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.21.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764855, 25.00328 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.22.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765045, 25.003067 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.22.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765385, 25.0024 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.23.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765385, 25.0024 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.23.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765385, 25.0024 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.26.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765035, 24.998835 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.25.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76502, 24.99951 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.26.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76499, 24.99293 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.28.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765077, 24.983125 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.28.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765075, 24.98299 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.29.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765085, 24.982527 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.28.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765075, 24.98299 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.29.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765092, 24.98166 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.31.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76516, 24.974872 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.31.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765087, 24.977697 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.32.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.761695, 24.97067 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.33.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.758135, 24.9681 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.34.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.754285, 24.965252 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.35.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.748082, 24.9606 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.35.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.748082, 24.9606 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.38.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.746972, 24.959845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.38.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.746167, 24.959257 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.38.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.745005, 24.958425 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.40.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.744647, 24.958165 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.39.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.744942, 24.95838 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.39.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.744942, 24.95838 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.40.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741922, 24.957772 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.42.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742315, 24.96072 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.40.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74356, 24.957305 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.44.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742675, 24.960902 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.49.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743425, 24.959615 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.50.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743777, 24.95919 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.50.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743777, 24.95919 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.51.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74409, 24.958865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.53.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.744225, 24.958615 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.54.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74431, 24.95854 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.01.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.763932, 24.972152 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.03.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76481, 24.97274 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.03.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76481, 24.97274 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.04.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76481, 24.97274 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.05.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76481, 24.97274 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.04.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76481, 24.97274 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.08.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765572, 24.979952 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.08.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76562, 24.97933 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.09.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765555, 24.981825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.34.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.751787, 24.963385 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.36.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.748082, 24.9606 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.37.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.748082, 24.9606 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.37.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.747542, 24.960255 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.38.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.744942, 24.95838 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.40.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742567, 24.95704 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.41.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740547, 24.959025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.42.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740397, 24.959695 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.44.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742675, 24.960902 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.45.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742675, 24.960902 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.45.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742675, 24.960902 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.47.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742675, 24.960902 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.47.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742675, 24.960902 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.46.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742675, 24.960902 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.48.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742675, 24.960902 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.47.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742675, 24.960902 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.48.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742675, 24.960902 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.48.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742675, 24.960902 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.49.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74254, 24.960955 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.52.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74409, 24.958865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.53.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74431, 24.95854 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.01.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.763512, 24.97187 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.02.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76481, 24.97274 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.02.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76481, 24.97274 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.04.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76481, 24.97274 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.05.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76481, 24.97274 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.06.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765635, 24.97636 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.07.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76562, 24.977255 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.08.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7656, 24.979175 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.07.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7656, 24.979175 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.10.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765477, 24.986815 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.10.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76547, 24.98771 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.12.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765425, 24.989632 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.13.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765425, 24.989632 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.14.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765425, 24.989632 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.18.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764707, 24.990302 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.18.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764707, 24.990302 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.19.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76393, 24.99043 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.19.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76393, 24.99043 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.20.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76393, 24.99043 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.20.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.763575, 24.99045 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.21.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.763575, 24.99045 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.21.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.763575, 24.99045 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.21.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.763575, 24.99045 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.23.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76304, 24.99044 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.24.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76282, 24.990437 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.25.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.762337, 24.990455 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.25.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.761745, 24.99048 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.26.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.761227, 24.990485 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.27.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760647, 24.991267 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.27.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760647, 24.991267 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.29.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760647, 24.991267 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.30.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760752, 24.99354 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.31.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760832, 24.994435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.06.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76562, 24.977255 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.07.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765585, 24.977655 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.07.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765602, 24.978847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.08.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765617, 24.979325 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.09.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765582, 24.98067 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.09.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765522, 24.983032 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.10.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76549, 24.985935 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.11.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765435, 24.988837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.11.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765425, 24.989632 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.13.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765425, 24.989632 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.12.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765425, 24.989632 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.13.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765425, 24.989632 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.13.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765425, 24.989632 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.14.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765425, 24.989632 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.15.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765425, 24.989632 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.15.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765405, 24.990015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.19.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764377, 24.990377 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.19.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764125, 24.99041 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.23.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76304, 24.99044 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.24.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76238, 24.990455 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.24.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7626, 24.990445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.22.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.763095, 24.99044 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.26.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76125, 24.990485 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.27.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760657, 24.991077 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.28.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760647, 24.991267 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.29.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760647, 24.991267 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.28.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760647, 24.991267 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.28.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760647, 24.991267 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.25.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.761437, 24.99049 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.32.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760832, 24.994435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.34.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760832, 24.994435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.36.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760832, 24.994435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.38.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760872, 24.995062 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.39.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76098, 24.9968 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.31.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760832, 24.994435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.40.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76099, 25.000155 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.40.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760845, 25.000525 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.41.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.759745, 25.002372 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.41.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.758435, 25.00457 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.44.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74941, 25.009075 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.44.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.746712, 25.009675 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.45.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74623, 25.01036 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.46.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74623, 25.01036 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.46.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.744447, 25.012692 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.47.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743397, 25.01407 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.48.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742555, 25.015287 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.50.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.50.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.51.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.52.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.53.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.54.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.54.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.55.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.50.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743777, 24.95919 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.50.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74398, 24.95897 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.51.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74409, 24.958865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.51.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74409, 24.958865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.52.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74409, 24.958865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.52.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74409, 24.958865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.53.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74431, 24.95854 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-14.53.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74431, 24.95854 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.00.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76208, 24.970865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.03.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76481, 24.97274 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.05.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7654, 24.973235 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.14.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765425, 24.989632 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.14.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765425, 24.989632 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.15.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765425, 24.989632 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.15.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764905, 24.990292 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.16.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764707, 24.990302 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.17.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764707, 24.990302 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.17.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764707, 24.990302 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.17.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764707, 24.990302 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.20.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.763575, 24.99045 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.20.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.763575, 24.99045 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.22.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.763575, 24.99045 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.22.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.763575, 24.99045 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.23.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76304, 24.99044 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.24.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.762337, 24.990455 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.25.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.762337, 24.990455 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.26.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760725, 24.99057 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.29.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760665, 24.991507 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.30.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760702, 24.992665 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.30.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76073, 24.993225 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.31.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760832, 24.994435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.32.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760832, 24.994435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.33.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760832, 24.994435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.35.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760832, 24.994435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.35.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760832, 24.994435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.38.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760832, 24.994435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.38.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760832, 24.994435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.39.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.761077, 24.9983 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.40.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760247, 25.001535 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.43.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.75189, 25.009235 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.45.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74623, 25.01036 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.44.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74623, 25.01036 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.47.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743645, 25.013887 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.48.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741587, 25.014195 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.49.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.50.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.52.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.52.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.53.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.53.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.55.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.57.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.57.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.58.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.00.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.09.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765505, 24.984447 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.10.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765475, 24.98722 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.11.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765422, 24.989112 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.11.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765452, 24.98841 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.12.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765425, 24.989632 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.12.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765425, 24.989632 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.16.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764707, 24.990302 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.16.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764707, 24.990302 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.16.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764707, 24.990302 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.17.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764707, 24.990302 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.18.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764707, 24.990302 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.18.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764707, 24.990302 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.21.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.763575, 24.99045 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.22.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.763575, 24.99045 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.23.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76304, 24.99044 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.26.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.761227, 24.990485 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.28.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760647, 24.991267 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.27.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760647, 24.991267 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.29.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76065, 24.992017 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.30.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76081, 24.99369 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.32.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760832, 24.994435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.34.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760832, 24.994435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.35.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760832, 24.994435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.35.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760832, 24.994435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.36.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760832, 24.994435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.37.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760832, 24.994435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.37.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760832, 24.994435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.37.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760832, 24.994435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.37.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760832, 24.994435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.38.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76094, 24.99569 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.39.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.761105, 24.99964 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.41.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.759565, 25.002667 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.42.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.757225, 25.00647 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.42.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.757895, 25.005435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.43.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.753305, 25.00938 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.43.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.754155, 25.009037 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.43.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.751157, 25.00917 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.44.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.747442, 25.009092 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.45.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74623, 25.01036 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.46.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.745972, 25.010672 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.47.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74353, 25.01403 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.47.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742915, 25.01484 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.50.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.54.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.55.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.56.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.57.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.58.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.00.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.02.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740397, 25.01471 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.02.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73978, 25.01524 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.04.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74011, 25.016585 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.04.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74011, 25.016585 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.06.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74121, 25.017315 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.55.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.56.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.56.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.57.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.59.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.59.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.01.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.01.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.02.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74015, 25.014962 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.03.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.739572, 25.016222 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.03.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74006, 25.016545 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.04.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740212, 25.016685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.05.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74085, 25.016992 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.07.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741022, 25.017745 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.07.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74053, 25.0183 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.07.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740962, 25.01775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.09.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.739705, 25.019647 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.05.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74085, 25.016992 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.10.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.739705, 25.019647 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.10.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.739715, 25.019657 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.11.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7375, 25.02281 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.11.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.737195, 25.023827 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.13.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740995, 25.0251 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.14.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741345, 25.02495 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.15.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741217, 25.024977 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.15.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741217, 25.024977 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.16.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74143, 25.024897 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.16.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74143, 25.024897 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.17.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741105, 25.02492 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.18.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.739547, 25.02457 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.19.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735447, 25.02607 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.19.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735067, 25.026432 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.20.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735245, 25.026485 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.22.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735465, 25.026555 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.21.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735245, 25.026485 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.21.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735245, 25.026485 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.22.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735992, 25.026925 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.24.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.25.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.25.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.26.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.26.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.26.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.28.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.29.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.30.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.31.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.29.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.32.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.32.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.34.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.35.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.36.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.37.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.38.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.31.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760825, 24.99432 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.32.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760832, 24.994435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.33.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760832, 24.994435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.33.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760832, 24.994435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.33.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760832, 24.994435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.34.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760832, 24.994435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.34.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760832, 24.994435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.36.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760832, 24.994435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.36.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760832, 24.994435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.39.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.761155, 24.999297 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.40.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76105, 24.999925 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.41.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.75911, 25.003435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.42.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.75541, 25.00845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.42.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.756522, 25.007597 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.45.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74623, 25.01036 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.46.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74517, 25.01174 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.48.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742722, 25.015177 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.48.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741875, 25.01489 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.49.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74071, 25.013955 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.49.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740425, 25.01443 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.49.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.51.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.51.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.51.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.52.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.53.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.54.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.56.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.58.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.58.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.59.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-15.59.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.00.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.00.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740417, 25.014445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.01.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74045, 25.01467 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.01.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740397, 25.01471 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.03.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.739795, 25.01636 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.05.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7406, 25.016895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.05.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74085, 25.016992 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.06.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74085, 25.016992 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.07.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741022, 25.017745 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.08.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740202, 25.018735 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.08.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.739705, 25.019647 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.27.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.28.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.28.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.29.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.30.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.31.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.37.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.37.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.38.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73584, 25.026965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.39.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73584, 25.026965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.39.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73584, 25.026965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.02.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.739437, 25.01577 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.03.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73995, 25.01646 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.04.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74011, 25.016585 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.06.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74085, 25.016992 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.06.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741022, 25.017745 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.08.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.739982, 25.01915 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.08.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.739705, 25.019647 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.09.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.739705, 25.019647 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.10.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.739395, 25.020002 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.11.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.736812, 25.0235 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.12.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.738942, 25.02434 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.13.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740785, 25.02498 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.14.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741345, 25.02495 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.14.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741345, 25.02495 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.14.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741217, 25.024977 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.15.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74143, 25.024897 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.16.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74143, 25.024897 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.18.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.739005, 25.024355 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.18.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73849, 25.024282 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.18.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.738005, 25.025247 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.19.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.736685, 25.02679 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.20.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735245, 25.026485 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.20.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735245, 25.026485 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.22.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735987, 25.026835 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.24.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.24.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.25.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.25.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.26.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.27.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.27.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.27.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.28.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.29.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.30.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.30.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.31.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.32.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.33.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.33.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.34.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.35.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.35.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.36.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.36.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.37.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.34.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.40.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73584, 25.026965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.40.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73584, 25.026965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.42.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73584, 25.026965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.43.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73584, 25.026965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.45.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73584, 25.026965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.45.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73584, 25.026965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.46.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73584, 25.026965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.48.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.733865, 25.02804 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.09.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.739705, 25.019647 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.10.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.739705, 25.019647 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.11.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7386, 25.021405 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.09.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.739705, 25.019647 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.12.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.737997, 25.024052 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.12.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740135, 25.02474 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.12.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740785, 25.02498 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.13.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741245, 25.025007 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.13.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.741122, 25.02511 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.15.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74143, 25.024897 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.16.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74143, 25.024897 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.17.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74121, 25.024905 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.17.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740302, 25.024842 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.17.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740767, 25.02502 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.19.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.737355, 25.02617 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.21.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735245, 25.026485 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.21.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735245, 25.026485 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.20.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735245, 25.026485 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.23.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.22.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.23.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.23.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.23.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.24.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.31.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.32.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.33.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.33.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.34.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.35.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.36.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.38.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73584, 25.026965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.39.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73584, 25.026965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.39.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73584, 25.026965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.40.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73584, 25.026965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.41.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73584, 25.026965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.42.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73584, 25.026965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.43.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73584, 25.026965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.44.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73584, 25.026965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.45.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73584, 25.026965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.47.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735965, 25.02697 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.48.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73481, 25.02683 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.51.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735547, 25.032662 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.52.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742145, 25.02856 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.52.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74074, 25.030045 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.53.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74485, 25.02802 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.54.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.752515, 25.02202 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.55.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.766327, 25.012752 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.56.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7673, 25.01145 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.56.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.772607, 25.009885 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.57.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77685, 25.008592 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.58.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.780517, 25.007552 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.58.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.781845, 25.007142 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.59.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.782052, 25.006222 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.40.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73584, 25.026965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.41.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73584, 25.026965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.42.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73584, 25.026965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.43.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73584, 25.026965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.44.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73584, 25.026965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.44.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73584, 25.026965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.45.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73584, 25.026965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.46.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73584, 25.026965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.47.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735965, 25.02697 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.47.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735965, 25.02697 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.49.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.731587, 25.031117 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.46.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73584, 25.026965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.50.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.731935, 25.033057 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.52.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743095, 25.027932 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.54.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.754197, 25.020295 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.55.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.762097, 25.017945 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.55.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7645, 25.016215 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.56.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.769927, 25.010685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.58.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.782182, 25.006375 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.59.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.782255, 25.005922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.01.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.78217, 25.006592 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.02.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.779465, 25.00782 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.06.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.776172, 25.015155 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.07.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77842, 25.016195 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.08.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.778595, 25.016802 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.09.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.778137, 25.01601 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.09.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.777775, 25.015765 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.09.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.777662, 25.015685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.10.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.774655, 25.015905 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.11.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77359, 25.016895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.11.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.773747, 25.017592 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.12.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.773812, 25.018142 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.10.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.776117, 25.015255 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.12.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77416, 25.019917 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.13.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77561, 25.020837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.14.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77294, 25.03162 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.15.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.775985, 25.034597 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.15.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.774357, 25.034052 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.17.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.780795, 25.0384 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.16.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.780007, 25.038345 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.17.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.781845, 25.03842 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.19.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.806547, 25.038607 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.22.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.851742, 25.040817 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.24.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.86873, 25.051005 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.24.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.87514, 25.055367 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.25.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88498, 25.061662 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.26.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88859, 25.068552 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.29.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.923155, 25.09414 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.30.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.927807, 25.097627 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.30.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92785, 25.09577 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.31.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926195, 25.098735 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.32.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920865, 25.09453 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.33.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921255, 25.095317 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.33.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921457, 25.096327 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.38.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73586, 25.026967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.41.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73584, 25.026965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.41.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73584, 25.026965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.42.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73584, 25.026965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.43.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73584, 25.026965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.44.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73584, 25.026965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.46.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73584, 25.026965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.47.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735965, 25.02697 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.48.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735932, 25.026807 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.48.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.735252, 25.026497 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.49.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73088, 25.03196 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.49.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73306, 25.0293 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.49.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73221, 25.030297 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.50.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.730952, 25.0323 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.50.37.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.730992, 25.03235 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.51.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.732947, 25.033622 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.51.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.736825, 25.031995 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.54.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.75672, 25.019662 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.55.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76577, 25.014395 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.57.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.778237, 25.008215 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.59.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.782255, 25.005922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.59.32.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.782255, 25.005922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.00.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.78217, 25.006592 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.01.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.782272, 25.006962 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.01.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.781202, 25.007502 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.05.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77415, 25.01177 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.06.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77453, 25.012595 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.07.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77866, 25.016752 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.08.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77866, 25.016752 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.09.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77721, 25.015205 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.12.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.774327, 25.020915 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.14.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.773165, 25.02792 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.14.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.772595, 25.029985 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.16.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.779015, 25.035235 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.16.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.779085, 25.037087 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.17.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.784932, 25.03841 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.17.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.783395, 25.038412 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.21.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.823407, 25.03414 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.21.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.831265, 25.033482 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.23.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.85561, 25.042672 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.23.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.86585, 25.048637 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.24.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.878685, 25.05715 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.25.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88694, 25.064805 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.27.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.89216, 25.073142 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.28.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.90522, 25.076972 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.28.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.90826, 25.0787 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.29.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.915852, 25.086615 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.33.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92077, 25.09466 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.34.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.36.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.35.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.36.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.37.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.37.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.50.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73091, 25.03226 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.50.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.730952, 25.0323 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.51.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.733817, 25.033515 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.52.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73851, 25.031135 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.53.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.746837, 25.027525 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.53.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.749515, 25.026392 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.53.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.751677, 25.024375 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.54.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.75936, 25.019012 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.57.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77764, 25.008355 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.56.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.775215, 25.009145 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-16.59.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.782155, 25.005975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.00.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.78217, 25.006592 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.02.15.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.78108, 25.007525 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.02.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.78067, 25.007555 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.02.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77794, 25.00828 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.04.10.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.774042, 25.009695 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.04.10.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.774042, 25.009695 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.04.10.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.774042, 25.009695 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.06.22.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.774792, 25.01306 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.06.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77699, 25.015012 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.07.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.777622, 25.015635 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.08.49.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.778635, 25.016697 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.10.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.773775, 25.01637 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.13.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77532, 25.023777 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.15.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.778257, 25.034775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.18.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.78607, 25.038475 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.18.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.787695, 25.038515 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.19.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.795635, 25.039867 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.19.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.802987, 25.03909 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.20.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.812822, 25.034537 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.20.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.819625, 25.03372 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.22.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.84391, 25.03698 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.24.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.87173, 25.05341 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.23.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.862907, 25.046535 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.25.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.888307, 25.067215 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.26.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.888395, 25.06745 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.26.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88959, 25.070717 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.27.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.89893, 25.07537 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.27.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.902202, 25.075945 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.29.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920762, 25.092205 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.31.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.923935, 25.10012 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.31.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92258, 25.09945 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.32.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921315, 25.094927 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.34.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.35.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.34.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.36.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.37.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.38.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.39.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.39.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.39.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.40.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.43.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.00.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.78217, 25.006592 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.00.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.78217, 25.006592 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.01.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.78217, 25.006592 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.02.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.781142, 25.00752 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.03.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.776635, 25.00874 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.05.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77401, 25.011195 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.07.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77862, 25.016622 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.08.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77866, 25.016752 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.08.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77862, 25.01662 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.10.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.775032, 25.015617 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.11.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.773635, 25.017147 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.11.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77366, 25.017362 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.13.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.775547, 25.022095 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.13.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.776045, 25.021047 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.14.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.774542, 25.025915 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.15.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.773537, 25.032737 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.12.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.774837, 25.0209 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.16.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.779387, 25.038117 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.18.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.789967, 25.03854 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.18.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.79241, 25.03904 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.19.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.799337, 25.039582 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.20.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8099, 25.03713 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.20.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.816017, 25.033415 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.21.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.82704, 25.03397 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.21.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.835467, 25.033757 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.22.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.839755, 25.035 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.22.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.847935, 25.038935 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.23.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.859397, 25.04451 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.25.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88199, 25.05902 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.26.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.888395, 25.06745 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.27.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.89549, 25.07472 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.28.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913362, 25.083745 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.28.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.91092, 25.081025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.29.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.91837, 25.0895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.30.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.925855, 25.094465 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.30.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92671, 25.098392 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.32.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92157, 25.097302 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.32.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92077, 25.094655 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.31.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.925365, 25.099375 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.35.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.40.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.41.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.42.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.43.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.43.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.45.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.47.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.47.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.48.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.49.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.51.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.51.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.52.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.53.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.33.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920902, 25.096787 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.34.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.35.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.36.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.37.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.38.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.38.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.38.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.40.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.40.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.41.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.43.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.44.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.44.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.47.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.46.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.41.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.47.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.48.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.49.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.49.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.49.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.50.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.54.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.54.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.56.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.56.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.57.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.58.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.58.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.58.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.59.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.59.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.59.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.54.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.00.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.02.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.02.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.03.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.04.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.04.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.06.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.07.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.09.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.10.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.11.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.12.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.13.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.14.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.13.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.14.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.15.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.15.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.15.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.17.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.44.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.44.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.45.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.45.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.50.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.50.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.51.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.52.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.52.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.53.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.54.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.55.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.56.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.57.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.57.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.58.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.01.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.02.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.02.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.04.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.06.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.06.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.08.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.10.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.11.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.11.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.11.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.12.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.12.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.14.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.16.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.18.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.18.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.19.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.20.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.21.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.23.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.23.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.24.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.25.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.26.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.26.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.28.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.29.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.30.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.32.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.32.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.33.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.33.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.35.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.34.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.36.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.35.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.36.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.37.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.39.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.41.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.42.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.42.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.42.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.45.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.46.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.46.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.46.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.48.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.48.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.50.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.51.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.52.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.55.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.56.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.57.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.59.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.01.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.01.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.03.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.03.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.07.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.08.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.08.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.09.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.10.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.09.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.13.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.14.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.16.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.16.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.16.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.19.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.18.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.22.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.21.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.21.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.25.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.27.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.28.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.29.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.30.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.31.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.33.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.32.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.36.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.35.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.37.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.38.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.39.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.40.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.42.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920885, 25.096337 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.45.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92086, 25.095555 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.46.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920842, 25.095527 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.53.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.53.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.55.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-17.55.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.00.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.00.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.00.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.01.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.03.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.05.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.04.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.05.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.05.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.05.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.06.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.07.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.07.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.09.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.08.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.10.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.12.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.13.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.15.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.18.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.19.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.22.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.24.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.23.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.23.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.25.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.26.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.27.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.27.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.28.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.29.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.29.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.31.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.32.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.34.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.37.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.39.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.39.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.41.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.42.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921005, 25.096162 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.43.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921005, 25.095925 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.44.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921005, 25.095925 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.44.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921005, 25.095925 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.45.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920842, 25.095527 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.47.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920575, 25.09524 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.47.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920575, 25.09524 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.49.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920575, 25.09524 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.49.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920575, 25.09524 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.49.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920575, 25.09524 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.50.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920575, 25.09524 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.51.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920575, 25.09524 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.17.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.17.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.17.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.19.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.20.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.20.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.20.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.21.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.22.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.22.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.24.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.24.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.25.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.26.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.27.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.28.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.30.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.30.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.31.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.31.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.33.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.34.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.34.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.35.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.36.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.37.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.38.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.39.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.41.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.42.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921005, 25.096162 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.43.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921005, 25.095925 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.43.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921005, 25.095925 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.44.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921005, 25.095925 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.46.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920842, 25.095527 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.46.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920842, 25.095527 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.47.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920575, 25.09524 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.46.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920842, 25.095527 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.47.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920575, 25.09524 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.48.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920575, 25.09524 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.48.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920575, 25.09524 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.50.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920575, 25.09524 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.50.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920575, 25.09524 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.51.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920575, 25.09524 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.51.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920575, 25.09524 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.53.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92053, 25.09521 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.54.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92048, 25.095152 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.55.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92447, 25.094412 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.56.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.927912, 25.0962 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.57.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92645, 25.09848 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.59.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.925957, 25.098757 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.59.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.925957, 25.098757 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.00.18.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.925815, 25.099035 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.00.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92569, 25.09907 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.00.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.924495, 25.099682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.02.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.90897, 25.079375 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.38.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.38.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.40.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.40.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.40.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.41.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92085, 25.096825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.41.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92073, 25.09673 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.42.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921012, 25.095965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.43.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921005, 25.095925 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.44.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921005, 25.095925 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.45.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920842, 25.095527 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.45.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920842, 25.095527 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.49.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920575, 25.09524 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.53.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920575, 25.09524 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.54.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920685, 25.094705 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.55.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.923757, 25.094047 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.56.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926862, 25.09825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.56.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.927807, 25.097565 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.59.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.925845, 25.099085 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.00.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.925845, 25.099085 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.59.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.925845, 25.099085 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.01.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.922175, 25.096475 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.02.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.906165, 25.0775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.03.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.895785, 25.074875 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.04.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.887475, 25.067917 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.04.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.887475, 25.067917 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.09.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.85158, 25.040912 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.09.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.84471, 25.037602 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.09.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.84832, 25.039347 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.10.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.830825, 25.03363 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.11.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.812542, 25.034755 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.12.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.807177, 25.038565 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.12.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.809975, 25.037102 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.12.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.800875, 25.03944 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.13.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.79233, 25.03914 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.13.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.789375, 25.03861 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.15.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.773327, 25.03862 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.15.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764742, 25.03917 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.16.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.759045, 25.038857 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.17.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.75404, 25.041885 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.16.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.75501, 25.04008 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.20.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74405, 25.03209 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.21.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743022, 25.0279 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.22.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.755745, 25.019877 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.25.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76548, 25.00167 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.26.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76507, 24.998365 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.26.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764955, 24.99578 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.26.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76502, 24.994482 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.27.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76505, 24.99311 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.27.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76507, 24.992827 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.28.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765085, 24.99145 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.29.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765102, 24.98886 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.32.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76507, 24.98419 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.32.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76507, 24.98419 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.48.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920575, 25.09524 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.48.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920575, 25.09524 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.50.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920575, 25.09524 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.52.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920575, 25.09524 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.54.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92048, 25.095152 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.56.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92757, 25.095695 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.55.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926357, 25.094735 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.57.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926325, 25.098452 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.58.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926325, 25.098452 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.57.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926325, 25.098452 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.58.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.925957, 25.098757 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.01.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.916965, 25.088115 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.01.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92174, 25.093615 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.01.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.919445, 25.090905 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.03.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.899475, 25.075462 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.03.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.902957, 25.076192 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.06.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88202, 25.059115 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.06.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.876017, 25.05588 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.07.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.873132, 25.054395 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.07.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.868475, 25.051035 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.08.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.860445, 25.045257 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.08.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.85748, 25.04375 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.08.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.854585, 25.04236 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.10.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.834445, 25.03375 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.12.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.804085, 25.039015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.13.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.797617, 25.03987 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.13.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.794812, 25.039857 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.14.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.78606, 25.038597 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.15.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.770005, 25.038635 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.14.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77669, 25.038615 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.16.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.761845, 25.039305 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.16.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.756477, 25.038942 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.18.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74382, 25.04515 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.18.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.745745, 25.04476 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.17.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.747622, 25.044355 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.20.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.742107, 25.02912 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.21.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7506, 25.02567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.22.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.753217, 25.02089 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.23.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760835, 25.01855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.22.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.75839, 25.019257 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.24.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7665, 25.01231 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.24.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.766115, 25.007142 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.25.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76564, 25.003295 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.25.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76529, 24.9999 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.27.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76506, 24.992887 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.28.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765075, 24.992445 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.28.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765092, 24.99056 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.30.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76511, 24.98852 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.31.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76507, 24.984227 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.32.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76507, 24.98419 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.32.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76507, 24.98419 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.33.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76507, 24.98419 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.33.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765085, 24.983895 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.33.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765055, 24.98372 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.51.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920575, 25.09524 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.52.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920575, 25.09524 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.52.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920575, 25.09524 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.52.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920575, 25.09524 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.53.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920575, 25.09524 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.53.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920575, 25.09524 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.54.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92231, 25.093565 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.55.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92334, 25.093545 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.57.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926375, 25.098367 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.58.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926145, 25.098612 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-18.58.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.925957, 25.098757 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.00.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92274, 25.098935 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.02.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.91431, 25.085077 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.03.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.892225, 25.073365 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.04.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.889455, 25.070927 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.04.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.887922, 25.068742 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.05.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88746, 25.06776 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.06.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.884555, 25.061457 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.07.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.866215, 25.049167 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.10.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.826935, 25.034097 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.11.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.815647, 25.033565 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.14.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.78006, 25.03863 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.15.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76721, 25.038722 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.18.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74335, 25.041897 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.19.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743487, 25.040162 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.19.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74357, 25.03843 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.19.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743697, 25.036725 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.20.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74396, 25.0337 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.20.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743547, 25.030225 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.21.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.747745, 25.02718 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.22.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.752112, 25.023145 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.23.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.766072, 25.014012 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.23.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.763015, 25.0174 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.23.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765012, 25.0157 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.24.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76629, 25.00958 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.29.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765105, 24.989107 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.30.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76511, 24.986867 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.31.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765102, 24.985035 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.34.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765005, 24.981355 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.34.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76502, 24.982215 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.35.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76336, 24.9802 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.37.11.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.761125, 24.979882 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.37.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760797, 24.97974 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.37.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.759965, 24.979837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.40.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.756775, 24.976955 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.41.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.75768, 24.97588 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.42.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.757122, 24.97245 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.43.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.756562, 24.968365 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.45.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.757032, 24.96682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.45.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.757137, 24.967085 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.46.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.75935, 24.968725 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.47.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760895, 24.96983 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.48.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76475, 24.972497 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.49.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.768232, 24.97535 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.02.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.911685, 25.08206 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.05.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88746, 25.067702 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.05.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.887165, 25.06656 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.05.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88634, 25.06421 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.07.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.870675, 25.05279 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.08.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.863452, 25.047115 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.06.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.879042, 25.057397 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.09.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.841245, 25.03593 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.10.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.837875, 25.034515 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.11.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.819142, 25.033795 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.11.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.823117, 25.034325 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.14.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.783112, 25.03862 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.17.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.75206, 25.04328 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.17.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.749692, 25.04342 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.18.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74318, 25.04385 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.19.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743845, 25.035067 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.21.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.745085, 25.027925 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.24.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76638, 25.011082 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.25.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76595, 25.00502 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.26.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764895, 24.996652 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.27.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76506, 24.992887 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.28.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765097, 24.98954 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.29.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765102, 24.988875 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.29.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765102, 24.98886 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.30.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765115, 24.987785 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.31.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765075, 24.98461 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.31.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76507, 24.98419 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.33.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76509, 24.984 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.34.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764992, 24.980975 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.35.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764857, 24.980815 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.36.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.761232, 24.98013 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.38.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.759392, 24.979745 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.38.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.75833, 24.979035 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.39.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.757705, 24.978027 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.39.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.75694, 24.977597 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.40.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.756767, 24.977465 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.41.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.75734, 24.976325 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.44.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.757127, 24.967745 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.45.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.756945, 24.966862 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.45.24.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.757032, 24.96682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.43.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.757007, 24.967875 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.47.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7618, 24.970455 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.47.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7624, 24.970902 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.47.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76352, 24.97169 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.48.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764942, 24.97261 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.49.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.768267, 24.975385 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.50.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.769817, 24.97669 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.50.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.771245, 24.977865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.51.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.772277, 24.97881 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.52.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.769635, 24.983387 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.53.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7685, 24.98514 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.54.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.766235, 24.988785 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.54.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765415, 24.990237 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.30.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765105, 24.986015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.35.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764532, 24.980692 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.36.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76108, 24.98 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.36.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76108, 24.98 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.37.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76108, 24.98 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.37.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760922, 24.979775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.37.39.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760642, 24.979725 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.38.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.758097, 24.97891 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.39.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.757975, 24.978772 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.42.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.756645, 24.971347 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.41.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.757405, 24.974382 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.43.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.75551, 24.969535 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.42.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.757415, 24.973435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.44.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.757032, 24.96682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.44.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.757437, 24.967367 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.44.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7575, 24.9671 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.46.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.75771, 24.967522 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.46.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.759855, 24.969082 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.48.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764942, 24.97261 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.48.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765337, 24.972882 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.49.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.766005, 24.973475 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.51.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77205, 24.97947 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.52.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.770262, 24.982405 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.52.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.769077, 24.98427 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.53.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.767962, 24.98599 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.53.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76701, 24.98754 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.55.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765387, 24.994067 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.56.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765417, 24.994915 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.57.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.766137, 24.997857 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.58.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.59.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.58.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.00.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.59.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.00.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.00.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.01.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.00.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.03.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.03.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.04.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.05.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.06.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.06.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.07.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.05.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.07.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.08.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.09.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.11.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.11.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.12.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.12.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.15.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.34.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76503, 24.98314 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.35.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76221, 24.979785 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.36.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7617, 24.980275 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.38.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.758827, 24.979397 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.39.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.758267, 24.978415 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.40.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.75694, 24.977597 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.40.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.75694, 24.977597 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.41.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.75731, 24.975082 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.42.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.75595, 24.970232 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.43.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.75609, 24.968862 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.45.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.757032, 24.96682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.46.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.758477, 24.968075 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.49.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76697, 24.97437 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.52.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.770845, 24.98151 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.55.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7654, 24.993575 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.55.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765362, 24.992027 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.56.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76538, 24.994102 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.56.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765407, 24.997245 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.56.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765422, 24.996025 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.57.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765645, 24.997802 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.59.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.01.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.02.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.04.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.04.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.06.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.10.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.10.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.11.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.12.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.13.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.13.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.14.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.14.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.15.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.15.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.18.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.19.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.20.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.20.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.21.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.21.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.22.41.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.767137, 24.99722 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.22.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.767095, 24.996647 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.23.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76701, 24.99537 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.23.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765907, 24.994775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.24.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765907, 24.994775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.25.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764932, 24.990967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.26.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764902, 24.990132 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.27.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.763267, 24.987045 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.27.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76188, 24.986035 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.28.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76087, 24.985285 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.31.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.753487, 24.979702 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.31.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.75274, 24.979072 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.50.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.768267, 24.975385 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.50.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.768562, 24.975625 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.51.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77152, 24.980385 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.51.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.771207, 24.98094 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.53.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.767435, 24.986815 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.54.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765997, 24.98927 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.54.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765777, 24.989507 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.57.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.57.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.58.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.59.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.02.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.02.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.03.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.05.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.07.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.10.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.14.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.15.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.16.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.17.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.18.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.19.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.20.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.20.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.21.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.21.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.22.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76615, 24.99785 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.22.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.767137, 24.997245 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.24.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765907, 24.994775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.24.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764952, 24.994355 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.26.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76492, 24.990892 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.26.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76492, 24.990892 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.30.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.756425, 24.981905 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.30.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.75756, 24.982775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.30.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.754217, 24.98026 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.33.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.748085, 24.980082 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.33.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74722, 24.979295 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.34.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74781, 24.97967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.35.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.747262, 24.978775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.36.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.748835, 24.977305 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.37.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.751785, 24.97847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.38.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.75313, 24.979322 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.38.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.754855, 24.980635 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.38.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.753625, 24.979747 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.40.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760257, 24.984707 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.40.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7598, 24.98435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.40.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760262, 24.984725 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.41.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760262, 24.984725 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.42.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760657, 24.99068 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.43.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760747, 24.9924 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.43.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.761125, 24.994935 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.43.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.762405, 24.994882 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.44.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764365, 24.994795 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.55.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765387, 24.994067 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-19.58.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.01.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.01.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.02.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.03.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.04.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.05.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.06.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.07.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.08.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.08.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.08.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.09.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.09.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.10.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.11.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.09.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.12.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.13.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.14.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.16.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.17.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.17.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.13.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.17.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.18.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.19.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.22.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.766972, 24.997782 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.25.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76498, 24.99267 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.25.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76492, 24.990892 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.26.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76492, 24.990892 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.27.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76451, 24.98802 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.25.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76492, 24.990892 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.28.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76087, 24.985285 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.29.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760577, 24.985065 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.29.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.758622, 24.983622 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.32.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.751245, 24.978265 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.32.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.748987, 24.977285 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.29.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76087, 24.985285 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.33.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.747347, 24.978725 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.34.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.748085, 24.980082 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.35.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.747115, 24.979115 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.34.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.747525, 24.97955 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.36.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.748127, 24.97803 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.37.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.750507, 24.97786 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.39.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.757075, 24.982282 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.40.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760262, 24.984725 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.42.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760392, 24.986175 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.44.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764365, 24.994795 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.44.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.763855, 24.994767 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.45.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765357, 24.995155 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.45.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764447, 24.99484 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.45.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765382, 24.99828 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.16.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.16.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.18.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.19.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76614, 24.997855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.23.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76644, 24.994772 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.23.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765907, 24.994775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.24.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765615, 24.99476 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.27.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764885, 24.988855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.28.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76087, 24.985285 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.28.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76087, 24.985285 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.29.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.759825, 24.98456 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.30.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.75523, 24.98102 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.31.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.752055, 24.97867 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.31.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.752975, 24.979375 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.34.43.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74781, 24.97967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.37.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.75271, 24.97896 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.39.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.757702, 24.982752 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.41.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760262, 24.984725 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.41.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76037, 24.985017 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.41.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760262, 24.984725 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.43.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76082, 24.993832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.44.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764365, 24.994795 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.46.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7657, 25.002312 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.46.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765757, 25.00288 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.47.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.767535, 25.005762 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.42.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76049, 24.98763 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.48.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77147, 25.00735 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.49.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.773615, 25.01586 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.49.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77428, 25.018485 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.50.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.772627, 25.02941 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.52.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77844, 25.03475 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.54.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.786, 25.038455 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.55.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.800852, 25.039385 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.56.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.809567, 25.037372 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.57.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.827435, 25.033885 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.59.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.854425, 25.042137 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.01.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8767, 25.056115 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.02.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88705, 25.06515 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.02.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.888065, 25.067115 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.03.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88878, 25.069482 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.04.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.89333, 25.07386 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.04.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.899577, 25.075452 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.05.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.908832, 25.079137 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.06.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.917967, 25.089122 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.07.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92791, 25.09578 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.08.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.925435, 25.09925 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.09.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92304, 25.09983 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.09.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.924587, 25.09991 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.10.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920775, 25.09472 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.10.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921462, 25.09617 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.11.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92136, 25.096715 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.12.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.14.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.13.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.32.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.75012, 24.977747 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.32.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.748157, 24.977995 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.33.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.747845, 24.979845 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.34.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74781, 24.97967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.35.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.747262, 24.978775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.35.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.747262, 24.978775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.36.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.747262, 24.978775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.36.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74744, 24.978672 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.37.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74936, 24.977315 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.38.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.754272, 24.980162 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.39.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.756035, 24.981512 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.39.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.758637, 24.983487 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.42.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.760572, 24.989135 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.46.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765487, 25.000237 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.46.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765807, 25.003455 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.47.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7693, 25.006365 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.47.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.770605, 25.006787 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.48.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77252, 25.00879 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.48.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.773212, 25.01373 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.51.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.773562, 25.03277 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.51.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.776205, 25.034607 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.51.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77439, 25.034035 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.52.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.779085, 25.03704 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.53.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.779565, 25.038295 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.53.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.780437, 25.03836 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.54.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.787432, 25.038525 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.53.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.782337, 25.038415 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.54.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.789465, 25.038525 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.54.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.791932, 25.038897 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.56.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.811672, 25.0354 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.56.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.80685, 25.038542 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.57.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.817357, 25.03341 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.56.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.814255, 25.0338 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.57.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.824105, 25.03416 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.58.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.841712, 25.0359 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.59.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.851547, 25.040722 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.01.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.870385, 25.0524 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.00.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.867495, 25.04997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.02.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.885485, 25.062357 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.02.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.883102, 25.059805 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.03.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88819, 25.067447 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.04.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.890545, 25.071855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.04.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.89649, 25.074965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.06.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.913495, 25.083965 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.07.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.9221, 25.093587 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.07.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926937, 25.094892 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.10.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920805, 25.094562 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.09.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92159, 25.095717 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.10.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92121, 25.095232 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.12.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.12.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.13.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.13.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.15.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.16.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.47.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.766355, 25.004685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.49.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77484, 25.021012 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.48.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77284, 25.011175 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.50.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77449, 25.025995 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.50.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77305, 25.028162 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.50.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.772605, 25.030415 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.52.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.779015, 25.035682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.55.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.794767, 25.039752 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.55.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.79788, 25.039785 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.55.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.803835, 25.038982 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.57.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.820835, 25.03391 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.58.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.834642, 25.033575 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.58.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.83821, 25.03439 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.59.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.845102, 25.03756 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.59.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.848525, 25.03922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.00.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.864482, 25.047635 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.00.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.86113, 25.045492 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.01.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.880045, 25.05781 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.03.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8882, 25.067465 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.05.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.902987, 25.076125 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.06.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.91572, 25.086532 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.06.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.9203, 25.09175 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.07.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92452, 25.094395 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.08.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92799, 25.09738 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.08.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926757, 25.09832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.11.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.11.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.12.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.11.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.14.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.15.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.15.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.16.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.16.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.17.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.18.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.18.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.19.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.20.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.20.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.22.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.23.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.26.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.27.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.29.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.28.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.30.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.30.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.31.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.31.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.31.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.32.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.32.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.35.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.36.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.45.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76542, 24.996295 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.49.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.775265, 25.023655 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.51.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.772852, 25.031475 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.52.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.779342, 25.03795 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.53.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.78433, 25.03839 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-20.58.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.83102, 25.033457 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.00.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.857505, 25.043642 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.01.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.873335, 25.05438 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.03.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.888257, 25.06767 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.05.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.91127, 25.081427 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.05.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.906102, 25.077395 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.08.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.925877, 25.09894 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.09.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92168, 25.098065 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.13.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.14.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.15.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.16.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.17.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.21.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.21.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.22.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.23.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.24.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.24.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.24.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.25.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.25.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.27.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.28.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.29.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.29.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.32.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.33.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.34.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.35.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.34.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.35.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.36.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.37.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.38.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.42.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.42.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.43.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.43.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.43.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.43.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.44.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.46.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.47.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.48.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.50.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.52.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.54.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.54.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.54.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.14.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.17.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.17.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.18.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.19.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.19.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.20.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.19.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.21.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.22.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.21.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.22.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.23.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.25.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.25.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.26.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.26.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.26.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.27.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.28.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.28.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.29.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.30.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.32.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.33.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.33.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.36.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.38.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.38.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.38.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.39.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.40.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.40.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.40.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.41.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.42.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.42.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.45.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.45.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.46.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.47.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.48.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.49.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.49.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.49.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.51.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.52.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.52.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.52.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.57.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.57.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.58.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.58.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.00.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.59.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.18.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.20.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.24.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.23.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.27.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.30.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.31.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.34.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.33.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.34.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.35.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.36.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.37.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.40.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.39.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.41.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.41.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.44.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.44.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.46.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.45.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.48.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.50.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.51.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.53.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.53.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.54.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.55.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.55.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.58.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.59.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.01.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.00.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.01.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.02.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.03.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.03.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.06.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.08.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.08.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.09.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.09.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.10.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.11.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.11.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.12.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.12.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.12.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.13.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.14.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.15.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.16.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.16.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.17.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.17.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.37.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.37.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.39.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.39.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.41.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.44.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.45.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.46.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.47.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.47.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.48.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.49.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.50.06.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.50.21.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.51.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.51.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.53.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.53.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.56.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.57.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.58.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.59.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.02.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.01.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.06.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.05.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.11.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.12.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.13.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.14.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.15.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.16.34.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.20.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.20.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.22.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.23.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.24.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.25.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.25.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.26.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.28.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.28.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.29.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.30.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.31.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.31.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.32.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.32.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.33.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.34.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.37.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92109, 25.09678 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.37.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921015, 25.096355 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.38.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921015, 25.096355 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.39.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921055, 25.096227 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.39.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92099, 25.095855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.02.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.03.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.03.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.04.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.04.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.04.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.06.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.07.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.07.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.08.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.05.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.09.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.10.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.11.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.13.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.13.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.14.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.17.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.17.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.18.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.15.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.18.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.19.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.21.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.21.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.22.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.23.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.23.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.24.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.23.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.25.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.26.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.27.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.28.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.30.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.31.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.31.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.32.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.33.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.34.34.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.35.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.37.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921015, 25.096355 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.38.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921055, 25.096227 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.40.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92099, 25.095855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.41.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92099, 25.095855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.41.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92099, 25.095855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.43.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92075, 25.09554 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.43.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920515, 25.095237 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.44.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920335, 25.09502 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.45.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.923292, 25.09352 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.46.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.927492, 25.09559 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.47.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926975, 25.09813 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.48.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926975, 25.09813 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.48.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926975, 25.09813 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.49.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.9272, 25.098177 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.55.36.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.55.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.56.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.56.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.56.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.57.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-21.59.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.00.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.00.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.01.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.02.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.04.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.05.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.05.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.06.51.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.07.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.07.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.09.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.08.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.10.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.10.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.14.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.15.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.16.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.18.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.19.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.20.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.20.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.21.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.22.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.24.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.24.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.25.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.29.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.29.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.29.49.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.33.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.33.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.34.49.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.35.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.35.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.36.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.28.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.38.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921055, 25.096227 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.39.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921055, 25.096227 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.40.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92099, 25.095855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.42.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92075, 25.09554 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.42.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92075, 25.09554 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.43.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920515, 25.095237 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.45.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92251, 25.093452 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.45.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92361, 25.093885 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.46.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.924375, 25.094387 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.47.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92786, 25.09611 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.48.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926975, 25.09813 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.49.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.927192, 25.098195 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.18.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.19.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.19.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.21.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.22.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.26.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.26.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.27.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.27.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.27.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.30.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.30.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.32.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.34.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.36.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.35.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.36.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.36.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921167, 25.096847 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.37.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920995, 25.096482 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.38.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921055, 25.096227 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.39.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920997, 25.095865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.40.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92099, 25.095855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.41.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92099, 25.095855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.41.49.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92075, 25.09554 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.42.34.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92075, 25.09554 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.44.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920515, 25.095237 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.44.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920382, 25.095065 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.46.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926035, 25.094615 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.47.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.927862, 25.097437 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.49.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.9272, 25.098177 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.53.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926667, 25.098792 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.53.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.927167, 25.098925 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.53.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.927167, 25.098925 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.54.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.927025, 25.098905 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.55.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926165, 25.09853 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.55.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.925762, 25.098775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.56.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926212, 25.098922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.59.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92295, 25.098777 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.00.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926665, 25.099317 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.01.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.922662, 25.098825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.01.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.919305, 25.090797 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.02.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.909695, 25.08002 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.03.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.894275, 25.0744 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.04.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.887537, 25.067855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.04.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88864, 25.069762 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.05.49.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.882005, 25.059122 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.07.34.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.857155, 25.043597 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.09.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.82043, 25.034105 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.06.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.878345, 25.05706 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.11.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.808562, 25.03828 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.11.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.805665, 25.034682 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.13.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.805197, 25.015265 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.13.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.804452, 25.01862 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.13.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.80718, 25.01233 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.40.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92099, 25.095855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.42.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92075, 25.09554 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.43.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92075, 25.09554 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.44.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.920482, 25.094855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.45.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.921117, 25.09437 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.46.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.923775, 25.09406 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.47.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92741, 25.097945 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.49.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92684, 25.09805 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.48.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926975, 25.09813 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.50.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926735, 25.098187 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.50.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926642, 25.098207 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.51.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926615, 25.098357 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.51.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926515, 25.098345 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.51.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926722, 25.09837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.53.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926667, 25.098792 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.56.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926212, 25.098922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.57.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926712, 25.09908 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.57.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92621, 25.09902 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.58.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926465, 25.099565 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.59.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.923935, 25.098855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.00.27.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92655, 25.099295 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.01.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.922185, 25.096435 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.01.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92169, 25.09357 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.02.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.917037, 25.088165 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.02.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.91254, 25.083055 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.05.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.887305, 25.066825 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.06.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.874335, 25.055045 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.07.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.860872, 25.045515 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.08.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.849365, 25.039842 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.10.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.81217, 25.03556 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.12.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.805387, 25.02872 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.12.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.80473, 25.02218 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.14.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.812155, 25.00742 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.15.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.82163, 24.993605 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.18.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.82341, 24.967187 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.18.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.823535, 24.967425 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.19.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.82341, 24.967187 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.19.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.82341, 24.967187 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.20.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.82341, 24.967187 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.21.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.82172, 24.962827 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.21.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.817525, 24.959587 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.22.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.814832, 24.95874 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.23.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.80066, 24.95857 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.24.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.784287, 24.953815 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.24.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.78202, 24.952897 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.24.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.78009, 24.951887 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.25.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.777065, 24.950152 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.26.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77782, 24.947855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.26.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.778595, 24.9463 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.27.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.776797, 24.943022 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.29.28.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77716, 24.941842 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.28.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.777285, 24.94138 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.29.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77715, 24.941842 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.30.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.777295, 24.94135 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.50.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.9272, 25.098177 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.50.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926642, 25.098207 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.52.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926722, 25.09837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.52.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926785, 25.098695 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.54.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.927092, 25.098865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.54.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926625, 25.098672 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.55.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92632, 25.098922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.56.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926065, 25.09902 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.56.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926212, 25.098922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.54.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.9275, 25.098602 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.58.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92665, 25.099645 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.59.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92577, 25.09938 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.00.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.92585, 25.099192 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.00.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.924425, 25.099717 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.02.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.915145, 25.08599 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.03.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.906632, 25.07778 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.03.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.90283, 25.076157 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.03.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.89851, 25.075325 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.04.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.8875, 25.067707 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.05.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.88648, 25.06442 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.07.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.864342, 25.047762 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.07.49.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.853352, 25.041767 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.09.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.82852, 25.033857 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.09.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.82442, 25.034355 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.10.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.81695, 25.0336 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.10.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.81399, 25.0342 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.11.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.81068, 25.03689 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.11.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.806275, 25.037125 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.12.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.805672, 25.031852 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.14.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.815815, 25.002155 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.15.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.81964, 24.99657 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.16.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.829847, 24.982822 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.16.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.829032, 24.986225 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.16.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.827775, 24.97685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.17.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.82436, 24.968472 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.19.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.82341, 24.967187 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.20.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.82341, 24.967187 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.19.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.82341, 24.967187 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.20.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.82328, 24.966685 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.21.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.819687, 24.960832 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.22.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.80411, 24.958622 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.23.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.797437, 24.957792 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.24.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.78738, 24.954977 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.25.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.777065, 24.950152 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.26.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77697, 24.950095 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.28.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.776395, 24.94094 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.29.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77716, 24.941842 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.31.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.777385, 24.94091 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.32.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.777362, 24.937075 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.32.34.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7777, 24.935775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.33.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.774505, 24.933575 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.34.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.773087, 24.933495 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.35.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.772725, 24.934327 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.35.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7718, 24.93782 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.51.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926515, 25.098345 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.52.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926722, 25.09837 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.52.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926667, 25.098792 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.55.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.925862, 25.098802 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.57.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926712, 25.09917 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.57.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926287, 25.09914 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.58.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926465, 25.099565 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.58.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926175, 25.09944 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-22.59.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.924885, 25.099132 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.00.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.926715, 25.09953 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.04.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.890855, 25.07236 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.05.34.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.884655, 25.061592 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.06.34.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.870825, 25.052917 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.06.49.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.867607, 25.050345 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.08.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.84494, 25.03771 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.08.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.83655, 25.03416 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.08.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.84082, 25.035727 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.09.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.832425, 25.033612 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.10.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.812005, 25.035775 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.12.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.80506, 25.025487 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.17.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.826612, 24.974045 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.18.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.82341, 24.967187 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.21.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.822875, 24.965107 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.22.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.81145, 24.95855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.23.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.790535, 24.955935 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.25.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.778025, 24.950702 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.25.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.777065, 24.950152 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.27.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.778222, 24.94493 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.27.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.776395, 24.94094 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.27.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.776385, 24.941125 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.28.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.777342, 24.94078 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.29.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.777165, 24.941777 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.29.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77716, 24.941842 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.30.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.777212, 24.941525 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.31.49.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.776685, 24.93956 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.33.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77619, 24.93396 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.34.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.773087, 24.933495 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.35.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.771395, 24.939285 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.41.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76791, 24.95176 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.42.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.766847, 24.960257 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.43.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76668, 24.96244 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.43.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.766415, 24.965875 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.44.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76599, 24.97113 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.45.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765847, 24.972967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.45.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765847, 24.972967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.45.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765847, 24.972967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.46.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765847, 24.972967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.47.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765605, 24.97693 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.46.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765847, 24.972967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.47.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765807, 24.973887 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.48.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76557, 24.980382 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.48.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76559, 24.980167 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.49.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765537, 24.982505 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.50.34.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765197, 24.99567 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.31.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.776852, 24.940735 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.31.34.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.776625, 24.940615 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.32.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.777027, 24.938315 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.33.34.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77342, 24.93348 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.33.49.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.773087, 24.933495 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.34.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.773087, 24.933495 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.35.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77226, 24.935945 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.36.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.770437, 24.942755 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.36.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.769852, 24.945527 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.37.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.768807, 24.946205 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.38.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.763992, 24.945812 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.38.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764205, 24.947812 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.39.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765752, 24.949272 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.39.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765015, 24.948957 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.40.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76818, 24.948992 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.40.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.769235, 24.946772 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.41.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.767472, 24.953575 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.42.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.767255, 24.954922 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.42.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.767132, 24.956765 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.44.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765847, 24.972967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.45.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765847, 24.972967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.46.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765847, 24.972967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.47.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765697, 24.975327 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.47.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76558, 24.978545 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.49.49.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765325, 24.98828 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.50.04.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765282, 24.990335 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.52.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.766607, 25.01187 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.55.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74787, 25.027217 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.56.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.734745, 25.033127 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.57.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73338, 25.033885 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.57.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.733305, 25.03393 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.58.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.733305, 25.03393 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.58.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.733305, 25.03393 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.59.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.728905, 25.035552 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.37.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.769737, 24.94625 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.38.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764407, 24.946737 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.39.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.764555, 24.948547 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.40.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.768692, 24.947452 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.43.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.766275, 24.96752 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.44.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.766125, 24.969385 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.49.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76549, 24.984442 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.49.34.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76539, 24.986362 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.44.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765885, 24.972412 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.50.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76526, 24.99283 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.51.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765917, 25.0036 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.51.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76576, 25.001785 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.51.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765952, 25.0053 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.52.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.766472, 25.009805 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.53.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7631, 25.01744 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.54.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.755537, 25.020007 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.54.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.751932, 25.023425 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.56.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.740315, 25.030327 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.56.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.73859, 25.031165 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.59.19.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.732375, 25.03448 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.59.34.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.730762, 25.035015 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.51.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765522, 25.000282 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.52.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.766195, 25.00747 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.52.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.766187, 25.013887 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.53.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7607, 25.0187 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.53.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.758152, 25.019412 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.54.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.750552, 25.025752 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.55.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74203, 25.02953 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.56.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.736645, 25.032122 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.57.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.733305, 25.03393 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.59.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.733277, 25.03397 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.13.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.80988, 25.00992 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.14.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.813957, 25.004865 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.14.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.81768, 24.99943 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.15.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.826695, 24.988727 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.15.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.823997, 24.99086 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.16.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.828927, 24.979645 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.17.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.82549, 24.971325 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.17.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.82479, 24.969545 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.18.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.824037, 24.96787 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.20.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.82341, 24.967187 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.22.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.807735, 24.958585 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.23.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.794057, 24.956705 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.26.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.777105, 24.94927 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.28.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.776402, 24.940897 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.30.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.777142, 24.941855 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.30.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.77704, 24.941945 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.32.49.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.777815, 24.93448 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.34.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.773087, 24.933495 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.36.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.770927, 24.94097 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.36.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.769975, 24.94428 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.37.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.767535, 24.945245 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.37.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765405, 24.944915 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.38.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.763555, 24.94506 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.39.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76681, 24.94916 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.40.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.767657, 24.94918 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.41.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.768407, 24.949992 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.41.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76885, 24.94831 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.42.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.767005, 24.958412 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.43.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76652, 24.964455 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.46.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.765847, 24.972967 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.48.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76558, 24.979725 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.48.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76555, 24.981265 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.50.49.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.7653, 24.9982 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.53.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.76498, 25.015822 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.54.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.75308, 25.020997 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.55.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.74517, 25.028135 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.55.35.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.743455, 25.029137 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.57.20.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.733305, 25.03393 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.58.05.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.733305, 25.03393 ] } }, +{ "type": "Feature", "properties": { "time": "2016-12-14-23.58.50.000000" }, "geometry": { "type": "Point", "coordinates": [ 102.733305, 25.03393 ] } } +] +} diff --git a/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs b/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs index fb33add..969eee9 100644 --- a/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs +++ b/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs @@ -16,7 +16,7 @@ namespace Sandwych.MapMatchingKit.Examples.HelloWorldApp { class Program { - private static readonly string s_dataDir = System.IO.Path.GetFullPath(System.IO.Path.Combine(Directory.GetCurrentDirectory(), "..", "..", "data")); + private static readonly string s_dataDir = Path.GetFullPath(Path.Combine(Directory.GetCurrentDirectory(), "..", "..", "data")); static void Main(string[] args) { @@ -113,7 +113,7 @@ private static void OfflineMatch( private static IEnumerable ReadSamples() { - var json = File.ReadAllText(System.IO.Path.Combine(s_dataDir, @"samples.geojson")); + var json = File.ReadAllText(System.IO.Path.Combine(s_dataDir, @"samples.oneday.geojson")); var reader = new GeoJsonReader(); var fc = reader.Read(json); var timeFormat = "yyyy-MM-dd-HH.mm.ss"; diff --git a/src/Sandwych.MapMatchingKit/Markov/AbstractFilter.cs b/src/Sandwych.MapMatchingKit/Markov/AbstractFilter.cs index f73ad95..3eaac7b 100644 --- a/src/Sandwych.MapMatchingKit/Markov/AbstractFilter.cs +++ b/src/Sandwych.MapMatchingKit/Markov/AbstractFilter.cs @@ -17,7 +17,7 @@ namespace Sandwych.MapMatchingKit.Markov /// Sample inherits from {@link Sample}. public abstract class AbstractFilter : IFilter - where TCandidate : IStateCandidate + where TCandidate : class, IStateCandidate { public ILogger Logger { get; set; } = NullLogger.Instance; diff --git a/src/Sandwych.MapMatchingKit/Markov/AbstractStateCandidate.cs b/src/Sandwych.MapMatchingKit/Markov/AbstractStateCandidate.cs index b17406d..a80ef52 100644 --- a/src/Sandwych.MapMatchingKit/Markov/AbstractStateCandidate.cs +++ b/src/Sandwych.MapMatchingKit/Markov/AbstractStateCandidate.cs @@ -6,7 +6,7 @@ namespace Sandwych.MapMatchingKit.Markov { public abstract class AbstractStateCandidate : IStateCandidate - where TCandidate : IStateCandidate + where TCandidate : class, IStateCandidate { private TTransition _transition; @@ -38,13 +38,5 @@ public TTransition Transition } } - public virtual bool Equals(TCandidate other) - { - if (object.ReferenceEquals(this, other)) - { - return true; - } - return Predecessor.Equals(other.Predecessor) && Transition.Equals(other.Transition); - } } } diff --git a/src/Sandwych.MapMatchingKit/Markov/IFilter.cs b/src/Sandwych.MapMatchingKit/Markov/IFilter.cs index 7121a69..bf31cb6 100644 --- a/src/Sandwych.MapMatchingKit/Markov/IFilter.cs +++ b/src/Sandwych.MapMatchingKit/Markov/IFilter.cs @@ -5,7 +5,7 @@ namespace Sandwych.MapMatchingKit.Markov { public interface IFilter - where TCandidate : IStateCandidate + where TCandidate : class, IStateCandidate { ICollection Execute(IEnumerable predecessors, in TSample previous, in TSample sample); } diff --git a/src/Sandwych.MapMatchingKit/Markov/IStateCandidate.cs b/src/Sandwych.MapMatchingKit/Markov/IStateCandidate.cs index c27671d..2ed9cff 100644 --- a/src/Sandwych.MapMatchingKit/Markov/IStateCandidate.cs +++ b/src/Sandwych.MapMatchingKit/Markov/IStateCandidate.cs @@ -4,8 +4,8 @@ namespace Sandwych.MapMatchingKit.Markov { - public interface IStateCandidate : IEquatable - where TCandidate : IStateCandidate + public interface IStateCandidate + where TCandidate : class, IStateCandidate { double Seqprob { get; set; } double Filtprob { get; set; } diff --git a/src/Sandwych.MapMatchingKit/Matching/Matcher.cs b/src/Sandwych.MapMatchingKit/Matching/Matcher.cs index 5fb65f0..a15cbf9 100644 --- a/src/Sandwych.MapMatchingKit/Matching/Matcher.cs +++ b/src/Sandwych.MapMatchingKit/Matching/Matcher.cs @@ -21,7 +21,7 @@ namespace Sandwych.MapMatchingKit.Matching /// Transition inherits from {@link StateTransition}. /// Sample inherits from {@link Sample}. public class Matcher : AbstractFilter - where TCandidate : IStateCandidate + where TCandidate : class, IStateCandidate { private readonly RoadMap _map; private readonly IGraphRouter _router; diff --git a/src/Sandwych.MapMatchingKit/Matching/MatcherCandidate.cs b/src/Sandwych.MapMatchingKit/Matching/MatcherCandidate.cs index f47cf70..43a5f09 100644 --- a/src/Sandwych.MapMatchingKit/Matching/MatcherCandidate.cs +++ b/src/Sandwych.MapMatchingKit/Matching/MatcherCandidate.cs @@ -18,14 +18,5 @@ public MatcherCandidate(in MatcherSample sample, in RoadPoint point) : base(samp } public override int GetHashCode() => this.Point.GetHashCode(); - - public override bool Equals(MatcherCandidate other) - { - if (object.ReferenceEquals(this, other)) - { - return true; - } - return Point.Equals(other.Point) && Predecessor.Equals(other.Predecessor) && Transition.Equals(other.Transition); - } } } diff --git a/test/Sandwych.MapMatchingKit.Tests/Markov/FilterTest.cs b/test/Sandwych.MapMatchingKit.Tests/Markov/FilterTest.cs index 32bb8d9..ff80603 100644 --- a/test/Sandwych.MapMatchingKit.Tests/Markov/FilterTest.cs +++ b/test/Sandwych.MapMatchingKit.Tests/Markov/FilterTest.cs @@ -12,7 +12,7 @@ public struct MockStateTransition { } - private class MockElement : AbstractStateCandidate + private class MockElement : AbstractStateCandidate, IEquatable { public int Id { get; } @@ -27,7 +27,7 @@ public MockElement(int id, double filtprob, double seqprob) : this(default, id) this.Seqprob = seqprob; } - public override bool Equals(MockElement other) + public bool Equals(MockElement other) { return this.Id == other.Id; } From bf89fb5b74c45baa14fb3540beb2d1eec0f0d8a6 Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Mon, 5 Mar 2018 18:11:18 +0800 Subject: [PATCH 15/37] more test data --- .../RoutersBenchmark.cs | 11 ++++------- .../Program.cs | 14 +++++++++++--- .../Matching/Minset.cs | 2 +- .../Roads/RoadMapBuilder.cs | 2 +- .../Sandwych.MapMatchingKit.csproj | 4 ++++ .../Spatial/CartesianSpatialOperation.cs | 13 +++++-------- .../Topology/BadGraphException.cs | 10 ++++++++++ .../PrecomputedDijkstraRouter.cs | 14 ++++++++++++-- .../PrecomputedDijkstraTable.cs | 14 ++++++++++---- .../PrecomputedDijkstraTableGenerator.cs | 19 +++++++------------ .../Markov/KStateTest.cs | 4 ++-- .../Spatial/CartesianSpatialOperationTest.cs | 2 +- 12 files changed, 68 insertions(+), 41 deletions(-) create mode 100644 src/Sandwych.MapMatchingKit/Topology/BadGraphException.cs diff --git a/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/RoutersBenchmark.cs b/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/RoutersBenchmark.cs index b52a378..7a9dfaa 100644 --- a/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/RoutersBenchmark.cs +++ b/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/RoutersBenchmark.cs @@ -68,18 +68,16 @@ public void Setup() [Benchmark(Baseline = true)] public int NaiveDijkstraMatching() { - var candidates = this.DoMatching(_naiveDijkstraMatcher); - return candidates.Count(); + return this.DoMatching(_naiveDijkstraMatcher); } [Benchmark] public int PrecomputedDijkstraMatching() { - var candidates = this.DoMatching(_precomputedDijkstraMatcher); - return candidates.Count(); + return this.DoMatching(_precomputedDijkstraMatcher); } - private IEnumerable DoMatching(Matcher matcher) + private int DoMatching(Matcher matcher) { var kstate = new MatcherKState(); foreach (var sample in _samples) @@ -87,8 +85,7 @@ private IEnumerable DoMatching(Matcher ReadSamples() diff --git a/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs b/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs index 969eee9..ed257d7 100644 --- a/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs +++ b/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs @@ -11,6 +11,7 @@ using Sandwych.MapMatchingKit.Topology; using Sandwych.MapMatchingKit.Spatial; using GeoAPI.Geometries; +using Sandwych.MapMatchingKit.Topology.PrecomputedDijkstra; namespace Sandwych.MapMatchingKit.Examples.HelloWorldApp { @@ -28,10 +29,14 @@ static void Main(string[] args) var map = mapBuilder.AddRoads(roads).Build(); Console.WriteLine("The road map has been loaded"); + + //var router = new PrecomputedDijkstraRouter(map, Costs.TimePriorityCost, Costs.DistanceCost, 1000D); + var router = new DijkstraRouter(); + var matcher = new Matcher( - map, new DijkstraRouter(), Costs.TimePriorityCost, spatial); + map, router, Costs.TimePriorityCost, spatial); matcher.MaxDistance = 1000; // set maximum searching distance between two GPS points to 1000 meters. - matcher.MaxRadius = 200.0; // sets maximum radius for candidate selection to 200 meters + matcher.MaxRadius = 100.0; // sets maximum radius for candidate selection to 200 meters Console.WriteLine("Loading GPS samples..."); @@ -43,7 +48,7 @@ static void Main(string[] args) Console.WriteLine("Starting Online map-matching..."); - OnlineMatch(matcher, samples); + //OnlineMatch(matcher, samples); Console.WriteLine("All done!"); Console.ReadKey(); @@ -92,6 +97,7 @@ private static void OfflineMatch( Console.WriteLine("Results: [count={0}]", candidatesSequence.Count()); var csvLines = new List(); csvLines.Add("time,lng,lat,azimuth"); + int matchedCandidateCount = 0; foreach (var cand in candidatesSequence) { var roadId = cand.Point.Edge.RoadInfo.Id; // original road id @@ -103,7 +109,9 @@ private static void OfflineMatch( var geom = cand.Transition.Route.ToGeometry(); // path geometry(LineString) from last matching candidate //cand.Transition.Route.Edges // Road segments between two GPS position } + matchedCandidateCount++; } + Console.WriteLine("Matched Candidates: {0}, Rate: {1}%", matchedCandidateCount, matchedCandidateCount * 100 / samples.Count()); var csvFile = System.IO.Path.Combine(s_dataDir, "samples.output.csv"); Console.WriteLine("Writing output file: {0}", csvFile); diff --git a/src/Sandwych.MapMatchingKit/Matching/Minset.cs b/src/Sandwych.MapMatchingKit/Matching/Minset.cs index ee299ab..744e097 100644 --- a/src/Sandwych.MapMatchingKit/Matching/Minset.cs +++ b/src/Sandwych.MapMatchingKit/Matching/Minset.cs @@ -107,7 +107,7 @@ public static ICollection Minimize(IEnumerable candidates) map.Remove(id); } - return map.Values; + return new HashSet(map.Values); } } } diff --git a/src/Sandwych.MapMatchingKit/Roads/RoadMapBuilder.cs b/src/Sandwych.MapMatchingKit/Roads/RoadMapBuilder.cs index 7ecf0e0..5de1a94 100644 --- a/src/Sandwych.MapMatchingKit/Roads/RoadMapBuilder.cs +++ b/src/Sandwych.MapMatchingKit/Roads/RoadMapBuilder.cs @@ -35,7 +35,7 @@ public IRoadMapBuilder AddRoads(IEnumerable roads) public RoadMap Build() { - return new RoadMap(this.GetAllRoads()); + return new RoadMap(this.GetAllRoads(), _spatial); } private IEnumerable GetAllRoads() diff --git a/src/Sandwych.MapMatchingKit/Sandwych.MapMatchingKit.csproj b/src/Sandwych.MapMatchingKit/Sandwych.MapMatchingKit.csproj index 44b89c0..cd07a44 100644 --- a/src/Sandwych.MapMatchingKit/Sandwych.MapMatchingKit.csproj +++ b/src/Sandwych.MapMatchingKit/Sandwych.MapMatchingKit.csproj @@ -19,4 +19,8 @@ + + + + diff --git a/src/Sandwych.MapMatchingKit/Spatial/CartesianSpatialOperation.cs b/src/Sandwych.MapMatchingKit/Spatial/CartesianSpatialOperation.cs index de522a9..7f18f71 100644 --- a/src/Sandwych.MapMatchingKit/Spatial/CartesianSpatialOperation.cs +++ b/src/Sandwych.MapMatchingKit/Spatial/CartesianSpatialOperation.cs @@ -10,7 +10,6 @@ namespace Sandwych.MapMatchingKit.Spatial { -#if CARTESIAN_SPATIAL public sealed class CartesianSpatialOperation : ISpatialOperation { private const double TwoPi = Math.PI * 2; @@ -152,15 +151,13 @@ public Coordinate2D Interpolate(in Coordinate2D a, in Coordinate2D b, double f) public Envelope Envelope(in Coordinate2D c, double radius) { - //c 是圆心,radius 是外接正方形边长的一半 - var bottomLeft = (x: c.X - radius, y: c.Y - radius); - var topRight = (x: c.X + radius, y: c.Y + radius); - return new Envelope(bottomLeft.x, topRight.x, bottomLeft.y, topRight.y); + var minCorner = (X: c.X - radius, Y: c.Y - radius); + var maxCorner = (X: c.X + radius, Y: c.Y + radius); + return new Envelope(minCorner.X, maxCorner.X, minCorner.Y, maxCorner.Y); } - - + public Envelope Envelope(ILineString line) => + line.EnvelopeInternal; } -#endif } diff --git a/src/Sandwych.MapMatchingKit/Topology/BadGraphException.cs b/src/Sandwych.MapMatchingKit/Topology/BadGraphException.cs new file mode 100644 index 0000000..051afbb --- /dev/null +++ b/src/Sandwych.MapMatchingKit/Topology/BadGraphException.cs @@ -0,0 +1,10 @@ +using System; +using System.Collections.Generic; +using System.Text; + +namespace Sandwych.MapMatchingKit.Topology +{ + public class BadGraphException : Exception + { + } +} diff --git a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouter.cs b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouter.cs index 6c0fcd0..30ee105 100644 --- a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouter.cs +++ b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouter.cs @@ -86,14 +86,24 @@ private IEnumerable RouteInternal( IEnumerable GetPath() { yield return source.Edge; - foreach (var edge in _precomputedTable.GetPathByVertex(source.Edge.Target, target.Edge.Source)) + var foundPath = _precomputedTable.GetPathByVertex(source.Edge.Target, target.Edge.Source); + foreach (var edge in foundPath) { yield return edge; } yield return target.Edge; } - var edges = GetPath(); + IEnumerable edges = EmptyPath; + try + { + edges = GetPath(); + } + catch (BadGraphException) + { + yield break; + } + foreach (var edge in edges) { yield return edge; diff --git a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTable.cs b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTable.cs index 6541729..496826c 100644 --- a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTable.cs +++ b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTable.cs @@ -86,7 +86,7 @@ public IEnumerable GetPathByVertex(TVertex sourceVertex, TVertex targetVe { if (IsSameVertex(sourceVertex, targetVertex)) { - throw new InvalidOperationException(); + throw new ArgumentException(); } if (this.TryGetValue((sourceVertex, targetVertex), out var row)) @@ -97,9 +97,15 @@ public IEnumerable GetPathByVertex(TVertex sourceVertex, TVertex targetVe while (!currentStart.Equals(targetVertex)) { - row = this[(currentStart, targetVertex)]; - yield return row.SourceEdge; - currentStart = row.NextVertex; + if (this.TryGetValue((currentStart, targetVertex), out row)) + { + yield return row.SourceEdge; + currentStart = row.NextVertex; + } + else + { + throw new BadGraphException(); + } } } else diff --git a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTableGenerator.cs b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTableGenerator.cs index 3251112..b7794a4 100644 --- a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTableGenerator.cs +++ b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTableGenerator.cs @@ -1,4 +1,5 @@ using System; +using System.Linq; using System.Collections.Generic; using QuickGraph; @@ -14,23 +15,17 @@ public IEnumerable> ComputeRows( IVertexAndEdgeListGraph graph, Func cost, Func bound, double maxRadius) { - var dijkstra = new BoundedDijkstraShortestPathAlgorithm(graph, cost, bound, maxRadius); - - foreach (var rootVertex in graph.Vertices) - { - var rows = this.ComputeRowsSingleSource(graph, dijkstra, rootVertex); - foreach (var row in rows) - { - yield return row; - } - } + var pquery = graph.Vertices.AsParallel(); + var allRows = pquery.SelectMany(rootVertex => this.ComputeRowsSingleSource(graph, rootVertex, cost, bound, maxRadius)); + return allRows.ToList(); } private IEnumerable> ComputeRowsSingleSource( IVertexAndEdgeListGraph graph, - BoundedDijkstraShortestPathAlgorithm dijkstra, - TVertex sourceVertex) + TVertex sourceVertex, + Func cost, Func bound, double maxRadius) { + var dijkstra = new BoundedDijkstraShortestPathAlgorithm(graph, cost, bound, maxRadius); try { diff --git a/test/Sandwych.MapMatchingKit.Tests/Markov/KStateTest.cs b/test/Sandwych.MapMatchingKit.Tests/Markov/KStateTest.cs index 7eb8917..c8d56b1 100644 --- a/test/Sandwych.MapMatchingKit.Tests/Markov/KStateTest.cs +++ b/test/Sandwych.MapMatchingKit.Tests/Markov/KStateTest.cs @@ -13,7 +13,7 @@ public struct MockStateTransition { } - private class MockElem : AbstractStateCandidate + private class MockElem : AbstractStateCandidate, IEquatable { private readonly int _id; @@ -34,7 +34,7 @@ public MockElem(JSONObject json, MockFactory factory) */ public int Id => _id; - public override bool Equals(MockElem other) + public bool Equals(MockElem other) { return this.Id == other.Id; } diff --git a/test/Sandwych.MapMatchingKit.Tests/Spatial/CartesianSpatialOperationTest.cs b/test/Sandwych.MapMatchingKit.Tests/Spatial/CartesianSpatialOperationTest.cs index 1750acc..cc90b07 100644 --- a/test/Sandwych.MapMatchingKit.Tests/Spatial/CartesianSpatialOperationTest.cs +++ b/test/Sandwych.MapMatchingKit.Tests/Spatial/CartesianSpatialOperationTest.cs @@ -242,6 +242,6 @@ private double DistanceEpsg4326(Coordinate2D a, Coordinate2D b) } } - #endif + } From 8bed6d2e8cb28dd3390af54ff1bd5279cfd7dae9 Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Mon, 5 Mar 2018 18:12:27 +0800 Subject: [PATCH 16/37] add commit --- .../Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs | 1 + 1 file changed, 1 insertion(+) diff --git a/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs b/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs index ed257d7..f33a03a 100644 --- a/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs +++ b/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs @@ -48,6 +48,7 @@ static void Main(string[] args) Console.WriteLine("Starting Online map-matching..."); + //Uncomment below line to see how online-matching works //OnlineMatch(matcher, samples); Console.WriteLine("All done!"); From f70386a447a27049ffb8020567221334d1f4772e Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Mon, 5 Mar 2018 23:28:38 +0800 Subject: [PATCH 17/37] Add RBush --- Sandwych.MapMatchingKit.sln | 8 +- .../RoutersBenchmark.cs | 4 +- ...andwych.MapMatchingKit.BenchmarkApp.csproj | 2 +- .../Program.cs | 2 +- ...pMatchingKit.Examples.HelloWorldApp.csproj | 6 +- .../Matching/Matcher.cs | 7 +- src/Sandwych.MapMatchingKit/Roads/RoadMap.cs | 6 +- .../Sandwych.MapMatchingKit.csproj | 7 +- .../Spatial/Index/AbstractSpatialIndex.cs | 14 +- .../Spatial/Index/ISpatialIndex.cs | 9 +- .../Spatial/Index/IndexItemVisitor.cs | 2 +- .../Spatial/Index/RBush/Envelope.cs | 82 ++++++ .../Spatial/Index/RBush/ISpatialData.cs | 7 + .../Spatial/Index/RBush/ISpatialDatabase.cs | 13 + .../Spatial/Index/RBush/ISpatialIndex.cs | 10 + .../Spatial/Index/RBush/ProjectionComparer.cs | 117 +++++++++ .../Spatial/Index/RBush/RBush.Node.cs | 39 +++ .../Spatial/Index/RBush/RBush.Utilities.cs | 233 ++++++++++++++++++ .../Spatial/Index/RBush/RBush.cs | 117 +++++++++ .../Spatial/Index/RBush/RBushSpatialIndex.cs | 68 +++++ .../Spatial/Index/AbstractSpatialIndexTest.cs | 2 +- .../Spatial/Index/RBushIndexTest.cs | 16 ++ 22 files changed, 748 insertions(+), 23 deletions(-) create mode 100644 src/Sandwych.MapMatchingKit/Spatial/Index/RBush/Envelope.cs create mode 100644 src/Sandwych.MapMatchingKit/Spatial/Index/RBush/ISpatialData.cs create mode 100644 src/Sandwych.MapMatchingKit/Spatial/Index/RBush/ISpatialDatabase.cs create mode 100644 src/Sandwych.MapMatchingKit/Spatial/Index/RBush/ISpatialIndex.cs create mode 100644 src/Sandwych.MapMatchingKit/Spatial/Index/RBush/ProjectionComparer.cs create mode 100644 src/Sandwych.MapMatchingKit/Spatial/Index/RBush/RBush.Node.cs create mode 100644 src/Sandwych.MapMatchingKit/Spatial/Index/RBush/RBush.Utilities.cs create mode 100644 src/Sandwych.MapMatchingKit/Spatial/Index/RBush/RBush.cs create mode 100644 src/Sandwych.MapMatchingKit/Spatial/Index/RBush/RBushSpatialIndex.cs create mode 100644 test/Sandwych.MapMatchingKit.Tests/Spatial/Index/RBushIndexTest.cs diff --git a/Sandwych.MapMatchingKit.sln b/Sandwych.MapMatchingKit.sln index 8d0dc05..a711387 100644 --- a/Sandwych.MapMatchingKit.sln +++ b/Sandwych.MapMatchingKit.sln @@ -21,9 +21,12 @@ Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Source", "Source", "{CCB5D4 EndProject Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Benchmark", "Benchmark", "{CCEE7207-D1DA-4590-A89A-897FC90D3A87}" EndProject -Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Sandwych.MapMatchingKit.BenchmarkApp", "benchmark\Sandwych.MapMatchingKit.BenchmarkApp\Sandwych.MapMatchingKit.BenchmarkApp.csproj", "{7CB3D4C1-3386-4CAC-8FFA-004CD446EDA5}" +Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Sandwych.MapMatchingKit.BenchmarkApp", "benchmark\Sandwych.MapMatchingKit.BenchmarkApp\Sandwych.MapMatchingKit.BenchmarkApp.csproj", "{7CB3D4C1-3386-4CAC-8FFA-004CD446EDA5}" EndProject Global + GlobalSection(Performance) = preSolution + HasPerformanceSessions = true + EndGlobalSection GlobalSection(SolutionConfigurationPlatforms) = preSolution Debug|Any CPU = Debug|Any CPU Release|Any CPU = Release|Any CPU @@ -80,4 +83,7 @@ Global GlobalSection(Performance) = preSolution HasPerformanceSessions = true EndGlobalSection + GlobalSection(Performance) = preSolution + HasPerformanceSessions = true + EndGlobalSection EndGlobal diff --git a/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/RoutersBenchmark.cs b/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/RoutersBenchmark.cs index 7a9dfaa..b32ba3a 100644 --- a/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/RoutersBenchmark.cs +++ b/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/RoutersBenchmark.cs @@ -26,7 +26,7 @@ namespace Sandwych.MapMatchingKit.BenchmarkApp public class RoutersBenchmark { private const double MaxDistance = 1000D; - private const double MaxGpsRadius = 200D; + private const double MaxGpsRadius = 100D; private string DataDirPath { get; set; } private RoadMap _roadMap; @@ -55,7 +55,7 @@ public void Setup() } { - var precomputedDijkstraRouter = new PrecomputedDijkstraRouter(_roadMap, Costs.TimePriorityCost, Costs.DistanceCost, 1000D); + var precomputedDijkstraRouter = new PrecomputedDijkstraRouter(_roadMap, Costs.TimePriorityCost, Costs.DistanceCost, MaxDistance); _precomputedDijkstraMatcher = new Matcher( _roadMap, precomputedDijkstraRouter, Costs.TimePriorityCost, spatial); _precomputedDijkstraMatcher.MaxDistance = MaxDistance; // set maximum searching distance between two GPS points to 1000 meters. diff --git a/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/Sandwych.MapMatchingKit.BenchmarkApp.csproj b/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/Sandwych.MapMatchingKit.BenchmarkApp.csproj index 9ca048d..7750132 100644 --- a/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/Sandwych.MapMatchingKit.BenchmarkApp.csproj +++ b/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/Sandwych.MapMatchingKit.BenchmarkApp.csproj @@ -7,7 +7,7 @@ - + diff --git a/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs b/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs index f33a03a..90587a8 100644 --- a/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs +++ b/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs @@ -36,7 +36,7 @@ static void Main(string[] args) var matcher = new Matcher( map, router, Costs.TimePriorityCost, spatial); matcher.MaxDistance = 1000; // set maximum searching distance between two GPS points to 1000 meters. - matcher.MaxRadius = 100.0; // sets maximum radius for candidate selection to 200 meters + matcher.MaxRadius = 200.0; // sets maximum radius for candidate selection to 200 meters Console.WriteLine("Loading GPS samples..."); diff --git a/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Sandwych.MapMatchingKit.Examples.HelloWorldApp.csproj b/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Sandwych.MapMatchingKit.Examples.HelloWorldApp.csproj index a9e0232..c98dc84 100644 --- a/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Sandwych.MapMatchingKit.Examples.HelloWorldApp.csproj +++ b/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Sandwych.MapMatchingKit.Examples.HelloWorldApp.csproj @@ -5,12 +5,8 @@ netcoreapp2.0 - - AnyCPU - - - + diff --git a/src/Sandwych.MapMatchingKit/Matching/Matcher.cs b/src/Sandwych.MapMatchingKit/Matching/Matcher.cs index a15cbf9..127f2d9 100644 --- a/src/Sandwych.MapMatchingKit/Matching/Matcher.cs +++ b/src/Sandwych.MapMatchingKit/Matching/Matcher.cs @@ -84,11 +84,16 @@ public double Sigma /// public double MaxDistance { get; set; } = 15000.0; + ///

+ /// Gets or sets maximum number of candidates per state + /// + public int MaxCandidates { get; set; } = 8; + public override IReadOnlyCollection ComputeCandidates( IEnumerable predecessors, in MatcherSample sample) { - var points_ = this._map.Radius(sample.Coordinate, this.MaxRadius); + var points_ = this._map.Radius(sample.Coordinate, this.MaxRadius, this.MaxCandidates); var points = Minset.Minimize(points_); var dict = new Dictionary(points.Count); diff --git a/src/Sandwych.MapMatchingKit/Roads/RoadMap.cs b/src/Sandwych.MapMatchingKit/Roads/RoadMap.cs index a480ffb..5a7a1c0 100644 --- a/src/Sandwych.MapMatchingKit/Roads/RoadMap.cs +++ b/src/Sandwych.MapMatchingKit/Roads/RoadMap.cs @@ -31,7 +31,7 @@ public RoadMap(IEnumerable roads, ISpatialOperation spatial) : base(roads) // The original Barefoot is using Quad Tree for spatial indexing, however, in my experiment, NTS's STRtree is // much faster than NTS's Quadtree. - this.Index = new RtreeIndex(roads.Select(x => x.RoadInfo), spatial, r => r.Geometry, r => r.Length); + this.Index = new Spatial.Index.RBush.RBushSpatialIndex(roads.Select(x => x.RoadInfo), spatial, r => r.Geometry, r => r.Length); } public RoadMap(IEnumerable roads) : this(roads, GeographySpatialOperation.Instance) @@ -55,8 +55,8 @@ private IEnumerable Split(IEnumerable<(RoadInfo road, double fraction } } - public IEnumerable Radius(in Coordinate2D c, double r) => - this.Split(this.Index.Radius(c, r)); + public IEnumerable Radius(in Coordinate2D c, double r, int k = -1) => + this.Split(this.Index.Radius(c, r, k)); } } diff --git a/src/Sandwych.MapMatchingKit/Sandwych.MapMatchingKit.csproj b/src/Sandwych.MapMatchingKit/Sandwych.MapMatchingKit.csproj index cd07a44..5c66962 100644 --- a/src/Sandwych.MapMatchingKit/Sandwych.MapMatchingKit.csproj +++ b/src/Sandwych.MapMatchingKit/Sandwych.MapMatchingKit.csproj @@ -1,7 +1,7 @@ - netstandard1.6;netstandard2.0;net45;net461; + netstandard1.6;netstandard2.0;net451;net461; latest false @@ -9,13 +9,14 @@ - + + - + diff --git a/src/Sandwych.MapMatchingKit/Spatial/Index/AbstractSpatialIndex.cs b/src/Sandwych.MapMatchingKit/Spatial/Index/AbstractSpatialIndex.cs index c73370e..fdb7d15 100644 --- a/src/Sandwych.MapMatchingKit/Spatial/Index/AbstractSpatialIndex.cs +++ b/src/Sandwych.MapMatchingKit/Spatial/Index/AbstractSpatialIndex.cs @@ -1,5 +1,6 @@ using System; using System.Collections.Generic; +using System.Linq; using System.Text; using GeoAPI.Geometries; using NetTopologySuite.Index; @@ -14,7 +15,7 @@ public abstract class AbstractSpatialIndex : ISpatialIndex protected Func ItemGeometryGetter { get; } protected Func ItemLengthGetter { get; } - public AbstractSpatialIndex(IEnumerable items, ISpatialOperation spatialService, + public AbstractSpatialIndex(IEnumerable items, ISpatialOperation spatialService, Func geometryGetter, Func lengthGetter) { this.ItemGeometryGetter = geometryGetter; @@ -23,7 +24,7 @@ public AbstractSpatialIndex(IEnumerable items, ISpatialOperation spatialS this.AddRange(items); } - public IReadOnlyList<(TItem, double)> Radius(Coordinate2D c, double radius) + public IEnumerable<(TItem, double)> Radius(Coordinate2D c, double radius, int k = -1) { var neighbors = new List<(TItem, double)>(); var env = this.Spatial.Envelope(c, radius); @@ -43,7 +44,14 @@ public AbstractSpatialIndex(IEnumerable items, ISpatialOperation spatialS Index.Query(env, visitor); - return neighbors; + if (k > 0) + { + return neighbors.OrderBy(i => i.Item2).Take(k); + } + else + { + return neighbors; + } } protected void Add(TItem item) diff --git a/src/Sandwych.MapMatchingKit/Spatial/Index/ISpatialIndex.cs b/src/Sandwych.MapMatchingKit/Spatial/Index/ISpatialIndex.cs index 9d0a313..383d1b1 100644 --- a/src/Sandwych.MapMatchingKit/Spatial/Index/ISpatialIndex.cs +++ b/src/Sandwych.MapMatchingKit/Spatial/Index/ISpatialIndex.cs @@ -8,6 +8,13 @@ namespace Sandwych.MapMatchingKit.Spatial.Index { public interface ISpatialIndex { - IReadOnlyList<(TItem, double)> Radius(Coordinate2D c, double radius); + /// + /// Gets objects stored in the index that are within a certain radius or overlap a certain radius. + /// + /// Center point for radius search. + /// Radius in meters + /// maximum number of candidates + /// Result set of object(s) that are within a the given radius or overlap the radius, limited by k. + IEnumerable<(TItem, double)> Radius(Coordinate2D c, double radius, int k = -1); } } diff --git a/src/Sandwych.MapMatchingKit/Spatial/Index/IndexItemVisitor.cs b/src/Sandwych.MapMatchingKit/Spatial/Index/IndexItemVisitor.cs index ac1cb48..56d4973 100644 --- a/src/Sandwych.MapMatchingKit/Spatial/Index/IndexItemVisitor.cs +++ b/src/Sandwych.MapMatchingKit/Spatial/Index/IndexItemVisitor.cs @@ -5,7 +5,7 @@ namespace Sandwych.MapMatchingKit.Spatial.Index { - public readonly struct IndexItemVisitor : IItemVisitor + public sealed class IndexItemVisitor : IItemVisitor { public Action Action { get; } diff --git a/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/Envelope.cs b/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/Envelope.cs new file mode 100644 index 0000000..e3b871f --- /dev/null +++ b/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/Envelope.cs @@ -0,0 +1,82 @@ +using System; + +namespace RBush +{ + public readonly struct Envelope + { + public double MinX { get; } + public double MinY { get; } + public double MaxX { get; } + public double MaxY { get; } + + public double Area => Math.Max(this.MaxX - this.MinX, 0) * Math.Max(this.MaxY - this.MinY, 0); + public double Margin => Math.Max(this.MaxX - this.MinX, 0) + Math.Max(this.MaxY - this.MinY, 0); + + public Envelope(double minX, double minY, double maxX, double maxY) + { + this.MinX = minX; + this.MinY = minY; + this.MaxX = maxX; + this.MaxY = maxY; + } + + public Envelope Extend(in Envelope other) => + new Envelope( + Math.Min(this.MinX, other.MinX), + Math.Min(this.MinY, other.MinY), + Math.Max(this.MaxX, other.MaxX), + Math.Max(this.MaxY, other.MaxY)); + + public Envelope Clone() + { + return new Envelope(this.MinX, this.MinY, this.MaxX, this.MaxY); + } + + public Envelope Intersection(in Envelope other) => + new Envelope( + Math.Max(this.MinX, other.MinX), + Math.Max(this.MinY, other.MinY), + Math.Min(this.MaxX, other.MaxX), + Math.Min(this.MaxY, other.MaxY) + ); + + public Envelope Enlargement(in Envelope other) + { + var clone = this.Clone(); + clone.Extend(other); + return clone; + } + + public bool Contains(in Envelope other) + { + return + this.MinX <= other.MinX && + this.MinY <= other.MinY && + this.MaxX >= other.MaxX && + this.MaxY >= other.MaxY; + } + + public bool Intersects(in Envelope other) + { + return + this.MinX <= other.MaxX && + this.MinY <= other.MaxY && + this.MaxX >= other.MinX && + this.MaxY >= other.MinY; + } + + public static Envelope InfiniteBounds => + new Envelope( + double.NegativeInfinity, + double.NegativeInfinity, + double.PositiveInfinity, + double.PositiveInfinity); + + public static Envelope EmptyBounds => + new Envelope( + double.PositiveInfinity, + double.PositiveInfinity, + double.NegativeInfinity, + double.NegativeInfinity); + } +} \ No newline at end of file diff --git a/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/ISpatialData.cs b/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/ISpatialData.cs new file mode 100644 index 0000000..2a533cc --- /dev/null +++ b/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/ISpatialData.cs @@ -0,0 +1,7 @@ +namespace RBush +{ + public interface ISpatialData + { + ref readonly Envelope Envelope { get; } + } +} \ No newline at end of file diff --git a/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/ISpatialDatabase.cs b/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/ISpatialDatabase.cs new file mode 100644 index 0000000..5ed372b --- /dev/null +++ b/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/ISpatialDatabase.cs @@ -0,0 +1,13 @@ +using System.Collections.Generic; + +namespace RBush +{ + public interface ISpatialDatabase : ISpatialIndex + { + void Insert(T item); + void Delete(T item); + void Clear(); + + void BulkLoad(IEnumerable items); + } +} \ No newline at end of file diff --git a/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/ISpatialIndex.cs b/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/ISpatialIndex.cs new file mode 100644 index 0000000..6f1b69c --- /dev/null +++ b/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/ISpatialIndex.cs @@ -0,0 +1,10 @@ +using System.Collections.Generic; + +namespace RBush +{ + public interface ISpatialIndex + { + IEnumerable Search(); + IEnumerable Search(in Envelope boundingBox); + } +} \ No newline at end of file diff --git a/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/ProjectionComparer.cs b/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/ProjectionComparer.cs new file mode 100644 index 0000000..c42d652 --- /dev/null +++ b/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/ProjectionComparer.cs @@ -0,0 +1,117 @@ +using System; +using System.Collections.Generic; + +namespace RBush +{ + /// + /// Non-generic class to produce instances of the generic class, + /// optionally using type inference. + /// + public static class ProjectionComparer + { + /// + /// Creates an instance of ProjectionComparer using the specified projection. + /// + /// Type parameter for the elements to be compared + /// Type parameter for the keys to be compared, after being projected from the elements + /// Projection to use when determining the key of an element + /// A comparer which will compare elements by projecting each element to its key, and comparing keys + public static ProjectionComparer Create(Func projection) + { + return new ProjectionComparer(projection); + } + + /// + /// Creates an instance of ProjectionComparer using the specified projection. + /// The ignored parameter is solely present to aid type inference. + /// + /// Type parameter for the elements to be compared + /// Type parameter for the keys to be compared, after being projected from the elements + /// Value is ignored - type may be used by type inference + /// Projection to use when determining the key of an element + /// A comparer which will compare elements by projecting each element to its key, and comparing keys + public static ProjectionComparer Create + (TSource ignored, + Func projection) + { + return new ProjectionComparer(projection); + } + + } + + /// + /// Class generic in the source only to produce instances of the + /// doubly generic class, optionally using type inference. + /// + public static class ProjectionComparer + { + /// + /// Creates an instance of ProjectionComparer using the specified projection. + /// + /// Type parameter for the keys to be compared, after being projected from the elements + /// Projection to use when determining the key of an element + /// A comparer which will compare elements by projecting each element to its key, and comparing keys + public static ProjectionComparer Create(Func projection) + { + return new ProjectionComparer(projection); + } + } + + /// + /// Comparer which projects each element of the comparison to a key, and then compares + /// those keys using the specified (or default) comparer for the key type. + /// + /// Type of elements which this comparer will be asked to compare + /// Type of the key projected from the element + public class ProjectionComparer : IComparer + { + readonly Func projection; + readonly IComparer comparer; + + /// + /// Creates a new instance using the specified projection, which must not be null. + /// The default comparer for the projected type is used. + /// + /// Projection to use during comparisons + public ProjectionComparer(Func projection) + : this(projection, null) + { + } + + /// + /// Creates a new instance using the specified projection, which must not be null. + /// + /// Projection to use during comparisons + /// The comparer to use on the keys. May be null, in + /// which case the default comparer will be used. + public ProjectionComparer(Func projection, IComparer comparer) + { + this.comparer = comparer ?? Comparer.Default; + this.projection = projection; + } + + /// + /// Compares x and y by projecting them to keys and then comparing the keys. + /// Null values are not projected; they obey the + /// standard comparer contract such that two null values are equal; any null value is + /// less than any non-null value. + /// + public int Compare(TSource x, TSource y) + { + // Don't want to project from nullity + if (x == null && y == null) + { + return 0; + } + if (x == null) + { + return -1; + } + if (y == null) + { + return 1; + } + return comparer.Compare(projection(x), projection(y)); + } + } +} diff --git a/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/RBush.Node.cs b/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/RBush.Node.cs new file mode 100644 index 0000000..c443ede --- /dev/null +++ b/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/RBush.Node.cs @@ -0,0 +1,39 @@ +using System; +using System.Collections.Generic; +using System.Linq; + +namespace RBush +{ + public partial class RBush + { + internal class Node : ISpatialData + { + private Envelope _envelope; + + public Node(List items, int height) + { + this.Height = height; + this.Children = items; + ResetEnvelope(); + } + + public void Add(ISpatialData node) + { + Children.Add(node); + _envelope = Envelope.Extend(node.Envelope); + } + + public void ResetEnvelope() + { + _envelope = GetEnclosingEnvelope(Children); + } + + public List Children { get; } + public int Height { get; } + public bool IsLeaf => Height == 1; + public ref readonly Envelope Envelope => ref _envelope; + + + } + } +} \ No newline at end of file diff --git a/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/RBush.Utilities.cs b/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/RBush.Utilities.cs new file mode 100644 index 0000000..be5268f --- /dev/null +++ b/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/RBush.Utilities.cs @@ -0,0 +1,233 @@ +using System; +using System.Collections.Generic; +using System.Collections.Immutable; +using System.Linq; +using System.Text; + +namespace RBush +{ + public partial class RBush + { + #region Sort Functions + private static readonly IComparer CompareMinX = + ProjectionComparer.Create(d => d.Envelope.MinX); + private static readonly IComparer CompareMinY = + ProjectionComparer.Create(d => d.Envelope.MinY); + #endregion + + #region Search + private static readonly IReadOnlyList> EmptyIntersections = new IImmutableStack[] { }; + + private IReadOnlyList> DoSearch(in Envelope boundingBox) + { + var node = this.root; + if (!node.Envelope.Intersects(boundingBox)) + { + return EmptyIntersections; + } + + var intersections = new List>(); + var queue = new Queue>(); + queue.Enqueue(ImmutableStack.Empty.Push(node)); + + do + { + var current = queue.Dequeue(); + foreach (var c in (current.Peek() as Node).Children) + { + if (c.Envelope.Intersects(boundingBox)) + { + if (c is T) + { + intersections.Add(current.Push(c)); + } + else + { + queue.Enqueue(current.Push(c)); + } + } + } + } while (queue.Count != 0); + + return intersections; + } + #endregion + + #region Insert + private IReadOnlyList FindCoveringArea(in Envelope area, int depth) + { + var path = new List(); + var node = this.root; + var area_ = area; //FIX CS1628 + while (true) + { + path.Add(node); + if (node.IsLeaf || path.Count == depth) return path; + + node = node.Children + .Select(c => new { EnlargedArea = c.Envelope.Enlargement(area_).Area, c.Envelope.Area, Node = c as Node, }) + .OrderBy(x => x.EnlargedArea) + .ThenBy(x => x.Area) + .Select(x => x.Node) + .First(); + } + } + + private void Insert(ISpatialData data, int depth) + { + var envelope = data.Envelope; + var path = FindCoveringArea(envelope, depth); + + var insertNode = path.Last(); + insertNode.Add(data); + + while (--depth >= 0 && + path[depth].Children.Count > maxEntries) + { + var newNode = SplitNode(path[depth]); + if (depth == 0) + SplitRoot(newNode); + else + path[depth - 1].Add(newNode); + } + } + + #region SplitNode + private void SplitRoot(Node newNode) => + this.root = new Node(new List { this.root, newNode }, this.root.Height + 1); + + private Node SplitNode(Node node) + { + SortChildren(node); + + var splitPoint = GetBestSplitIndex(node.Children); + var newChildren = node.Children.Skip(splitPoint).ToList(); + node.Children.RemoveRange(splitPoint, node.Children.Count - splitPoint); + return new Node(newChildren, node.Height); + } + + #region SortChildren + private void SortChildren(Node node) + { + node.Children.Sort(CompareMinX); + var splitsByX = GetPotentialSplitMargins(node.Children); + node.Children.Sort(CompareMinY); + var splitsByY = GetPotentialSplitMargins(node.Children); + + if (splitsByX < splitsByY) + node.Children.Sort(CompareMinX); + } + + private double GetPotentialSplitMargins(List children) => + GetPotentialEnclosingMargins(children) + + GetPotentialEnclosingMargins(children.AsEnumerable().Reverse().ToList()); + + private double GetPotentialEnclosingMargins(List children) + { + var envelope = Envelope.EmptyBounds; + int i = 0; + for (; i < minEntries; i++) + { + envelope = envelope.Extend(children[i].Envelope); + } + + var totalMargin = envelope.Margin; + for (; i < children.Count - minEntries; i++) + { + envelope = envelope.Extend(children[i].Envelope); + totalMargin += envelope.Margin; + } + + return totalMargin; + } + #endregion + + private int GetBestSplitIndex(IEnumerable children) + { + return Enumerable.Range(minEntries, children.Count() - minEntries) + .Select(i => + { + var leftEnvelope = GetEnclosingEnvelope(children.Take(i)); + var rightEnvelope = GetEnclosingEnvelope(children.Skip(i)); + + var overlap = leftEnvelope.Intersection(rightEnvelope).Area; + var totalArea = leftEnvelope.Area + rightEnvelope.Area; + return new { i, overlap, totalArea }; + }) + .OrderBy(x => x.overlap) + .ThenBy(x => x.totalArea) + .Select(x => x.i) + .First(); + } + #endregion + #endregion + + #region BuildTree + private Node BuildTree(List data) + { + var treeHeight = GetDepth(data.Count); + var rootMaxEntries = (int)Math.Ceiling(data.Count / Math.Pow(this.maxEntries, treeHeight - 1)); + return BuildNodes(data, 0, data.Count - 1, treeHeight, rootMaxEntries); + } + + private int GetDepth(int numNodes) => + (int)Math.Ceiling(Math.Log(numNodes) / Math.Log(this.maxEntries)); + + private Node BuildNodes(List data, int left, int right, int height, int maxEntries) + { + var num = right - left + 1; + if (num <= maxEntries) + { + if (height == 1) + return new Node(data.Skip(left).Take(num).ToList(), height); + else + return new Node(new List { BuildNodes(data, left, right, height - 1, this.maxEntries) }, height); + } + + data.Sort(left, num, CompareMinX); + + var nodeSize = (num + (maxEntries - 1)) / maxEntries; + var subSortLength = nodeSize * (int)Math.Ceiling(Math.Sqrt(maxEntries)); + + var children = new List(maxEntries); + for (int subCounter = left; subCounter <= right; subCounter += subSortLength) + { + var subRight = Math.Min(subCounter + subSortLength - 1, right); + data.Sort(subCounter, subRight - subCounter + 1, CompareMinY); + + for (int nodeCounter = subCounter; nodeCounter <= subRight; nodeCounter += nodeSize) + { + children.Add( + BuildNodes( + data, + nodeCounter, + Math.Min(nodeCounter + nodeSize - 1, subRight), + height - 1, + this.maxEntries)); + } + } + + return new Node(children, height); + } + #endregion + + private static Envelope GetEnclosingEnvelope(IEnumerable items) + { + var envelope = Envelope.EmptyBounds; + foreach (var data in items) + { + envelope = envelope.Extend(data.Envelope); + } + return envelope; + } + + private IEnumerable GetAllChildren(Node n) + { + if (n.IsLeaf) + return n.Children.Cast(); + else + return n.Children.Cast().SelectMany(c => GetAllChildren(c)); + } + + } +} diff --git a/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/RBush.cs b/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/RBush.cs new file mode 100644 index 0000000..bebc0f1 --- /dev/null +++ b/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/RBush.cs @@ -0,0 +1,117 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; + +namespace RBush +{ + public partial class RBush : ISpatialDatabase, ISpatialIndex + where T : ISpatialData + { + private const int DefaultMaxEntries = 9; + private const int MinimumMaxEntries = 4; + private const int MinimumMinEntries = 2; + private const double DefaultFillFactor = 0.4; + + private readonly int maxEntries; + private readonly int minEntries; + internal Node root; + + public RBush() : this(DefaultMaxEntries) { } + public RBush(int maxEntries) + : this(maxEntries, EqualityComparer.Default) { } + public RBush(int maxEntries, EqualityComparer comparer) + { + this.maxEntries = Math.Max(MinimumMaxEntries, maxEntries); + this.minEntries = Math.Max(MinimumMinEntries, (int)Math.Ceiling(this.maxEntries * DefaultFillFactor)); + + this.Clear(); + } + + public int Count { get; private set; } + + public void Clear() + { + this.root = new Node(new List(), 1); + this.Count = 0; + } + + public IEnumerable Search() => GetAllChildren(this.root); + + public IEnumerable Search(in Envelope boundingBox) + { + return DoSearch(boundingBox).Select(x => (T)x.Peek()); + } + + public void Insert(T item) + { + Insert(item, this.root.Height); + this.Count++; + } + + public void BulkLoad(IEnumerable items) + { + var data = items.Cast().ToList(); + if (data.Count == 0) return; + + if (this.root.IsLeaf && + this.root.Children.Count + data.Count < maxEntries) + { + foreach (var i in data) + Insert((T)i); + return; + } + + if (data.Count < this.minEntries) + { + foreach (var i in data) + Insert((T)i); + return; + } + + var dataRoot = BuildTree(data); + this.Count += data.Count; + + if (this.root.Children.Count == 0) + this.root = dataRoot; + else if (this.root.Height == dataRoot.Height) + { + if (this.root.Children.Count + dataRoot.Children.Count <= this.maxEntries) + { + foreach (var isd in dataRoot.Children) + this.root.Add(dataRoot); + } + else + SplitRoot(dataRoot); + } + else + { + if (this.root.Height < dataRoot.Height) + { + var tmp = this.root; + this.root = dataRoot; + dataRoot = tmp; + } + + this.Insert(dataRoot, this.root.Height - dataRoot.Height); + } + } + + public void Delete(T item) + { + var candidates = DoSearch(item.Envelope); + + foreach (var c in candidates + .Where(c => object.Equals(item, c.Peek()))) + { + var path = c.Pop(); + (path.Peek() as Node).Children.Remove(item); + while (!path.IsEmpty) + { + (path.Peek() as Node).ResetEnvelope(); + path = path.Pop(); + } + } + } + } +} diff --git a/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/RBushSpatialIndex.cs b/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/RBushSpatialIndex.cs new file mode 100644 index 0000000..d2e5638 --- /dev/null +++ b/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/RBushSpatialIndex.cs @@ -0,0 +1,68 @@ +using System; +using System.Collections.Generic; +using System.Text; +using GeoAPI.Geometries; +using NetTopologySuite.Index; + +namespace Sandwych.MapMatchingKit.Spatial.Index.RBush +{ + public class RBushSpatialIndex : AbstractSpatialIndex + { + private sealed class NtsSpatialIndex : NetTopologySuite.Index.ISpatialIndex + { + private readonly global::RBush.RBush _backend = new global::RBush.RBush(); + + public void Insert(Envelope itemEnv, TItem item) + { + var env = new global::RBush.Envelope(itemEnv.MinX, itemEnv.MinY, itemEnv.MaxX, itemEnv.MaxY); + _backend.Insert(new RBushIndexItem(item, env)); + } + + public IList Query(Envelope searchEnv) + { + throw new NotSupportedException(); + } + + public void Query(Envelope searchEnv, IItemVisitor visitor) + { + var env = new global::RBush.Envelope(searchEnv.MinX, searchEnv.MinY, searchEnv.MaxX, searchEnv.MaxY); + var items = _backend.Search(env); + foreach (var i in items) + { + visitor.VisitItem(i.Item); + } + } + + public bool Remove(Envelope itemEnv, TItem item) + { + throw new NotSupportedException(); + } + } + + private class RBushIndexItem : global::RBush.ISpatialData + { + private global::RBush.Envelope _envelope; + + public RBushIndexItem(TItem item, in global::RBush.Envelope envelope) + { + this.Item = item; + this._envelope = envelope; + } + + public TItem Item { get; } + + public ref readonly global::RBush.Envelope Envelope => ref _envelope; + } + + private readonly NetTopologySuite.Index.ISpatialIndex _index = new NtsSpatialIndex(); + protected override NetTopologySuite.Index.ISpatialIndex Index => _index; + + public RBushSpatialIndex( + IEnumerable items, ISpatialOperation spatialService, + Func geometryGetter, Func lengthGetter) + : base(items, spatialService, geometryGetter, lengthGetter) + { + } + + } +} diff --git a/test/Sandwych.MapMatchingKit.Tests/Spatial/Index/AbstractSpatialIndexTest.cs b/test/Sandwych.MapMatchingKit.Tests/Spatial/Index/AbstractSpatialIndexTest.cs index 750a8a7..c2c15d6 100644 --- a/test/Sandwych.MapMatchingKit.Tests/Spatial/Index/AbstractSpatialIndexTest.cs +++ b/test/Sandwych.MapMatchingKit.Tests/Spatial/Index/AbstractSpatialIndexTest.cs @@ -86,7 +86,7 @@ private void AssertIndexRadius(Coordinate2D c, double r, int expectedNeighborsCo var points = index.Radius(c, r); - Assert.Equal(neighbors.Count, points.Count); + Assert.Equal(neighbors.Count, points.Count()); foreach (var pointId in points.Select(p => (int)p.Item1.UserData)) { Assert.Contains(pointId, neighbors); diff --git a/test/Sandwych.MapMatchingKit.Tests/Spatial/Index/RBushIndexTest.cs b/test/Sandwych.MapMatchingKit.Tests/Spatial/Index/RBushIndexTest.cs new file mode 100644 index 0000000..33e3b7f --- /dev/null +++ b/test/Sandwych.MapMatchingKit.Tests/Spatial/Index/RBushIndexTest.cs @@ -0,0 +1,16 @@ +using System; +using System.Collections.Generic; +using System.Text; +using GeoAPI.Geometries; +using Sandwych.MapMatchingKit.Spatial; +using Sandwych.MapMatchingKit.Spatial.Index; +using Sandwych.MapMatchingKit.Spatial.Index.RBush; + +namespace Sandwych.MapMatchingKit.Tests.Spatial.Index +{ + public class RBushIndexTest : AbstractSpatialIndexTest + { + protected override ISpatialIndex CreateSpatialIndex() => + new RBushSpatialIndex(this.Geometries, this.Spatial, x => x, x => this.Spatial.Length(x)); + } +} From 6ee2d685aae1abf939a2ef9c51dfc6170238f11b Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Tue, 6 Mar 2018 14:55:41 +0800 Subject: [PATCH 18/37] switch to rtree index --- ...andwych.MapMatchingKit.BenchmarkApp.csproj | 2 +- .../Program.cs | 3 +- ...pMatchingKit.Examples.HelloWorldApp.csproj | 2 +- .../Matching/Minset.cs | 2 +- src/Sandwych.MapMatchingKit/Roads/RoadMap.cs | 7 +- .../Sandwych.MapMatchingKit.csproj | 2 +- .../Spatial/CartesianSpatialOperation.cs | 17 +- .../Spatial/GeographySpatialOperation.cs | 22 +- .../Geometries/GeoAPILineStringExtensions.cs | 7 +- .../Geometries/NtsCoordinateExtensions.cs | 12 + .../Spatial/Index/AbstractNtsSpatialIndex.cs | 44 ++++ .../Spatial/Index/AbstractSpatialIndex.cs | 37 +--- .../Spatial/Index/ISpatialIndex.cs | 4 +- ...xItemVisitor.cs => NtsIndexItemVisitor.cs} | 4 +- .../Spatial/Index/QuadtreeIndex.cs | 2 +- .../Spatial/Index/RBush/ProjectionComparer.cs | 208 +++++++++--------- .../Spatial/Index/RBush/RBush.Node.cs | 2 +- .../Spatial/Index/RBush/RBushSpatialIndex.cs | 61 +++-- .../Spatial/Index/RtreeIndex.cs | 2 +- .../Projection/ICoordinateTransformation.cs | 2 +- .../Spatial/GeographySpatialOperationTest.cs | 4 +- 21 files changed, 241 insertions(+), 205 deletions(-) create mode 100644 src/Sandwych.MapMatchingKit/Spatial/Geometries/NtsCoordinateExtensions.cs create mode 100644 src/Sandwych.MapMatchingKit/Spatial/Index/AbstractNtsSpatialIndex.cs rename src/Sandwych.MapMatchingKit/Spatial/Index/{IndexItemVisitor.cs => NtsIndexItemVisitor.cs} (74%) diff --git a/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/Sandwych.MapMatchingKit.BenchmarkApp.csproj b/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/Sandwych.MapMatchingKit.BenchmarkApp.csproj index 7750132..fd1b1e6 100644 --- a/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/Sandwych.MapMatchingKit.BenchmarkApp.csproj +++ b/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/Sandwych.MapMatchingKit.BenchmarkApp.csproj @@ -7,7 +7,7 @@ - + diff --git a/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs b/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs index 90587a8..ed7fab2 100644 --- a/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs +++ b/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs @@ -17,7 +17,8 @@ namespace Sandwych.MapMatchingKit.Examples.HelloWorldApp { class Program { - private static readonly string s_dataDir = Path.GetFullPath(Path.Combine(Directory.GetCurrentDirectory(), "..", "..", "data")); + private static readonly string s_dataDir = + Path.GetFullPath(Path.Combine(typeof(Program).Assembly.Location, "../../../../../../", "data")); static void Main(string[] args) { diff --git a/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Sandwych.MapMatchingKit.Examples.HelloWorldApp.csproj b/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Sandwych.MapMatchingKit.Examples.HelloWorldApp.csproj index c98dc84..95d7d3e 100644 --- a/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Sandwych.MapMatchingKit.Examples.HelloWorldApp.csproj +++ b/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Sandwych.MapMatchingKit.Examples.HelloWorldApp.csproj @@ -6,7 +6,7 @@ - + diff --git a/src/Sandwych.MapMatchingKit/Matching/Minset.cs b/src/Sandwych.MapMatchingKit/Matching/Minset.cs index 744e097..d53efd5 100644 --- a/src/Sandwych.MapMatchingKit/Matching/Minset.cs +++ b/src/Sandwych.MapMatchingKit/Matching/Minset.cs @@ -61,7 +61,7 @@ private static double Round(double value) /// /// candidates Set of matching candidates as objects. /// Minimized (reduced) set of matching candidates as objects - public static ICollection Minimize(IEnumerable candidates) + public static HashSet Minimize(IEnumerable candidates) { var map = new Dictionary(candidates.Count()); var misses = new Dictionary(candidates.Count()); diff --git a/src/Sandwych.MapMatchingKit/Roads/RoadMap.cs b/src/Sandwych.MapMatchingKit/Roads/RoadMap.cs index 5a7a1c0..3522640 100644 --- a/src/Sandwych.MapMatchingKit/Roads/RoadMap.cs +++ b/src/Sandwych.MapMatchingKit/Roads/RoadMap.cs @@ -31,11 +31,8 @@ public RoadMap(IEnumerable roads, ISpatialOperation spatial) : base(roads) // The original Barefoot is using Quad Tree for spatial indexing, however, in my experiment, NTS's STRtree is // much faster than NTS's Quadtree. - this.Index = new Spatial.Index.RBush.RBushSpatialIndex(roads.Select(x => x.RoadInfo), spatial, r => r.Geometry, r => r.Length); - } - - public RoadMap(IEnumerable roads) : this(roads, GeographySpatialOperation.Instance) - { + //this.Index = new Spatial.Index.RBush.RBushSpatialIndex(roads.Select(x => x.RoadInfo), spatial, r => r.Geometry, r => r.Length); + this.Index = new RtreeIndex(roads.Select(x => x.RoadInfo), spatial, r => r.Geometry, r => r.Length); } private IEnumerable Split(IEnumerable<(RoadInfo road, double fraction)> points) diff --git a/src/Sandwych.MapMatchingKit/Sandwych.MapMatchingKit.csproj b/src/Sandwych.MapMatchingKit/Sandwych.MapMatchingKit.csproj index 5c66962..d805351 100644 --- a/src/Sandwych.MapMatchingKit/Sandwych.MapMatchingKit.csproj +++ b/src/Sandwych.MapMatchingKit/Sandwych.MapMatchingKit.csproj @@ -7,7 +7,7 @@ - + diff --git a/src/Sandwych.MapMatchingKit/Spatial/CartesianSpatialOperation.cs b/src/Sandwych.MapMatchingKit/Spatial/CartesianSpatialOperation.cs index 7f18f71..825fc83 100644 --- a/src/Sandwych.MapMatchingKit/Spatial/CartesianSpatialOperation.cs +++ b/src/Sandwych.MapMatchingKit/Spatial/CartesianSpatialOperation.cs @@ -29,14 +29,14 @@ public double Distance(in Coordinate2D a, in Coordinate2D b) => public double Intercept(ILineString p, in Coordinate2D c) { var d = Double.MaxValue; - var a = p.GetPointN(0).ToCoordinate2D(); + var a = p.GetCoordinateN(0).ToCoordinate2D(); var s = 0D; var sf = 0D; var ds = 0D; for (int i = 1; i < p.NumPoints; ++i) { - var b = p.GetPointN(i).ToCoordinate2D(); + var b = p.GetCoordinateN(i).ToCoordinate2D(); ds = this.Distance(a, b); @@ -108,7 +108,7 @@ public Coordinate2D Interpolate(ILineString path, double l, double f) { throw new ArgumentOutOfRangeException(nameof(f)); } - var p0 = path.GetPointN(0).ToCoordinate2D(); + var p0 = path.GetCoordinateN(0).ToCoordinate2D(); var a = p0; double d = l * f; @@ -121,12 +121,12 @@ public Coordinate2D Interpolate(ILineString path, double l, double f) if (f > 1 - 1E-10) { - return path.GetPointN(path.NumPoints - 1).ToCoordinate2D(); + return path.GetCoordinateN(path.NumPoints - 1).ToCoordinate2D(); } for (int i = 1; i < path.NumPoints; ++i) { - var b = path.GetPointN(i).ToCoordinate2D(); + var b = path.GetCoordinateN(i).ToCoordinate2D(); ds = this.Distance(a, b); if ((s + ds) >= d) @@ -156,8 +156,11 @@ public Envelope Envelope(in Coordinate2D c, double radius) return new Envelope(minCorner.X, maxCorner.X, minCorner.Y, maxCorner.Y); } - public Envelope Envelope(ILineString line) => - line.EnvelopeInternal; + public Envelope Envelope(ILineString line) + { + return line.EnvelopeInternal; + } + } } diff --git a/src/Sandwych.MapMatchingKit/Spatial/GeographySpatialOperation.cs b/src/Sandwych.MapMatchingKit/Spatial/GeographySpatialOperation.cs index fe6c986..a1006a7 100644 --- a/src/Sandwych.MapMatchingKit/Spatial/GeographySpatialOperation.cs +++ b/src/Sandwych.MapMatchingKit/Spatial/GeographySpatialOperation.cs @@ -43,24 +43,24 @@ public double Azimuth(ILineString path, double l, double f) throw new ArgumentOutOfRangeException(nameof(f)); } - var a = path.GetPointN(0).ToCoordinate2D(); + var a = path.GetCoordinateN(0).ToCoordinate2D(); double d = l * f; double s = 0, ds = 0; if (f < 0 + 1E-10) { - return this.Azimuth(path.GetPointN(0).ToCoordinate2D(), path.GetPointN(1).ToCoordinate2D(), 0); + return this.Azimuth(path.GetCoordinateN(0).ToCoordinate2D(), path.GetCoordinateN(1).ToCoordinate2D(), 0); } if (f > 1 - 1E-10) { - return this.Azimuth(path.GetPointN(path.NumPoints - 2).ToCoordinate2D(), - path.GetPointN(path.NumPoints - 1).ToCoordinate2D(), f); + return this.Azimuth(path.GetCoordinateN(path.NumPoints - 2).ToCoordinate2D(), + path.GetCoordinateN(path.NumPoints - 1).ToCoordinate2D(), f); } for (int i = 1; i < path.NumPoints; ++i) { - var b = path.GetPointN(i).ToCoordinate2D(); + var b = path.GetCoordinateN(i).ToCoordinate2D(); ds = this.Distance(a, b); if ((s + ds) >= d) @@ -95,14 +95,14 @@ public Envelope Envelope(ILineString line) public double Intercept(ILineString p, in Coordinate2D c) { var d = Double.MaxValue; - var a = p.GetPointN(0).ToCoordinate2D(); + var a = p.GetCoordinateN(0).ToCoordinate2D(); var s = 0D; var sf = 0D; var ds = 0D; for (int i = 1; i < p.NumPoints; ++i) { - var b = p.GetPointN(i).ToCoordinate2D(); + var b = p.GetCoordinateN(i).ToCoordinate2D(); ds = this.Distance(a, b); @@ -153,7 +153,7 @@ public Coordinate2D Interpolate(ILineString path, double l, double f) throw new ArgumentOutOfRangeException(nameof(f)); } - var p0 = path.GetPointN(0).ToCoordinate2D(); + var p0 = path.GetCoordinateN(0).ToCoordinate2D(); var a = p0; double d = l * f; double s = 0, ds = 0; @@ -165,12 +165,12 @@ public Coordinate2D Interpolate(ILineString path, double l, double f) if (f > 1 - 1E-10) { - return path.GetPointN(path.NumPoints - 1).ToCoordinate2D(); + return path.GetCoordinateN(path.NumPoints - 1).ToCoordinate2D(); } for (int i = 1; i < path.NumPoints; ++i) { - var b = path.GetPointN(i).ToCoordinate2D(); + var b = path.GetCoordinateN(i).ToCoordinate2D(); ds = this.Distance(a, b); if ((s + ds) >= d) @@ -190,7 +190,7 @@ public double Length(ILineString line) var d = 0D; for (var i = 1; i < line.NumPoints; ++i) { - d += this.Distance(line.GetPointN(i - 1).ToCoordinate2D(), line.GetPointN(i).ToCoordinate2D()); + d += this.Distance(line.GetCoordinateN(i - 1).ToCoordinate2D(), line.GetCoordinateN(i).ToCoordinate2D()); } return d; } diff --git a/src/Sandwych.MapMatchingKit/Spatial/Geometries/GeoAPILineStringExtensions.cs b/src/Sandwych.MapMatchingKit/Spatial/Geometries/GeoAPILineStringExtensions.cs index 52c71be..8a3e152 100644 --- a/src/Sandwych.MapMatchingKit/Spatial/Geometries/GeoAPILineStringExtensions.cs +++ b/src/Sandwych.MapMatchingKit/Spatial/Geometries/GeoAPILineStringExtensions.cs @@ -7,10 +7,7 @@ namespace Sandwych.MapMatchingKit.Spatial.Geometries { public static class GeoAPILineStringExtensions { - public static Coordinate2D GetCoordinate2DAt(this ILineString line, int n) - { - var p = line.GetPointN(n); - return new Coordinate2D(p.X, p.Y); - } + public static Coordinate2D GetCoordinate2DAt(this ILineString line, int n) => + line.GetCoordinateN(n).ToCoordinate2D(); } } diff --git a/src/Sandwych.MapMatchingKit/Spatial/Geometries/NtsCoordinateExtensions.cs b/src/Sandwych.MapMatchingKit/Spatial/Geometries/NtsCoordinateExtensions.cs new file mode 100644 index 0000000..2927224 --- /dev/null +++ b/src/Sandwych.MapMatchingKit/Spatial/Geometries/NtsCoordinateExtensions.cs @@ -0,0 +1,12 @@ +using System; +using System.Collections.Generic; +using System.Text; + +namespace Sandwych.MapMatchingKit.Spatial.Geometries +{ + public static class NtsCoordinateExtensions + { + public static Coordinate2D ToCoordinate2D(this GeoAPI.Geometries.Coordinate coord) => + new Coordinate2D(coord.X, coord.Y); + } +} diff --git a/src/Sandwych.MapMatchingKit/Spatial/Index/AbstractNtsSpatialIndex.cs b/src/Sandwych.MapMatchingKit/Spatial/Index/AbstractNtsSpatialIndex.cs new file mode 100644 index 0000000..ba0ca21 --- /dev/null +++ b/src/Sandwych.MapMatchingKit/Spatial/Index/AbstractNtsSpatialIndex.cs @@ -0,0 +1,44 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using GeoAPI.Geometries; +using NetTopologySuite.Index; +using Sandwych.MapMatchingKit.Spatial.Geometries; + +namespace Sandwych.MapMatchingKit.Spatial.Index +{ + public abstract class AbstractNtsSpatialIndex : AbstractSpatialIndex + { + protected abstract NetTopologySuite.Index.ISpatialIndex Index { get; } + + protected AbstractNtsSpatialIndex(IEnumerable items, ISpatialOperation spatialService, + Func geometryGetter, Func lengthGetter) + : base(items, spatialService, geometryGetter, lengthGetter) + { + + } + + protected override void Add(TItem item) + { + var geom = this.ItemGeometryGetter(item); + var env = this.Spatial.Envelope(geom as ILineString); + var ntsEnv = new GeoAPI.Geometries.Envelope(env.MinX, env.MaxX, env.MinY, env.MaxY); + this.Index.Insert(ntsEnv, item); + } + + protected override void AddRange(IEnumerable items) + { + foreach (var item in items) + { + this.Add(item); + } + } + + public override IEnumerable Search(Envelope envelope) + { + return this.Index.Query(envelope); + } + + } +} diff --git a/src/Sandwych.MapMatchingKit/Spatial/Index/AbstractSpatialIndex.cs b/src/Sandwych.MapMatchingKit/Spatial/Index/AbstractSpatialIndex.cs index fdb7d15..8ec6d9b 100644 --- a/src/Sandwych.MapMatchingKit/Spatial/Index/AbstractSpatialIndex.cs +++ b/src/Sandwych.MapMatchingKit/Spatial/Index/AbstractSpatialIndex.cs @@ -3,14 +3,12 @@ using System.Linq; using System.Text; using GeoAPI.Geometries; -using NetTopologySuite.Index; using Sandwych.MapMatchingKit.Spatial.Geometries; namespace Sandwych.MapMatchingKit.Spatial.Index { public abstract class AbstractSpatialIndex : ISpatialIndex { - protected abstract NetTopologySuite.Index.ISpatialIndex Index { get; } protected ISpatialOperation Spatial { get; } protected Func ItemGeometryGetter { get; } protected Func ItemLengthGetter { get; } @@ -24,25 +22,23 @@ public AbstractSpatialIndex(IEnumerable items, ISpatialOperation spatialS this.AddRange(items); } - public IEnumerable<(TItem, double)> Radius(Coordinate2D c, double radius, int k = -1) + public virtual IEnumerable<(TItem, double)> Radius(in Coordinate2D c, double radius, int k = -1) { - var neighbors = new List<(TItem, double)>(); + var neighbors = new List<(TItem, double)>(16); var env = this.Spatial.Envelope(c, radius); - - var visitor = new IndexItemVisitor(item => + var candidates = this.Search(env); + foreach (var candidate in candidates) { - var geometry = this.ItemGeometryGetter(item); + var geometry = this.ItemGeometryGetter(candidate); var f = this.Spatial.Intercept(geometry, c); - var p = this.Spatial.Interpolate(geometry, this.ItemLengthGetter(item), f); + var p = this.Spatial.Interpolate(geometry, this.ItemLengthGetter(candidate), f); var d = this.Spatial.Distance(p, c); if (d < radius) { - neighbors.Add((item, f)); + neighbors.Add((candidate, f)); } - }); - - Index.Query(env, visitor); + } if (k > 0) { @@ -54,20 +50,11 @@ public AbstractSpatialIndex(IEnumerable items, ISpatialOperation spatialS } } - protected void Add(TItem item) - { - var geom = this.ItemGeometryGetter(item); - var env = this.Spatial.Envelope(geom as ILineString); - this.Index.Insert(env, item); - } + protected abstract void Add(TItem item); + protected abstract void AddRange(IEnumerable items); - protected void AddRange(IEnumerable items) - { - foreach (var item in items) - { - this.Add(item); - } - } + public abstract IEnumerable Search(Envelope envelope); } + } diff --git a/src/Sandwych.MapMatchingKit/Spatial/Index/ISpatialIndex.cs b/src/Sandwych.MapMatchingKit/Spatial/Index/ISpatialIndex.cs index 383d1b1..22af771 100644 --- a/src/Sandwych.MapMatchingKit/Spatial/Index/ISpatialIndex.cs +++ b/src/Sandwych.MapMatchingKit/Spatial/Index/ISpatialIndex.cs @@ -8,6 +8,8 @@ namespace Sandwych.MapMatchingKit.Spatial.Index { public interface ISpatialIndex { + IEnumerable Search(Envelope envelope); + /// /// Gets objects stored in the index that are within a certain radius or overlap a certain radius. /// @@ -15,6 +17,6 @@ public interface ISpatialIndex /// Radius in meters /// maximum number of candidates /// Result set of object(s) that are within a the given radius or overlap the radius, limited by k. - IEnumerable<(TItem, double)> Radius(Coordinate2D c, double radius, int k = -1); + IEnumerable<(TItem, double)> Radius(in Coordinate2D c, double radius, int k = -1); } } diff --git a/src/Sandwych.MapMatchingKit/Spatial/Index/IndexItemVisitor.cs b/src/Sandwych.MapMatchingKit/Spatial/Index/NtsIndexItemVisitor.cs similarity index 74% rename from src/Sandwych.MapMatchingKit/Spatial/Index/IndexItemVisitor.cs rename to src/Sandwych.MapMatchingKit/Spatial/Index/NtsIndexItemVisitor.cs index 56d4973..b170bb2 100644 --- a/src/Sandwych.MapMatchingKit/Spatial/Index/IndexItemVisitor.cs +++ b/src/Sandwych.MapMatchingKit/Spatial/Index/NtsIndexItemVisitor.cs @@ -5,11 +5,11 @@ namespace Sandwych.MapMatchingKit.Spatial.Index { - public sealed class IndexItemVisitor : IItemVisitor + public sealed class NtsIndexItemVisitor : IItemVisitor { public Action Action { get; } - public IndexItemVisitor(Action action) + public NtsIndexItemVisitor(Action action) { this.Action = action; } diff --git a/src/Sandwych.MapMatchingKit/Spatial/Index/QuadtreeIndex.cs b/src/Sandwych.MapMatchingKit/Spatial/Index/QuadtreeIndex.cs index 9cbcd3b..deb3ef9 100644 --- a/src/Sandwych.MapMatchingKit/Spatial/Index/QuadtreeIndex.cs +++ b/src/Sandwych.MapMatchingKit/Spatial/Index/QuadtreeIndex.cs @@ -7,7 +7,7 @@ namespace Sandwych.MapMatchingKit.Spatial.Index { - public class QuadtreeIndex : AbstractSpatialIndex + public class QuadtreeIndex : AbstractNtsSpatialIndex { private readonly NetTopologySuite.Index.ISpatialIndex _index = new Quadtree(); diff --git a/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/ProjectionComparer.cs b/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/ProjectionComparer.cs index c42d652..c14c0e9 100644 --- a/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/ProjectionComparer.cs +++ b/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/ProjectionComparer.cs @@ -3,115 +3,115 @@ namespace RBush { - /// - /// Non-generic class to produce instances of the generic class, - /// optionally using type inference. - /// - public static class ProjectionComparer - { - /// - /// Creates an instance of ProjectionComparer using the specified projection. - /// - /// Type parameter for the elements to be compared - /// Type parameter for the keys to be compared, after being projected from the elements - /// Projection to use when determining the key of an element - /// A comparer which will compare elements by projecting each element to its key, and comparing keys - public static ProjectionComparer Create(Func projection) - { - return new ProjectionComparer(projection); - } + /// + /// Non-generic class to produce instances of the generic class, + /// optionally using type inference. + /// + public static class ProjectionComparer + { + /// + /// Creates an instance of ProjectionComparer using the specified projection. + /// + /// Type parameter for the elements to be compared + /// Type parameter for the keys to be compared, after being projected from the elements + /// Projection to use when determining the key of an element + /// A comparer which will compare elements by projecting each element to its key, and comparing keys + public static ProjectionComparer Create(Func projection) + { + return new ProjectionComparer(projection); + } - /// - /// Creates an instance of ProjectionComparer using the specified projection. - /// The ignored parameter is solely present to aid type inference. - /// - /// Type parameter for the elements to be compared - /// Type parameter for the keys to be compared, after being projected from the elements - /// Value is ignored - type may be used by type inference - /// Projection to use when determining the key of an element - /// A comparer which will compare elements by projecting each element to its key, and comparing keys - public static ProjectionComparer Create - (TSource ignored, - Func projection) - { - return new ProjectionComparer(projection); - } + /// + /// Creates an instance of ProjectionComparer using the specified projection. + /// The ignored parameter is solely present to aid type inference. + /// + /// Type parameter for the elements to be compared + /// Type parameter for the keys to be compared, after being projected from the elements + /// Value is ignored - type may be used by type inference + /// Projection to use when determining the key of an element + /// A comparer which will compare elements by projecting each element to its key, and comparing keys + public static ProjectionComparer Create + (TSource ignored, + Func projection) + { + return new ProjectionComparer(projection); + } - } + } - /// - /// Class generic in the source only to produce instances of the - /// doubly generic class, optionally using type inference. - /// - public static class ProjectionComparer - { - /// - /// Creates an instance of ProjectionComparer using the specified projection. - /// - /// Type parameter for the keys to be compared, after being projected from the elements - /// Projection to use when determining the key of an element - /// A comparer which will compare elements by projecting each element to its key, and comparing keys - public static ProjectionComparer Create(Func projection) - { - return new ProjectionComparer(projection); - } - } + /// + /// Class generic in the source only to produce instances of the + /// doubly generic class, optionally using type inference. + /// + public static class ProjectionComparer + { + /// + /// Creates an instance of ProjectionComparer using the specified projection. + /// + /// Type parameter for the keys to be compared, after being projected from the elements + /// Projection to use when determining the key of an element + /// A comparer which will compare elements by projecting each element to its key, and comparing keys + public static ProjectionComparer Create(Func projection) + { + return new ProjectionComparer(projection); + } + } - /// - /// Comparer which projects each element of the comparison to a key, and then compares - /// those keys using the specified (or default) comparer for the key type. - /// - /// Type of elements which this comparer will be asked to compare - /// Type of the key projected from the element - public class ProjectionComparer : IComparer - { - readonly Func projection; - readonly IComparer comparer; + /// + /// Comparer which projects each element of the comparison to a key, and then compares + /// those keys using the specified (or default) comparer for the key type. + /// + /// Type of elements which this comparer will be asked to compare + /// Type of the key projected from the element + public readonly struct ProjectionComparer : IComparer + { + readonly Func projection; + readonly IComparer comparer; - /// - /// Creates a new instance using the specified projection, which must not be null. - /// The default comparer for the projected type is used. - /// - /// Projection to use during comparisons - public ProjectionComparer(Func projection) - : this(projection, null) - { - } + /// + /// Creates a new instance using the specified projection, which must not be null. + /// The default comparer for the projected type is used. + /// + /// Projection to use during comparisons + public ProjectionComparer(Func projection) + : this(projection, null) + { + } - /// - /// Creates a new instance using the specified projection, which must not be null. - /// - /// Projection to use during comparisons - /// The comparer to use on the keys. May be null, in - /// which case the default comparer will be used. - public ProjectionComparer(Func projection, IComparer comparer) - { - this.comparer = comparer ?? Comparer.Default; - this.projection = projection; - } + /// + /// Creates a new instance using the specified projection, which must not be null. + /// + /// Projection to use during comparisons + /// The comparer to use on the keys. May be null, in + /// which case the default comparer will be used. + public ProjectionComparer(Func projection, IComparer comparer) + { + this.comparer = comparer ?? Comparer.Default; + this.projection = projection; + } - /// - /// Compares x and y by projecting them to keys and then comparing the keys. - /// Null values are not projected; they obey the - /// standard comparer contract such that two null values are equal; any null value is - /// less than any non-null value. - /// - public int Compare(TSource x, TSource y) - { - // Don't want to project from nullity - if (x == null && y == null) - { - return 0; - } - if (x == null) - { - return -1; - } - if (y == null) - { - return 1; - } - return comparer.Compare(projection(x), projection(y)); - } - } + /// + /// Compares x and y by projecting them to keys and then comparing the keys. + /// Null values are not projected; they obey the + /// standard comparer contract such that two null values are equal; any null value is + /// less than any non-null value. + /// + public int Compare(TSource x, TSource y) + { + // Don't want to project from nullity + if (x == null && y == null) + { + return 0; + } + if (x == null) + { + return -1; + } + if (y == null) + { + return 1; + } + return comparer.Compare(projection(x), projection(y)); + } + } } diff --git a/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/RBush.Node.cs b/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/RBush.Node.cs index c443ede..0e358f3 100644 --- a/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/RBush.Node.cs +++ b/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/RBush.Node.cs @@ -6,7 +6,7 @@ namespace RBush { public partial class RBush { - internal class Node : ISpatialData + internal sealed class Node : ISpatialData { private Envelope _envelope; diff --git a/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/RBushSpatialIndex.cs b/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/RBushSpatialIndex.cs index d2e5638..92ca9ef 100644 --- a/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/RBushSpatialIndex.cs +++ b/src/Sandwych.MapMatchingKit/Spatial/Index/RBush/RBushSpatialIndex.cs @@ -6,40 +6,13 @@ namespace Sandwych.MapMatchingKit.Spatial.Index.RBush { + using Sandwych.MapMatchingKit.Spatial.Geometries; + using System.Linq; + using RB = global::RBush; + public class RBushSpatialIndex : AbstractSpatialIndex { - private sealed class NtsSpatialIndex : NetTopologySuite.Index.ISpatialIndex - { - private readonly global::RBush.RBush _backend = new global::RBush.RBush(); - - public void Insert(Envelope itemEnv, TItem item) - { - var env = new global::RBush.Envelope(itemEnv.MinX, itemEnv.MinY, itemEnv.MaxX, itemEnv.MaxY); - _backend.Insert(new RBushIndexItem(item, env)); - } - - public IList Query(Envelope searchEnv) - { - throw new NotSupportedException(); - } - - public void Query(Envelope searchEnv, IItemVisitor visitor) - { - var env = new global::RBush.Envelope(searchEnv.MinX, searchEnv.MinY, searchEnv.MaxX, searchEnv.MaxY); - var items = _backend.Search(env); - foreach (var i in items) - { - visitor.VisitItem(i.Item); - } - } - - public bool Remove(Envelope itemEnv, TItem item) - { - throw new NotSupportedException(); - } - } - - private class RBushIndexItem : global::RBush.ISpatialData + private class RBushIndexItem : RB.ISpatialData { private global::RBush.Envelope _envelope; @@ -54,8 +27,7 @@ public RBushIndexItem(TItem item, in global::RBush.Envelope envelope) public ref readonly global::RBush.Envelope Envelope => ref _envelope; } - private readonly NetTopologySuite.Index.ISpatialIndex _index = new NtsSpatialIndex(); - protected override NetTopologySuite.Index.ISpatialIndex Index => _index; + private readonly RB.RBush _index = new RB.RBush(); public RBushSpatialIndex( IEnumerable items, ISpatialOperation spatialService, @@ -64,5 +36,26 @@ public RBushSpatialIndex( { } + protected override void Add(TItem item) + { + var env = this.Spatial.Envelope(ItemGeometryGetter(item) as ILineString); + var rbEnv = new RB.Envelope(env.MinX, env.MinY, env.MaxX, env.MaxY); + var rbItem = new RBushIndexItem(item, rbEnv); + _index.Insert(rbItem); + } + + protected override void AddRange(IEnumerable items) + { + foreach (var item in items) + { + this.Add(item); + } + } + + public override IEnumerable Search(Envelope envelope) + { + var rbEnv = new RB.Envelope(envelope.MinX, envelope.MinY, envelope.MaxX, envelope.MaxY); + return _index.Search(rbEnv).Select(e => e.Item); + } } } diff --git a/src/Sandwych.MapMatchingKit/Spatial/Index/RtreeIndex.cs b/src/Sandwych.MapMatchingKit/Spatial/Index/RtreeIndex.cs index f4dfbe9..fc2850a 100644 --- a/src/Sandwych.MapMatchingKit/Spatial/Index/RtreeIndex.cs +++ b/src/Sandwych.MapMatchingKit/Spatial/Index/RtreeIndex.cs @@ -7,7 +7,7 @@ namespace Sandwych.MapMatchingKit.Spatial.Index { - public class RtreeIndex : AbstractSpatialIndex + public class RtreeIndex : AbstractNtsSpatialIndex { private readonly NetTopologySuite.Index.ISpatialIndex _index = new STRtree(); diff --git a/src/Sandwych.MapMatchingKit/Spatial/Projection/ICoordinateTransformation.cs b/src/Sandwych.MapMatchingKit/Spatial/Projection/ICoordinateTransformation.cs index 2295f75..557f934 100644 --- a/src/Sandwych.MapMatchingKit/Spatial/Projection/ICoordinateTransformation.cs +++ b/src/Sandwych.MapMatchingKit/Spatial/Projection/ICoordinateTransformation.cs @@ -21,7 +21,7 @@ public static ILineString Transform(this ICoordinateTransformation self, ILineSt var newCoords = new Coordinate[line.NumPoints]; for (var i = 0; i < line.NumPoints; i++) { - var pt = line.GetPointN(i); + var pt = line.GetCoordinateN(i); var coord = newCoords[i]; var oldCoord = new Coordinate2D(pt.X, pt.Y); var transformedCoord = self.Transform(oldCoord); diff --git a/test/Sandwych.MapMatchingKit.Tests/Spatial/GeographySpatialOperationTest.cs b/test/Sandwych.MapMatchingKit.Tests/Spatial/GeographySpatialOperationTest.cs index 0391201..d317109 100644 --- a/test/Sandwych.MapMatchingKit.Tests/Spatial/GeographySpatialOperationTest.cs +++ b/test/Sandwych.MapMatchingKit.Tests/Spatial/GeographySpatialOperationTest.cs @@ -59,8 +59,8 @@ public void TestLineInterception() { var wktReader = new WKTReader(); var ab = wktReader.Read("LINESTRING(11.4047661 48.1403687,11.4053519 48.141055)") as ILineString; - var a = ab.GetPointN(0).ToCoordinate2D(); - var b = ab.GetPointN(1).ToCoordinate2D(); + var a = ab.GetCoordinateN(0).ToCoordinate2D(); + var b = ab.GetCoordinateN(1).ToCoordinate2D(); var points = new string[] { "POINT(11.406501117689324 48.14051652560591)", // East From f9fcad33eb59589bfb3d40e3550ff95a4f52fab6 Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Tue, 6 Mar 2018 15:13:11 +0800 Subject: [PATCH 19/37] new build scripts --- .gitignore | 1 + build-scripts/setup.cake | 158 --------------------------- build.cake | 134 +++++++++++++++++++++++ build-scripts/build.ps1 => build.ps1 | 133 +++++++++++++++------- build.sh | 117 ++++++++++++++++++++ 5 files changed, 344 insertions(+), 199 deletions(-) delete mode 100644 build-scripts/setup.cake create mode 100644 build.cake rename build-scripts/build.ps1 => build.ps1 (60%) create mode 100644 build.sh diff --git a/.gitignore b/.gitignore index 7e806aa..04ee57a 100644 --- a/.gitignore +++ b/.gitignore @@ -31,3 +31,4 @@ project.lock.json .dotnetcli *.qgs~ *.output.csv +/tools/ diff --git a/build-scripts/setup.cake b/build-scripts/setup.cake deleted file mode 100644 index 6a4b9b6..0000000 --- a/build-scripts/setup.cake +++ /dev/null @@ -1,158 +0,0 @@ -#tool "nuget:?package=GitVersion.CommandLine" -#tool nuget:?package=OpenCover -#tool nuget:?package=Codecov -#addin nuget:?package=Cake.Figlet -#addin "Cake.DocFx" -#tool "docfx.console" - -var target = Argument("target", "Default"); -var configuration = Argument("configuration", "Release"); -var artifactPath = Argument("artifactPath", "./artifacts"); -var versionAssemblyInfoFile = Argument("versionAssemblyInfo", "./build/VersionAssemblyInfo.cs"); - -var buildPath = MakeAbsolute(Directory("./build")); -var slnPath = "./MaltReport.sln"; -var artifacts = MakeAbsolute(Directory(artifactPath)); -var versionAssemblyInfo = MakeAbsolute(File(versionAssemblyInfoFile)); -GitVersion versionInfo = null; - - -Setup(context => -{ - Information(Figlet("Sandwych.Reporting")); - - EnsureDirectoryExists(artifacts); - - EnsureDirectoryExists(buildPath); - /* - var binDirs = GetDirectories(solutionPath.GetDirectory() +@"\src\**\bin"); - var objDirs = GetDirectories(solutionPath.GetDirectory() +@"\src\**\obj"); - DeleteDirectories(binDirs, true); - DeleteDirectories(objDirs, true); - */ - -}); - - -Task("Update-Version-Info") - .IsDependentOn("Create-Version-Info") - .Does(() => -{ - versionInfo = GitVersion(new GitVersionSettings { - UpdateAssemblyInfo = true, - UpdateAssemblyInfoFilePath = versionAssemblyInfo - }); - if(versionInfo != null) { - Information("Version: {0}", versionInfo.FullSemVer); - } else { - throw new Exception("Unable to determine version"); - } -}); - - -Task("Create-Version-Info") - .WithCriteria(() => !FileExists(versionAssemblyInfo)) - .Does(() => -{ - Information("Creating version assembly info"); - CreateAssemblyInfo(versionAssemblyInfo, new AssemblyInfoSettings { - Version = "0.0.0.0", - FileVersion = "0.0.0.0", - InformationalVersion = "", - }); -}); - - -Task("Clean").Does(() => -{ - CleanDirectories(new[]{"./Sandwych.Reporting/bin", "./Sandwych.Reporting.Demo/bin", "./Sandwych.Reporting.Tests/bin"}); -}); - -Task("Restore") - .IsDependentOn("Clean") - .IsDependentOn("Update-Version-Info") - .Does(() => -{ - NuGetRestore(slnPath, new NuGetRestoreSettings()); -}); - - -Task("Build") - .IsDependentOn("Restore") - .Does(() => -{ - MSBuild(slnPath, c => c - .SetConfiguration(configuration) - .SetVerbosity(Verbosity.Minimal) - .UseToolVersion(MSBuildToolVersion.VS2015) - .WithProperty("TreatWarningsAsErrors", "true") - .WithTarget("Build") - ); - -}); - - -Task("Tests") - .IsDependentOn("Build") - .Does(() => -{ -}); - - -Task("Document").Does(() => DocFxBuild("./docs/docfx.json")); - - -Task("ServeDocument").Does(() => { - var settings = new DocFxBuildSettings { - Serve = true, - }; - DocFxBuild("./docs/docfx.json", settings); - -}); - - -Task("Pack").IsDependentOn("Tests").Does(() => -{ - var version = GitVersion(); - var nuGetPackSettings = new NuGetPackSettings { - Id = "MaltReport2", - Version = versionInfo.NuGetVersionV2, - NoPackageAnalysis = true, - BasePath = "./Sandwych.Reporting/Bin/Release", - OutputDirectory = artifacts, - Files = new [] { - new NuSpecContent {Source = "Sandwych.Reporting.dll", Target = "lib/net45"}, - }, - }; - - NuGetPack("./MaltReport2.nuspec", nuGetPackSettings); -}); - -//AppVeyor Stuff - -Task("AppVeyor-Update-Build-Number") - .IsDependentOn("Update-Version-Info") - .WithCriteria(() => AppVeyor.IsRunningOnAppVeyor) - .Does(() => -{ - AppVeyor.UpdateBuildVersion(versionInfo.FullSemVer +"|" +AppVeyor.Environment.Build.Number); -}); -Task("Appveyor-Upload-Artifacts") - .IsDependentOn("Pack") - .WithCriteria(() => AppVeyor.IsRunningOnAppVeyor) - .Does(() => -{ - foreach(var nupkg in GetFiles(artifacts +"/*.nupkg")) { - AppVeyor.UploadArtifact(nupkg); - } -}); -Task("Appveyor") - .WithCriteria(() => AppVeyor.IsRunningOnAppVeyor) - .IsDependentOn("Pack") - .IsDependentOn("AppVeyor-Update-Build-Number") - .IsDependentOn("AppVeyor-Upload-Artifacts"); - - -Task("Default").IsDependentOn("Pack"); - -RunTarget(target); diff --git a/build.cake b/build.cake new file mode 100644 index 0000000..debfbf6 --- /dev/null +++ b/build.cake @@ -0,0 +1,134 @@ +//#addin nuget:?package=Cake.DocFx&version=0.5.0 +//#tool "docfx.console" + +var solutionFile = "Sandwych.MapMatchingKit.sln"; + +var target = Argument("target", "Default"); +var configuration = Argument("configuration", "Release"); + +Task("Restore-NuGet-Packages") + .Does(() => +{ + DotNetCoreRestore(solutionFile, new DotNetCoreRestoreSettings + { + Verbosity = DotNetCoreVerbosity.Minimal, + }); +}); + + +Task("Build") + .IsDependentOn("Restore-NuGet-Packages") + .Does(() => +{ + Information("Building Libraries..."); + var libSettings = new DotNetCoreBuildSettings() { + NoRestore = true, + Configuration = configuration, + }; + + if(!IsRunningOnWindows()) + { + libSettings.Framework = "netstandard2.0"; + } + + var libProjects = GetFiles("./src/**/*.csproj"); + foreach(var project in libProjects) + { + // .NET Core + DotNetCoreBuild(project.ToString(), libSettings); + } + + Information("Building Unit tests..."); + var testSettings = new DotNetCoreBuildSettings() { + NoRestore = true, + Configuration = configuration, + }; + + var testProjects = GetFiles("./test/**/*.csproj"); + foreach(var project in testProjects) + { + // .NET Core + DotNetCoreBuild(project.ToString(), testSettings); + } + +}); + + +Task("Run-Unit-Tests") + .IsDependentOn("Build") + .Does(() => +{ + var settings = new DotNetCoreTestSettings + { + Framework = "netcoreapp2.0", + NoBuild = true, + NoRestore = true, + Configuration = configuration, + }; + + var projects = GetFiles("./test/**/*.Tests.csproj"); + foreach(var project in projects) + { + DotNetCoreTest(project.ToString(), settings); + } +}); + + +Task("Create-NuGet-Packages") + .IsDependentOn("Run-Unit-Tests") + .Does(() => +{ + // Build libraries + var projects = GetFiles("./src/**/*.csproj"); + foreach(var project in projects) + { + var name = project.GetDirectory().FullPath; + if(name.EndsWith("Tests") || name.EndsWith("Xunit")) + { + continue; + } + + DotNetCorePack(project.FullPath, new DotNetCorePackSettings { + NoBuild = true, + NoRestore = true, + IncludeSymbols = false, + Configuration = configuration, + }); + } +}); + + +/* +Task("Generate-Docs").Does(() => { + DocFxBuild("./docs/docfx.json"); +}); + + +Task("View-Docs").Does(() => { + DocFxBuild("./docs/docfx.json", new DocFxBuildSettings { + Serve = true, + }); +}); +*/ + + +Task("Travis") + .IsDependentOn("Run-Unit-Tests"); + + +Task("Appveyor-Build") + .IsDependentOn("Create-NuGet-Packages"); + + +Task("Appveyor-Test") + .IsDependentOn("Run-Unit-Tests"); + + +Task("Default") + .IsDependentOn("Run-Unit-Tests") + .Does(() => { + Information("Executing the default task..."); +}); + + +RunTarget(target); diff --git a/build-scripts/build.ps1 b/build.ps1 similarity index 60% rename from build-scripts/build.ps1 rename to build.ps1 index 0ec3f2a..82529cf 100644 --- a/build-scripts/build.ps1 +++ b/build.ps1 @@ -5,11 +5,14 @@ ########################################################################## <# + .SYNOPSIS This is a Powershell script to bootstrap a Cake build. + .DESCRIPTION This Powershell script will download NuGet if missing, restore NuGet tools (including Cake) and execute your Cake build script with the parameters you provide. + .PARAMETER Script The build script to execute. .PARAMETER Target @@ -18,32 +21,35 @@ The build script target to run. The build configuration to use. .PARAMETER Verbosity Specifies the amount of information to be displayed. +.PARAMETER ShowDescription +Shows description about tasks. +.PARAMETER DryRun +Performs a dry run. .PARAMETER Experimental -Tells Cake to use the latest Roslyn release. -.PARAMETER WhatIf -Performs a dry run of the build script. -No tasks will be executed. +Uses the nightly builds of the Roslyn script engine. .PARAMETER Mono -Tells Cake to use the Mono scripting engine. +Uses the Mono Compiler rather than the Roslyn script engine. .PARAMETER SkipToolPackageRestore Skips restoring of packages. .PARAMETER ScriptArgs Remaining arguments are added here. + .LINK -http://cakebuild.net +https://cakebuild.net + #> [CmdletBinding()] Param( - [string]$Script = "setup.cake", - [string]$Target = "Default", - [ValidateSet("Release", "Debug")] - [string]$Configuration = "Release", + [string]$Script = "build.cake", + [string]$Target, + [string]$Configuration, [ValidateSet("Quiet", "Minimal", "Normal", "Verbose", "Diagnostic")] - [string]$Verbosity = "Verbose", + [string]$Verbosity, + [switch]$ShowDescription, + [Alias("WhatIf", "Noop")] + [switch]$DryRun, [switch]$Experimental, - [Alias("DryRun","Noop")] - [switch]$WhatIf, [switch]$Mono, [switch]$SkipToolPackageRestore, [Parameter(Position=0,Mandatory=$false,ValueFromRemainingArguments=$true)] @@ -75,6 +81,15 @@ function MD5HashFile([string] $filePath) } } +function GetProxyEnabledWebClient +{ + $wc = New-Object System.Net.WebClient + $proxy = [System.Net.WebRequest]::GetSystemWebProxy() + $proxy.Credentials = [System.Net.CredentialCache]::DefaultCredentials + $wc.Proxy = $proxy + return $wc +} + Write-Host "Preparing to run build script..." if(!$PSScriptRoot){ @@ -82,31 +97,15 @@ if(!$PSScriptRoot){ } $TOOLS_DIR = Join-Path $PSScriptRoot "tools" +$ADDINS_DIR = Join-Path $TOOLS_DIR "Addins" +$MODULES_DIR = Join-Path $TOOLS_DIR "Modules" $NUGET_EXE = Join-Path $TOOLS_DIR "nuget.exe" $CAKE_EXE = Join-Path $TOOLS_DIR "Cake/Cake.exe" $NUGET_URL = "https://dist.nuget.org/win-x86-commandline/latest/nuget.exe" $PACKAGES_CONFIG = Join-Path $TOOLS_DIR "packages.config" $PACKAGES_CONFIG_MD5 = Join-Path $TOOLS_DIR "packages.config.md5sum" - -# Should we use mono? -$UseMono = ""; -if($Mono.IsPresent) { - Write-Verbose -Message "Using the Mono based scripting engine." - $UseMono = "-mono" -} - -# Should we use the new Roslyn? -$UseExperimental = ""; -if($Experimental.IsPresent -and !($Mono.IsPresent)) { - Write-Verbose -Message "Using experimental version of Roslyn." - $UseExperimental = "-experimental" -} - -# Is this a dry run? -$UseDryRun = ""; -if($WhatIf.IsPresent) { - $UseDryRun = "-dryrun" -} +$ADDINS_PACKAGES_CONFIG = Join-Path $ADDINS_DIR "packages.config" +$MODULES_PACKAGES_CONFIG = Join-Path $MODULES_DIR "packages.config" # Make sure tools folder exists if ((Test-Path $PSScriptRoot) -and !(Test-Path $TOOLS_DIR)) { @@ -116,8 +115,10 @@ if ((Test-Path $PSScriptRoot) -and !(Test-Path $TOOLS_DIR)) { # Make sure that packages.config exist. if (!(Test-Path $PACKAGES_CONFIG)) { - Write-Verbose -Message "Downloading packages.config..." - try { (New-Object System.Net.WebClient).DownloadFile("http://cakebuild.net/download/bootstrapper/packages", $PACKAGES_CONFIG) } catch { + Write-Verbose -Message "Downloading packages.config..." + try { + $wc = GetProxyEnabledWebClient + $wc.DownloadFile("https://cakebuild.net/download/bootstrapper/packages", $PACKAGES_CONFIG) } catch { Throw "Could not download packages.config." } } @@ -125,7 +126,7 @@ if (!(Test-Path $PACKAGES_CONFIG)) { # Try find NuGet.exe in path if not exists if (!(Test-Path $NUGET_EXE)) { Write-Verbose -Message "Trying to find nuget.exe in PATH..." - $existingPaths = $Env:Path -Split ';' | Where-Object { (![string]::IsNullOrEmpty($_)) -and (Test-Path $_) } + $existingPaths = $Env:Path -Split ';' | Where-Object { (![string]::IsNullOrEmpty($_)) -and (Test-Path $_ -PathType Container) } $NUGET_EXE_IN_PATH = Get-ChildItem -Path $existingPaths -Filter "nuget.exe" | Select -First 1 if ($NUGET_EXE_IN_PATH -ne $null -and (Test-Path $NUGET_EXE_IN_PATH.FullName)) { Write-Verbose -Message "Found in PATH at $($NUGET_EXE_IN_PATH.FullName)." @@ -137,7 +138,8 @@ if (!(Test-Path $NUGET_EXE)) { if (!(Test-Path $NUGET_EXE)) { Write-Verbose -Message "Downloading NuGet.exe..." try { - (New-Object System.Net.WebClient).DownloadFile($NUGET_URL, $NUGET_EXE) + $wc = GetProxyEnabledWebClient + $wc.DownloadFile($NUGET_URL, $NUGET_EXE) } catch { Throw "Could not download NuGet.exe." } @@ -156,20 +158,56 @@ if(-Not $SkipToolPackageRestore.IsPresent) { if((!(Test-Path $PACKAGES_CONFIG_MD5)) -Or ($md5Hash -ne (Get-Content $PACKAGES_CONFIG_MD5 ))) { Write-Verbose -Message "Missing or changed package.config hash..." - Remove-Item * -Recurse -Exclude packages.config,nuget.exe + Get-ChildItem -Exclude packages.config,nuget.exe,Cake.Bakery | + Remove-Item -Recurse } Write-Verbose -Message "Restoring tools from NuGet..." - $NuGetOutput = Invoke-Expression "&`"$NUGET_EXE`" install -ExcludeVersion -PreRelease -OutputDirectory `"$TOOLS_DIR`" -Source https://www.myget.org/F/cake/api/v3/index.json" + $NuGetOutput = Invoke-Expression "&`"$NUGET_EXE`" install -ExcludeVersion -OutputDirectory `"$TOOLS_DIR`"" if ($LASTEXITCODE -ne 0) { - Throw "An error occured while restoring NuGet tools." + Throw "An error occurred while restoring NuGet tools." } else { $md5Hash | Out-File $PACKAGES_CONFIG_MD5 -Encoding "ASCII" } Write-Verbose -Message ($NuGetOutput | out-string) + + Pop-Location +} + +# Restore addins from NuGet +if (Test-Path $ADDINS_PACKAGES_CONFIG) { + Push-Location + Set-Location $ADDINS_DIR + + Write-Verbose -Message "Restoring addins from NuGet..." + $NuGetOutput = Invoke-Expression "&`"$NUGET_EXE`" install -ExcludeVersion -OutputDirectory `"$ADDINS_DIR`"" + + if ($LASTEXITCODE -ne 0) { + Throw "An error occurred while restoring NuGet addins." + } + + Write-Verbose -Message ($NuGetOutput | out-string) + + Pop-Location +} + +# Restore modules from NuGet +if (Test-Path $MODULES_PACKAGES_CONFIG) { + Push-Location + Set-Location $MODULES_DIR + + Write-Verbose -Message "Restoring modules from NuGet..." + $NuGetOutput = Invoke-Expression "&`"$NUGET_EXE`" install -ExcludeVersion -OutputDirectory `"$MODULES_DIR`"" + + if ($LASTEXITCODE -ne 0) { + Throw "An error occurred while restoring NuGet modules." + } + + Write-Verbose -Message ($NuGetOutput | out-string) + Pop-Location } @@ -178,7 +216,20 @@ if (!(Test-Path $CAKE_EXE)) { Throw "Could not find Cake.exe at $CAKE_EXE" } + + +# Build Cake arguments +$cakeArguments = @("$Script"); +if ($Target) { $cakeArguments += "-target=$Target" } +if ($Configuration) { $cakeArguments += "-configuration=$Configuration" } +if ($Verbosity) { $cakeArguments += "-verbosity=$Verbosity" } +if ($ShowDescription) { $cakeArguments += "-showdescription" } +if ($DryRun) { $cakeArguments += "-dryrun" } +if ($Experimental) { $cakeArguments += "-experimental" } +if ($Mono) { $cakeArguments += "-mono" } +$cakeArguments += $ScriptArgs + # Start Cake Write-Host "Running build script..." -Invoke-Expression "& `"$CAKE_EXE`" `"$Script`" -target=`"$Target`" -configuration=`"$Configuration`" -verbosity=`"$Verbosity`" $UseMono $UseDryRun $UseExperimental $ScriptArgs" +&$CAKE_EXE $cakeArguments exit $LASTEXITCODE diff --git a/build.sh b/build.sh new file mode 100644 index 0000000..b9e1252 --- /dev/null +++ b/build.sh @@ -0,0 +1,117 @@ +#!/usr/bin/env bash + +########################################################################## +# This is the Cake bootstrapper script for Linux and OS X. +# This file was downloaded from https://github.com/cake-build/resources +# Feel free to change this file to fit your needs. +########################################################################## + +# Define directories. +SCRIPT_DIR=$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd ) +TOOLS_DIR=$SCRIPT_DIR/tools +ADDINS_DIR=$TOOLS_DIR/Addins +MODULES_DIR=$TOOLS_DIR/Modules +NUGET_EXE=$TOOLS_DIR/nuget.exe +CAKE_EXE=$TOOLS_DIR/Cake/Cake.exe +PACKAGES_CONFIG=$TOOLS_DIR/packages.config +PACKAGES_CONFIG_MD5=$TOOLS_DIR/packages.config.md5sum +ADDINS_PACKAGES_CONFIG=$ADDINS_DIR/packages.config +MODULES_PACKAGES_CONFIG=$MODULES_DIR/packages.config + +# Define md5sum or md5 depending on Linux/OSX +MD5_EXE= +if [[ "$(uname -s)" == "Darwin" ]]; then + MD5_EXE="md5 -r" +else + MD5_EXE="md5sum" +fi + +# Define default arguments. +SCRIPT="build.cake" +CAKE_ARGUMENTS=() + +# Parse arguments. +for i in "$@"; do + case $1 in + -s|--script) SCRIPT="$2"; shift ;; + --) shift; CAKE_ARGUMENTS+=("$@"); break ;; + *) CAKE_ARGUMENTS+=("$1") ;; + esac + shift +done + +# Make sure the tools folder exist. +if [ ! -d "$TOOLS_DIR" ]; then + mkdir "$TOOLS_DIR" +fi + +# Make sure that packages.config exist. +if [ ! -f "$TOOLS_DIR/packages.config" ]; then + echo "Downloading packages.config..." + curl -Lsfo "$TOOLS_DIR/packages.config" https://cakebuild.net/download/bootstrapper/packages + if [ $? -ne 0 ]; then + echo "An error occurred while downloading packages.config." + exit 1 + fi +fi + +# Download NuGet if it does not exist. +if [ ! -f "$NUGET_EXE" ]; then + echo "Downloading NuGet..." + curl -Lsfo "$NUGET_EXE" https://dist.nuget.org/win-x86-commandline/latest/nuget.exe + if [ $? -ne 0 ]; then + echo "An error occurred while downloading nuget.exe." + exit 1 + fi +fi + +# Restore tools from NuGet. +pushd "$TOOLS_DIR" >/dev/null +if [ ! -f "$PACKAGES_CONFIG_MD5" ] || [ "$( cat "$PACKAGES_CONFIG_MD5" | sed 's/\r$//' )" != "$( $MD5_EXE "$PACKAGES_CONFIG" | awk '{ print $1 }' )" ]; then + find . -type d ! -name . ! -name 'Cake.Bakery' | xargs rm -rf +fi + +mono "$NUGET_EXE" install -ExcludeVersion +if [ $? -ne 0 ]; then + echo "Could not restore NuGet tools." + exit 1 +fi + +$MD5_EXE "$PACKAGES_CONFIG" | awk '{ print $1 }' >| "$PACKAGES_CONFIG_MD5" + +popd >/dev/null + +# Restore addins from NuGet. +if [ -f "$ADDINS_PACKAGES_CONFIG" ]; then + pushd "$ADDINS_DIR" >/dev/null + + mono "$NUGET_EXE" install -ExcludeVersion + if [ $? -ne 0 ]; then + echo "Could not restore NuGet addins." + exit 1 + fi + + popd >/dev/null +fi + +# Restore modules from NuGet. +if [ -f "$MODULES_PACKAGES_CONFIG" ]; then + pushd "$MODULES_DIR" >/dev/null + + mono "$NUGET_EXE" install -ExcludeVersion + if [ $? -ne 0 ]; then + echo "Could not restore NuGet modules." + exit 1 + fi + + popd >/dev/null +fi + +# Make sure that Cake has been installed. +if [ ! -f "$CAKE_EXE" ]; then + echo "Could not find Cake.exe at '$CAKE_EXE'." + exit 1 +fi + +# Start Cake +exec mono "$CAKE_EXE" $SCRIPT "${CAKE_ARGUMENTS[@]}" From 02ecb8797ab2cb6c6c4016ea33ce99eb87784c37 Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Tue, 6 Mar 2018 21:32:32 +0800 Subject: [PATCH 20/37] Fix NTS's bug in Unit test --- .../Program.cs | 4 +-- .../Roads/RoadMapBuilder.cs | 10 +++---- .../Spatial/Index/AbstractNtsSpatialIndex.cs | 3 +- .../Topology/BadGraphException.cs | 10 ------- .../Topology/BadGraphPathException.cs | 19 +++++++++++++ .../PrecomputedDijkstraRouter.cs | 2 +- .../PrecomputedDijkstraTable.cs | 5 +++- .../Spatial/GeographySpatialOperationTest.cs | 28 +++++++++++++++---- 8 files changed, 54 insertions(+), 27 deletions(-) delete mode 100644 src/Sandwych.MapMatchingKit/Topology/BadGraphException.cs create mode 100644 src/Sandwych.MapMatchingKit/Topology/BadGraphPathException.cs diff --git a/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs b/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs index ed7fab2..c43ba9f 100644 --- a/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs +++ b/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs @@ -31,8 +31,8 @@ static void Main(string[] args) Console.WriteLine("The road map has been loaded"); - //var router = new PrecomputedDijkstraRouter(map, Costs.TimePriorityCost, Costs.DistanceCost, 1000D); - var router = new DijkstraRouter(); + var router = new PrecomputedDijkstraRouter(map, Costs.TimePriorityCost, Costs.DistanceCost, 1000D); + //var router = new DijkstraRouter(); var matcher = new Matcher( map, router, Costs.TimePriorityCost, spatial); diff --git a/src/Sandwych.MapMatchingKit/Roads/RoadMapBuilder.cs b/src/Sandwych.MapMatchingKit/Roads/RoadMapBuilder.cs index 5de1a94..c7c225c 100644 --- a/src/Sandwych.MapMatchingKit/Roads/RoadMapBuilder.cs +++ b/src/Sandwych.MapMatchingKit/Roads/RoadMapBuilder.cs @@ -40,16 +40,16 @@ public RoadMap Build() private IEnumerable GetAllRoads() { - foreach (var r in _roads.Values) + foreach (var roadInfo in _roads.Values) { - if (r.OneWay) + if (roadInfo.OneWay) { - yield return new Road(r, Heading.Forward); + yield return new Road(roadInfo, Heading.Forward); } else { - yield return new Road(r, Heading.Forward); - yield return new Road(r, Heading.Backward); + yield return new Road(roadInfo, Heading.Forward); + yield return new Road(roadInfo, Heading.Backward); } } } diff --git a/src/Sandwych.MapMatchingKit/Spatial/Index/AbstractNtsSpatialIndex.cs b/src/Sandwych.MapMatchingKit/Spatial/Index/AbstractNtsSpatialIndex.cs index ba0ca21..67a6caa 100644 --- a/src/Sandwych.MapMatchingKit/Spatial/Index/AbstractNtsSpatialIndex.cs +++ b/src/Sandwych.MapMatchingKit/Spatial/Index/AbstractNtsSpatialIndex.cs @@ -23,8 +23,7 @@ protected override void Add(TItem item) { var geom = this.ItemGeometryGetter(item); var env = this.Spatial.Envelope(geom as ILineString); - var ntsEnv = new GeoAPI.Geometries.Envelope(env.MinX, env.MaxX, env.MinY, env.MaxY); - this.Index.Insert(ntsEnv, item); + this.Index.Insert(env, item); } protected override void AddRange(IEnumerable items) diff --git a/src/Sandwych.MapMatchingKit/Topology/BadGraphException.cs b/src/Sandwych.MapMatchingKit/Topology/BadGraphException.cs deleted file mode 100644 index 051afbb..0000000 --- a/src/Sandwych.MapMatchingKit/Topology/BadGraphException.cs +++ /dev/null @@ -1,10 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Text; - -namespace Sandwych.MapMatchingKit.Topology -{ - public class BadGraphException : Exception - { - } -} diff --git a/src/Sandwych.MapMatchingKit/Topology/BadGraphPathException.cs b/src/Sandwych.MapMatchingKit/Topology/BadGraphPathException.cs new file mode 100644 index 0000000..2f72909 --- /dev/null +++ b/src/Sandwych.MapMatchingKit/Topology/BadGraphPathException.cs @@ -0,0 +1,19 @@ +using System; +using System.Collections.Generic; +using System.Text; + +namespace Sandwych.MapMatchingKit.Topology +{ + public class BadGraphPathException : Exception + { + public BadGraphPathException() : base() + { + + } + + public BadGraphPathException(string message) : base(message) + { + + } + } +} diff --git a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouter.cs b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouter.cs index 30ee105..6ad9eaf 100644 --- a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouter.cs +++ b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouter.cs @@ -99,7 +99,7 @@ IEnumerable GetPath() { edges = GetPath(); } - catch (BadGraphException) + catch (BadGraphPathException) { yield break; } diff --git a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTable.cs b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTable.cs index 496826c..f55ebd8 100644 --- a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTable.cs +++ b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTable.cs @@ -104,7 +104,10 @@ public IEnumerable GetPathByVertex(TVertex sourceVertex, TVertex targetVe } else { - throw new BadGraphException(); + var msg = string.Format( + "Bad precomputed Dijkstra path: [sourceVertex={0}, targetVertex={1}, currentVertex={2}]", + sourceVertex, targetVertex, currentStart); + throw new BadGraphPathException(msg); } } } diff --git a/test/Sandwych.MapMatchingKit.Tests/Spatial/GeographySpatialOperationTest.cs b/test/Sandwych.MapMatchingKit.Tests/Spatial/GeographySpatialOperationTest.cs index d317109..047fc74 100644 --- a/test/Sandwych.MapMatchingKit.Tests/Spatial/GeographySpatialOperationTest.cs +++ b/test/Sandwych.MapMatchingKit.Tests/Spatial/GeographySpatialOperationTest.cs @@ -57,11 +57,13 @@ public void TestGnomonic() [Fact] public void TestLineInterception() { - var wktReader = new WKTReader(); + var factory = GeoAPI.GeometryServiceProvider.Instance.CreateGeometryFactory(); + var wktReader = new WKTReader(factory); var ab = wktReader.Read("LINESTRING(11.4047661 48.1403687,11.4053519 48.141055)") as ILineString; var a = ab.GetCoordinateN(0).ToCoordinate2D(); var b = ab.GetCoordinateN(1).ToCoordinate2D(); + /* FIXME NTS Bug var points = new string[] { "POINT(11.406501117689324 48.14051652560591)", // East "POINT(11.406713245538327 48.14182906667162)", // Northeast @@ -72,10 +74,23 @@ public void TestLineInterception() "POINT(11.405221721600025 48.1392039845402)", // South "POINT(11.406255844863914 48.13963486923349)" // Southeast }; + */ + + var points = new Coordinate2D[] { + new Coordinate2D(11.406501117689324, 48.14051652560591), // East + new Coordinate2D(11.406713245538327, 48.14182906667162), // Northeast + new Coordinate2D(11.404923416812364, 48.14258477213369), // North + new Coordinate2D(11.403300759321036, 48.14105540093837), // Northwest + new Coordinate2D(11.403193249043934, 48.140881120346386), // West + new Coordinate2D(11.40327279698731, 48.13987351306362), // Southwest + new Coordinate2D(11.405221721600025, 48.1392039845402), // South + new Coordinate2D(11.406255844863914, 48.13963486923349) // Southeast + }; for (int i = 0; i < points.Length; ++i) { - var c = (wktReader.Read(points[i]) as IPoint).ToCoordinate2D(); + //var c = (wktReader.Read(points[i]) as IPoint).ToCoordinate2D(); + var c = points[i]; var f = Spatial.Intercept(a, b, c); var p = Spatial.Interpolate(a, b, f); @@ -116,11 +131,11 @@ public void TestLineAzimuth() public void TestPathInterception1() { var wktReader = new WKTReader(); - var point = "POINT(11.410624 48.144161)"; + //var point = "POINT(11.410624 48.144161)"; var line = "LINESTRING(11.4047013 48.1402147,11.4047038 48.1402718,11.4047661 48.1403687,11.4053519 48.141055,11.4054617 48.1411901,11.4062664 48.1421968,11.4064586 48.1424479,11.4066449 48.1427372,11.4067254 48.1429028,11.4067864 48.1430673,11.4068647 48.1433303,11.4069456 48.1436822,11.4070524 48.1440368,11.4071569 48.1443314,11.4072635 48.1445915,11.4073887 48.1448641,11.4075228 48.1450729,11.407806 48.1454843,11.4080135 48.1458112,11.4083012 48.1463167,11.4086211 48.1469061,11.4087461 48.1471386,11.4088719 48.1474078,11.4089422 48.1476014,11.409028 48.1478353,11.409096 48.1480701,11.4091568 48.1483459,11.4094282 48.1498536)"; - var c = (wktReader.Read(point) as IPoint).ToCoordinate2D(); + var c = new Coordinate2D(11.410624, 48.144161);//(wktReader.Read(point) as IPoint).ToCoordinate2D(); var ab = wktReader.Read(line) as ILineString; var f = Spatial.Intercept(ab, c); @@ -139,10 +154,11 @@ public void TestPathInterception1() public void TestPathInterception2() { var wktReader = new WKTReader(); - String point = "POINT(11.584009286555187 48.17578656762985)"; + //String point = "POINT(11.584009286555187 48.17578656762985)"; String line = "LINESTRING(11.5852021 48.1761996, 11.585284 48.175924, 11.5852937 48.1758945)"; - var c = (wktReader.Read(point) as IPoint).ToCoordinate2D(); + //var c = (wktReader.Read(point) as IPoint).ToCoordinate2D(); + var c = new Coordinate2D(11.584009286555187, 48.17578656762985); var ab = wktReader.Read(line) as ILineString; var f = Spatial.Intercept(ab, c); From 5aeea3e84638aeb0bed17751883d82718c5691e0 Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Tue, 6 Mar 2018 22:40:27 +0800 Subject: [PATCH 21/37] UBODT works! --- Sandwych.MapMatchingKit.sln | 3 ++ .../Program.cs | 2 +- .../PrecomputedDijkstraRouter.cs | 33 ++++++++++--------- .../PrecomputedDijkstraTable.cs | 3 +- 4 files changed, 23 insertions(+), 18 deletions(-) diff --git a/Sandwych.MapMatchingKit.sln b/Sandwych.MapMatchingKit.sln index a711387..39e3e3f 100644 --- a/Sandwych.MapMatchingKit.sln +++ b/Sandwych.MapMatchingKit.sln @@ -86,4 +86,7 @@ Global GlobalSection(Performance) = preSolution HasPerformanceSessions = true EndGlobalSection + GlobalSection(Performance) = preSolution + HasPerformanceSessions = true + EndGlobalSection EndGlobal diff --git a/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs b/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs index c43ba9f..8257e16 100644 --- a/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs +++ b/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs @@ -17,7 +17,7 @@ namespace Sandwych.MapMatchingKit.Examples.HelloWorldApp { class Program { - private static readonly string s_dataDir = + private static readonly string s_dataDir = Path.GetFullPath(Path.Combine(typeof(Program).Assembly.Location, "../../../../../../", "data")); static void Main(string[] args) diff --git a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouter.cs b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouter.cs index 6ad9eaf..79de075 100644 --- a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouter.cs +++ b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouter.cs @@ -53,18 +53,26 @@ public IReadOnlyDictionary> Route(P source, IEnumerable

public IEnumerable Route(P source, P target, Func cost, Func bound = null, double max = double.NaN) { - var edges = RouteInternal(source, target, cost, bound, max); - if (bound != null && !double.IsNaN(max)) + try { - var boundingDistance = edges.Sum(bound); - boundingDistance -= source.Edge.Cost(source.Fraction, bound); - boundingDistance -= target.Edge.Cost(1D - target.Fraction, bound); - if (boundingDistance > max) + var edges = RouteInternal(source, target, cost, bound, max); + if (bound != null && !double.IsNaN(max)) { - return EmptyPath; + var boundingDistance = edges.Sum(bound); + boundingDistance -= source.Edge.Cost(source.Fraction, bound); + boundingDistance -= target.Edge.Cost(1D - target.Fraction, bound); + if (boundingDistance > max) + { + return EmptyPath; + } } + return edges; + } + catch (BadGraphPathException bgpe) + { + this.Logger.LogError(bgpe.Message); + return EmptyPath; } - return edges; } private IEnumerable RouteInternal( @@ -95,14 +103,7 @@ IEnumerable GetPath() } IEnumerable edges = EmptyPath; - try - { - edges = GetPath(); - } - catch (BadGraphPathException) - { - yield break; - } + edges = GetPath(); foreach (var edge in edges) { diff --git a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTable.cs b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTable.cs index f55ebd8..7ce3fbf 100644 --- a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTable.cs +++ b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTable.cs @@ -80,6 +80,7 @@ public IEnumerable GetPathByEdge(TEdge sourceEdge, TEdge targetEdge) yield return edge; } } + } public IEnumerable GetPathByVertex(TVertex sourceVertex, TVertex targetVertex) @@ -105,7 +106,7 @@ public IEnumerable GetPathByVertex(TVertex sourceVertex, TVertex targetVe else { var msg = string.Format( - "Bad precomputed Dijkstra path: [sourceVertex={0}, targetVertex={1}, currentVertex={2}]", + "Bad precomputed Dijkstra path: [sourceVertex={0}, targetVertex={1}, currentVertex={2}]", sourceVertex, targetVertex, currentStart); throw new BadGraphPathException(msg); } From 6751594e544083fc40ae93bb73eef499ab8deede Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Tue, 6 Mar 2018 23:48:10 +0800 Subject: [PATCH 22/37] add logging to UBODT generator --- .../PrecomputedDijkstraTableGenerator.cs | 12 +++++++++++- 1 file changed, 11 insertions(+), 1 deletion(-) diff --git a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTableGenerator.cs b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTableGenerator.cs index b7794a4..490b1c5 100644 --- a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTableGenerator.cs +++ b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTableGenerator.cs @@ -2,6 +2,8 @@ using System.Linq; using System.Collections.Generic; using QuickGraph; +using Microsoft.Extensions.Logging; +using Sandwych.MapMatchingKit.Utility; namespace Sandwych.MapMatchingKit.Topology.PrecomputedDijkstra { @@ -10,6 +12,7 @@ public class PrecomputedDijkstraTableGenerator where TVertex : IEquatable { + public ILogger Logger { get; set; } = NullLogger.Instance; public IEnumerable> ComputeRows( IVertexAndEdgeListGraph graph, @@ -17,7 +20,14 @@ public IEnumerable> ComputeRows( { var pquery = graph.Vertices.AsParallel(); var allRows = pquery.SelectMany(rootVertex => this.ComputeRowsSingleSource(graph, rootVertex, cost, bound, maxRadius)); - return allRows.ToList(); + var rowsList = allRows.ToArray(); + + if (this.Logger.IsEnabled(LogLevel.Debug)) + { + this.Logger.LogDebug("Rows count: {0}", rowsList.Length); + } + + return rowsList; } private IEnumerable> ComputeRowsSingleSource( From 5f8f610d3fb56aca1a7ad8e48c5b9f329955fb76 Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Tue, 6 Mar 2018 23:54:35 +0800 Subject: [PATCH 23/37] README.md --- README.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/README.md b/README.md index c395a87..7c6ff6e 100644 --- a/README.md +++ b/README.md @@ -152,3 +152,5 @@ All honors belongs to the original Barefoot developed by BMW Car IT GmbH: [https * "NetTopologySuite & ProjNET4GeoAPI" from NetTopologySuite Project: [https://github.com/NetTopologySuite](https://github.com/NetTopologySuite) * PriorityQueue class from Rx.NET Project: [https://github.com/Reactive-Extensions/Rx.NET](https://github.com/Reactive-Extensions/Rx.NET) * The UBODT(upper-bounded origin destination table) algroithm from Can Yang: [https://github.com/cyang-kth/fmm](https://github.com/cyang-kth/fmm) +* RBush - The R-Tree spatial index implementation from viceroypenguin: [https://github.com/viceroypenguin/RBush](https://github.com/viceroypenguin/RBush) +* QuickGraph from Peli: [https://github.com/oldrev/Sandwych.QuickGraph](https://github.com/oldrev/Sandwych.QuickGraph) From cf270f16639d7300b24a296affbd463815aed4e2 Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Wed, 7 Mar 2018 11:03:43 +0800 Subject: [PATCH 24/37] small optimization --- .../Program.cs | 10 +- .../SpatialIndexBenchmark.cs | 133 ++++++++++++++++++ src/Sandwych.MapMatchingKit/Markov/KState.cs | 4 +- .../Matching/Matcher.cs | 28 ++-- .../Matching/MatcherSample.cs | 1 + .../Spatial/GeographySpatialOperation.cs | 54 ++++--- .../Spatial/Index/AbstractSpatialIndex.cs | 9 +- .../Spatial/Index/ISpatialIndex.cs | 2 +- 8 files changed, 201 insertions(+), 40 deletions(-) create mode 100644 benchmark/Sandwych.MapMatchingKit.BenchmarkApp/SpatialIndexBenchmark.cs diff --git a/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/Program.cs b/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/Program.cs index 8d91827..f376de2 100644 --- a/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/Program.cs +++ b/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/Program.cs @@ -8,7 +8,15 @@ public class Program { static void Main(string[] args) { - var summary = BenchmarkRunner.Run(); + + var switcher = new BenchmarkSwitcher(new[] + { + typeof(RoutersBenchmark), + typeof(SpatialIndexBenchmark), + }); + + switcher.Run(args); + Console.ReadKey(); } } } diff --git a/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/SpatialIndexBenchmark.cs b/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/SpatialIndexBenchmark.cs new file mode 100644 index 0000000..c22b197 --- /dev/null +++ b/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/SpatialIndexBenchmark.cs @@ -0,0 +1,133 @@ +using System; +using System.Collections.Generic; +using System.IO; +using System.Linq; +using System.Text; +using System.Globalization; +using BenchmarkDotNet.Attributes; +using BenchmarkDotNet.Attributes.Columns; +using BenchmarkDotNet.Attributes.Exporters; +using BenchmarkDotNet.Attributes.Jobs; +using BenchmarkDotNet.Running; +using NetTopologySuite.Features; +using NetTopologySuite.IO; +using GeoAPI.Geometries; +using Sandwych.MapMatchingKit.Matching; +using Sandwych.MapMatchingKit.Spatial.Geometries; +using Sandwych.MapMatchingKit.Roads; +using Sandwych.MapMatchingKit.Spatial; +using Sandwych.MapMatchingKit.Topology; +using Sandwych.MapMatchingKit.Topology.PrecomputedDijkstra; +using Sandwych.MapMatchingKit.Spatial.Index; +using Sandwych.MapMatchingKit.Spatial.Index.RBush; + +namespace Sandwych.MapMatchingKit.BenchmarkApp +{ + [RPlotExporter, HtmlExporter, RankColumn] + [MemoryDiagnoser, ShortRunJob] + public class SpatialIndexBenchmark + { + private const double MaxDistance = 1000D; + private const double MaxGpsRadius = 100D; + private string DataDirPath { get; set; } + + private ISpatialOperation Spatial = new GeographySpatialOperation(); + private RtreeIndex _ntsRtreeIndex; + private QuadtreeIndex _ntsQuadtreeIndex; + private RBushSpatialIndex _rbushIndex; + + protected IReadOnlyList _geometries; + + static SpatialIndexBenchmark() + { + GeoAPI.NetTopologySuiteBootstrapper.Bootstrap(); + } + + [GlobalSetup] + public void Setup() + { + _geometries = this.MakeGeometries(); + _ntsRtreeIndex = new RtreeIndex(_geometries, this.Spatial, x => x, x => this.Spatial.Length(x)); + _ntsQuadtreeIndex = new QuadtreeIndex(_geometries, this.Spatial, x => x, x => this.Spatial.Length(x)); + _rbushIndex = new RBushSpatialIndex(_geometries, this.Spatial, x => x, x => this.Spatial.Length(x)); + } + + [Benchmark] + public void NtsSTRTreeBenchmark() + { + this.DoRadius(_ntsRtreeIndex); + } + + [Benchmark(Baseline = true)] + public void NtsQuadTreeBenchmark() + { + this.DoRadius(_ntsQuadtreeIndex); + } + + [Benchmark] + public void RBushRtreeBenchmark() + { + this.DoRadius(_rbushIndex); + } + + private int DoRadius(ISpatialIndex index) + { + { + var c = new Coordinate2D(11.343629, 48.083797); + var r = 50; + index.Radius(c, r); + } + { + var c = new Coordinate2D(11.344827, 48.083752); + var r = 10; + index.Radius(c, r); + } + { + var c = new Coordinate2D(11.344827, 48.083752); + var r = 5; + index.Radius(c, r); + } + return 0; + } + + private IReadOnlyList MakeGeometries() + { + /* + * (p2) (p3) ----- (e1) : (p1) -> (p2) ---------------------------------------------------- + * - \ / --------- (e2) : (p3) -> (p1) ---------------------------------------------------- + * | (p1) | ------ (e3) : (p4) -> (p1) ---------------------------------------------------- + * - / \ --------- (e4) : (p1) -> (p5) ---------------------------------------------------- + * (p4) (p5) ----- (e5) : (p2) -> (p4) ---------------------------------------------------- + * --------------- (e6) : (p5) -> (p3) ---------------------------------------------------- + */ + String p1 = "11.3441505 48.0839963"; + String p2 = "11.3421209 48.0850624"; + String p3 = "11.3460348 48.0850108"; + String p4 = "11.3427522 48.0832129"; + String p5 = "11.3469701 48.0825356"; + var reader = new WKTReader(); + ILineString readAsLineString(string wkt) => reader.Read("SRID=4326;" + wkt) as ILineString; + + var geometries = new ILineString[] { + readAsLineString("LINESTRING(" + p1 + "," + p2 + ")"), + readAsLineString("LINESTRING(" + p3 + "," + p1 + ")"), + readAsLineString("LINESTRING(" + p4 + "," + p1 + ")"), + readAsLineString("LINESTRING(" + p1 + "," + p5 + ")"), + readAsLineString("LINESTRING(" + p2 + "," + p4 + ")"), + readAsLineString("LINESTRING(" + p5 + "," + p3 + ")"), + }; + + var geoms = new List(); + for (int i = 0; i < geometries.Length; i++) + { + var g = geometries[i]; + g.UserData = i; + geoms.Add(g); + } + + return geoms; + } + + + } +} diff --git a/src/Sandwych.MapMatchingKit/Markov/KState.cs b/src/Sandwych.MapMatchingKit/Markov/KState.cs index f0341ff..71ff54f 100644 --- a/src/Sandwych.MapMatchingKit/Markov/KState.cs +++ b/src/Sandwych.MapMatchingKit/Markov/KState.cs @@ -25,7 +25,7 @@ private readonly struct SequenceEntry public TSample Sample { get; } public TCandidate EstimatedCandidate { get; } - public SequenceEntry(ICollection candidates, in TSample sample, in TCandidate estimated) + public SequenceEntry(ICollection candidates, in TSample sample, TCandidate estimated) { this.Candidates = candidates; this.Sample = sample; @@ -217,7 +217,7 @@ public ICollection Vector() } else { - return _sequence[_sequence.Count - 1].Candidates; + return _sequence.PeekLast().Candidates; } } diff --git a/src/Sandwych.MapMatchingKit/Matching/Matcher.cs b/src/Sandwych.MapMatchingKit/Matching/Matcher.cs index 127f2d9..3d61bd0 100644 --- a/src/Sandwych.MapMatchingKit/Matching/Matcher.cs +++ b/src/Sandwych.MapMatchingKit/Matching/Matcher.cs @@ -122,16 +122,7 @@ public override IReadOnlyCollection ComputeCandidates( foreach (var point in points) { double dz = _spatial.Distance(sample.Coordinate, point.Coordinate); - double emission = 1 / _sqrt_2pi_sig2 * Math.Exp((-1) * dz * dz / (2 * _sig2)); - if (!double.IsNaN(sample.Azimuth)) - { - double da = sample.Azimuth > point.Azimuth - ? Math.Min(sample.Azimuth - point.Azimuth, - 360 - (sample.Azimuth - point.Azimuth)) - : Math.Min(point.Azimuth - sample.Azimuth, - 360 - (point.Azimuth - sample.Azimuth)); - emission *= Math.Max(1E-2, 1 / _sqrt_2pi_sigA * Math.Exp((-1) * da / (2 * _sigA))); - } + double emission = this.ComputeEmissionProbability(sample, point, dz); var candidate = new MatcherCandidate(sample, point); candidates.Add(new CandidateProbability(candidate, emission)); @@ -189,5 +180,22 @@ public override IDictionary candidates.Azimuth + ? Math.Min(sample.Azimuth - candidates.Azimuth, + 360 - (sample.Azimuth - candidates.Azimuth)) + : Math.Min(candidates.Azimuth - sample.Azimuth, + 360 - (candidates.Azimuth - sample.Azimuth)); + emission *= Math.Max(1E-2, 1 / _sqrt_2pi_sigA * Math.Exp((-1) * da / (2 * _sigA))); + } + + return emission; + } } } diff --git a/src/Sandwych.MapMatchingKit/Matching/MatcherSample.cs b/src/Sandwych.MapMatchingKit/Matching/MatcherSample.cs index 4d99192..8f52163 100644 --- a/src/Sandwych.MapMatchingKit/Matching/MatcherSample.cs +++ b/src/Sandwych.MapMatchingKit/Matching/MatcherSample.cs @@ -19,6 +19,7 @@ namespace Sandwych.MapMatchingKit.Matching public float Azimuth { get; } public Coordinate2D Coordinate { get; } public bool IsNaN => this.Id < 0; + public bool HasAzimuth => !float.IsNaN(this.Azimuth); public MatcherSample(long id, long time, double lng, double lat, float azimuth = float.NaN) { diff --git a/src/Sandwych.MapMatchingKit/Spatial/GeographySpatialOperation.cs b/src/Sandwych.MapMatchingKit/Spatial/GeographySpatialOperation.cs index a1006a7..8539fe0 100644 --- a/src/Sandwych.MapMatchingKit/Spatial/GeographySpatialOperation.cs +++ b/src/Sandwych.MapMatchingKit/Spatial/GeographySpatialOperation.cs @@ -104,9 +104,10 @@ public double Intercept(ILineString p, in Coordinate2D c) { var b = p.GetCoordinateN(i).ToCoordinate2D(); - ds = this.Distance(a, b); + var interceptTuple = this.InterceptInternal(a, b, c); + ds = interceptTuple.Distance; + var f_ = interceptTuple.Fraction; - var f_ = this.Intercept(a, b, c); f_ = (f_ > 1) ? 1 : (f_ < 0) ? 0 : f_; var x = this.Interpolate(a, b, f_); double d_ = this.Distance(c, x); @@ -123,25 +124,12 @@ public double Intercept(ILineString p, in Coordinate2D c) return s == 0 ? 0 : sf / s; } - public double Intercept(in Coordinate2D a, in Coordinate2D b, in Coordinate2D c) - { - if (a.X == b.X && a.Y == b.Y) - { - return 0; - } - var inter = new GeodesicInterception(Geodesic.WGS84); - var ci = inter.Intercept(a.Y, a.X, b.Y, b.X, c.Y, c.X); - var ai = Geodesic.WGS84.Inverse(a.Y, a.X, ci.lat2, ci.lon2); - var ab = Geodesic.WGS84.Inverse(a.Y, a.X, b.Y, b.X); - return (Math.Abs(ai.azi1 - ab.azi1) < 1) ? ai.s12 / ab.s12 : (-1) * ai.s12 / ab.s12; - } + public double Intercept(in Coordinate2D a, in Coordinate2D b, in Coordinate2D c) => + this.InterceptInternal(a, b, c).Fraction; + + public Coordinate2D Interpolate(in Coordinate2D a, in Coordinate2D b, double f) => + this.InterpolateInternal(a, b, f).Point; - public Coordinate2D Interpolate(in Coordinate2D a, in Coordinate2D b, double f) - { - var inv = Geodesic.WGS84.Inverse(a.Y, a.X, b.Y, b.X); - var pos = Geodesic.WGS84.Line(inv.lat1, inv.lon1, inv.azi1).Position(inv.s12 * f); - return new Coordinate2D(pos.lon2, pos.lat2); - } public Coordinate2D Interpolate(ILineString path, double f) => this.Interpolate(path, this.Length(path), f); @@ -178,13 +166,14 @@ public Coordinate2D Interpolate(ILineString path, double l, double f) return this.Interpolate(a, b, (d - s) / ds); } - s = s + ds; + s += ds; a = b; } return Coordinate2D.NaN; } + public double Length(ILineString line) { var d = 0D; @@ -195,8 +184,31 @@ public double Length(ILineString line) return d; } + public double Length(IMultiLineString line) => line.Geometries.Cast().Sum(x => this.Length(x)); + + private (Coordinate2D Point, double Distance) InterpolateInternal(in Coordinate2D a, in Coordinate2D b, double f) + { + var inv = Geodesic.WGS84.Inverse(a.Y, a.X, b.Y, b.X); + var pos = Geodesic.WGS84.Line(inv.lat1, inv.lon1, inv.azi1).Position(inv.s12 * f); + return (new Coordinate2D(pos.lon2, pos.lat2), inv.s12 * f); + } + + private (double Distance, double Fraction) InterceptInternal(in Coordinate2D a, in Coordinate2D b, in Coordinate2D c) + { + if (a.X == b.X && a.Y == b.Y) + { + return (0D, 0D); + } + var inter = new GeodesicInterception(Geodesic.WGS84); + var ci = inter.Intercept(a.Y, a.X, b.Y, b.X, c.Y, c.X); + var ai = Geodesic.WGS84.Inverse(a.Y, a.X, ci.lat2, ci.lon2); + var ab = Geodesic.WGS84.Inverse(a.Y, a.X, b.Y, b.X); + var fraction = (Math.Abs(ai.azi1 - ab.azi1) < 1) ? ai.s12 / ab.s12 : (-1) * ai.s12 / ab.s12; + return (ab.s12, fraction); + } + } } diff --git a/src/Sandwych.MapMatchingKit/Spatial/Index/AbstractSpatialIndex.cs b/src/Sandwych.MapMatchingKit/Spatial/Index/AbstractSpatialIndex.cs index 8ec6d9b..51d5571 100644 --- a/src/Sandwych.MapMatchingKit/Spatial/Index/AbstractSpatialIndex.cs +++ b/src/Sandwych.MapMatchingKit/Spatial/Index/AbstractSpatialIndex.cs @@ -12,7 +12,6 @@ public abstract class AbstractSpatialIndex : ISpatialIndex protected ISpatialOperation Spatial { get; } protected Func ItemGeometryGetter { get; } protected Func ItemLengthGetter { get; } - public AbstractSpatialIndex(IEnumerable items, ISpatialOperation spatialService, Func geometryGetter, Func lengthGetter) { @@ -22,9 +21,9 @@ public AbstractSpatialIndex(IEnumerable items, ISpatialOperation spatialS this.AddRange(items); } - public virtual IEnumerable<(TItem, double)> Radius(in Coordinate2D c, double radius, int k = -1) + public virtual IEnumerable<(TItem Item, double Distance)> Radius(in Coordinate2D c, double radius, int k = -1) { - var neighbors = new List<(TItem, double)>(16); + var neighbors = new List<(TItem Item, double Distance)>(20); var env = this.Spatial.Envelope(c, radius); var candidates = this.Search(env); foreach (var candidate in candidates) @@ -34,7 +33,7 @@ public AbstractSpatialIndex(IEnumerable items, ISpatialOperation spatialS var p = this.Spatial.Interpolate(geometry, this.ItemLengthGetter(candidate), f); var d = this.Spatial.Distance(p, c); - if (d < radius) + if (d <= radius) { neighbors.Add((candidate, f)); } @@ -42,7 +41,7 @@ public AbstractSpatialIndex(IEnumerable items, ISpatialOperation spatialS if (k > 0) { - return neighbors.OrderBy(i => i.Item2).Take(k); + return neighbors.OrderBy(i => i.Distance).Take(k); } else { diff --git a/src/Sandwych.MapMatchingKit/Spatial/Index/ISpatialIndex.cs b/src/Sandwych.MapMatchingKit/Spatial/Index/ISpatialIndex.cs index 22af771..d179899 100644 --- a/src/Sandwych.MapMatchingKit/Spatial/Index/ISpatialIndex.cs +++ b/src/Sandwych.MapMatchingKit/Spatial/Index/ISpatialIndex.cs @@ -17,6 +17,6 @@ public interface ISpatialIndex /// Radius in meters /// maximum number of candidates /// Result set of object(s) that are within a the given radius or overlap the radius, limited by k. - IEnumerable<(TItem, double)> Radius(in Coordinate2D c, double radius, int k = -1); + IEnumerable<(TItem Item, double Distance)> Radius(in Coordinate2D c, double radius, int k = -1); } } From dbc7a5bbcd05d5f74ea188b2d83d795fadf05618 Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Thu, 8 Mar 2018 00:53:17 +0800 Subject: [PATCH 25/37] refactor --- Sandwych.MapMatchingKit.sln | 3 + .../SpatialIndexBenchmark.cs | 12 ++-- .../Program.cs | 4 +- .../Matching/IMatcherSample.cs | 17 +++++ .../Matching/MatcherCandidate.cs | 2 +- .../Matching/MatcherSample.cs | 8 +++ src/Sandwych.MapMatchingKit/Roads/Costs.cs | 2 +- src/Sandwych.MapMatchingKit/Roads/RoadMap.cs | 8 +-- .../Roads/RoadPoint.cs | 11 ++- src/Sandwych.MapMatchingKit/Roads/Route.cs | 9 ++- .../Spatial/Geometries/Coordinate2D.cs | 5 +- .../Geometries/Coordinate2DExtensions.cs | 4 +- .../Spatial/Geometries/ICoordinate2D.cs | 2 +- .../Spatial/Geometries/Vector3D.cs | 9 +-- .../Spatial/Index/AbstractSpatialIndex.cs | 6 +- .../Spatial/Index/ISpatialIndex.cs | 2 +- .../Topology/DijkstraRouter.cs | 12 ++-- src/Sandwych.MapMatchingKit/Topology/IPath.cs | 2 +- .../PrecomputedDijkstraRouter.cs | 55 ++++++++------ .../PrecomputedDijkstraTable.cs | 71 ++++++++----------- .../Topology/RouteMark.cs | 8 ++- .../Utility/HashCodeHelper.cs | 65 +++++++++++++++++ .../PrecomputedDijkstraTableTest.cs | 10 +-- 23 files changed, 216 insertions(+), 111 deletions(-) create mode 100644 src/Sandwych.MapMatchingKit/Matching/IMatcherSample.cs create mode 100644 src/Sandwych.MapMatchingKit/Utility/HashCodeHelper.cs diff --git a/Sandwych.MapMatchingKit.sln b/Sandwych.MapMatchingKit.sln index 39e3e3f..f39664a 100644 --- a/Sandwych.MapMatchingKit.sln +++ b/Sandwych.MapMatchingKit.sln @@ -89,4 +89,7 @@ Global GlobalSection(Performance) = preSolution HasPerformanceSessions = true EndGlobalSection + GlobalSection(Performance) = preSolution + HasPerformanceSessions = true + EndGlobalSection EndGlobal diff --git a/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/SpatialIndexBenchmark.cs b/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/SpatialIndexBenchmark.cs index c22b197..8cbf5f1 100644 --- a/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/SpatialIndexBenchmark.cs +++ b/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/SpatialIndexBenchmark.cs @@ -53,21 +53,21 @@ public void Setup() } [Benchmark] - public void NtsSTRTreeBenchmark() + public int NtsSTRTreeBenchmark() { - this.DoRadius(_ntsRtreeIndex); + return this.DoRadius(_ntsRtreeIndex); } [Benchmark(Baseline = true)] - public void NtsQuadTreeBenchmark() + public int NtsQuadTreeBenchmark() { - this.DoRadius(_ntsQuadtreeIndex); + return this.DoRadius(_ntsQuadtreeIndex); } [Benchmark] - public void RBushRtreeBenchmark() + public int RBushRtreeBenchmark() { - this.DoRadius(_rbushIndex); + return this.DoRadius(_rbushIndex); } private int DoRadius(ISpatialIndex index) diff --git a/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs b/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs index 8257e16..96aa284 100644 --- a/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs +++ b/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Program.cs @@ -31,8 +31,8 @@ static void Main(string[] args) Console.WriteLine("The road map has been loaded"); - var router = new PrecomputedDijkstraRouter(map, Costs.TimePriorityCost, Costs.DistanceCost, 1000D); - //var router = new DijkstraRouter(); + //var router = new PrecomputedDijkstraRouter(map, Costs.TimePriorityCost, Costs.DistanceCost, 1000D); + var router = new DijkstraRouter(); var matcher = new Matcher( map, router, Costs.TimePriorityCost, spatial); diff --git a/src/Sandwych.MapMatchingKit/Matching/IMatcherSample.cs b/src/Sandwych.MapMatchingKit/Matching/IMatcherSample.cs new file mode 100644 index 0000000..58df0b7 --- /dev/null +++ b/src/Sandwych.MapMatchingKit/Matching/IMatcherSample.cs @@ -0,0 +1,17 @@ +using Sandwych.MapMatchingKit.Markov; +using Sandwych.MapMatchingKit.Spatial.Geometries; +using System; +using System.Collections.Generic; +using System.Text; + +namespace Sandwych.MapMatchingKit.Matching +{ + public interface IMatcherSample : ISample + { + long Id { get; } + float Azimuth { get; } + Coordinate2D Coordinate { get; } + bool IsNaN { get; } + bool HasAzimuth { get; } + } +} diff --git a/src/Sandwych.MapMatchingKit/Matching/MatcherCandidate.cs b/src/Sandwych.MapMatchingKit/Matching/MatcherCandidate.cs index 43a5f09..35d65d9 100644 --- a/src/Sandwych.MapMatchingKit/Matching/MatcherCandidate.cs +++ b/src/Sandwych.MapMatchingKit/Matching/MatcherCandidate.cs @@ -17,6 +17,6 @@ public MatcherCandidate(in MatcherSample sample, in RoadPoint point) : base(samp this._point = point; } - public override int GetHashCode() => this.Point.GetHashCode(); + public override int GetHashCode() => Point.GetHashCode(); } } diff --git a/src/Sandwych.MapMatchingKit/Matching/MatcherSample.cs b/src/Sandwych.MapMatchingKit/Matching/MatcherSample.cs index 8f52163..b7191ba 100644 --- a/src/Sandwych.MapMatchingKit/Matching/MatcherSample.cs +++ b/src/Sandwych.MapMatchingKit/Matching/MatcherSample.cs @@ -45,6 +45,14 @@ public MatcherSample(long id, DateTimeOffset time, in Coordinate2D point, float this.Azimuth = NormAzimuth(azimuth); } + public MatcherSample(long id, DateTimeOffset time, double x, double y, float azimuth = float.NaN) + { + this.Id = id; + this.Time = time; + this.Coordinate = new Coordinate2D(x, y); + this.Azimuth = NormAzimuth(azimuth); + } + private static float NormAzimuth(float azimuth) => azimuth >= 360f ? azimuth - (360f * (int)(azimuth / 360f)) : azimuth < 0f ? azimuth - (360f * ((int)(azimuth / 360f) - 1f)) : azimuth; diff --git a/src/Sandwych.MapMatchingKit/Roads/Costs.cs b/src/Sandwych.MapMatchingKit/Roads/Costs.cs index ed68838..ceb9991 100644 --- a/src/Sandwych.MapMatchingKit/Roads/Costs.cs +++ b/src/Sandwych.MapMatchingKit/Roads/Costs.cs @@ -16,7 +16,7 @@ public static class Costs public static double TimePriorityCost(Road road) => TimeCost(road) * Math.Max(HuristicPriority, road.Priority); - public static double Cost(this TEdge edge, double fraction, Func costFunc) + public static double ComputeCost(this TEdge edge, double fraction, Func costFunc) where TEdge : IGraphEdge => costFunc(edge) * fraction; } diff --git a/src/Sandwych.MapMatchingKit/Roads/RoadMap.cs b/src/Sandwych.MapMatchingKit/Roads/RoadMap.cs index 3522640..c15fc75 100644 --- a/src/Sandwych.MapMatchingKit/Roads/RoadMap.cs +++ b/src/Sandwych.MapMatchingKit/Roads/RoadMap.cs @@ -35,19 +35,19 @@ public RoadMap(IEnumerable roads, ISpatialOperation spatial) : base(roads) this.Index = new RtreeIndex(roads.Select(x => x.RoadInfo), spatial, r => r.Geometry, r => r.Length); } - private IEnumerable Split(IEnumerable<(RoadInfo road, double fraction)> points) + private IEnumerable Split(IEnumerable<(RoadInfo Item, double Fraction, Coordinate2D InterpolatedPoint)> points) { /* * This uses the road */ foreach (var point in points) { - yield return new RoadPoint(this.EdgeMap[point.road.Id * 2], point.fraction, _spatial); + yield return new RoadPoint(this.EdgeMap[point.Item.Id * 2], point.Fraction, point.InterpolatedPoint, _spatial); - var backwardRoadId = point.road.Id * 2 + 1; + var backwardRoadId = point.Item.Id * 2 + 1; if (this.EdgeMap.TryGetValue(backwardRoadId, out var road)) { - yield return new RoadPoint(road, 1.0 - point.fraction, _spatial); + yield return new RoadPoint(road, 1.0 - point.Fraction, point.InterpolatedPoint, _spatial); } } } diff --git a/src/Sandwych.MapMatchingKit/Roads/RoadPoint.cs b/src/Sandwych.MapMatchingKit/Roads/RoadPoint.cs index 8d67abf..543c343 100644 --- a/src/Sandwych.MapMatchingKit/Roads/RoadPoint.cs +++ b/src/Sandwych.MapMatchingKit/Roads/RoadPoint.cs @@ -5,6 +5,7 @@ using GeoAPI.Geometries; using Sandwych.MapMatchingKit.Spatial; using Sandwych.MapMatchingKit.Spatial.Geometries; +using Sandwych.MapMatchingKit.Utility; namespace Sandwych.MapMatchingKit.Roads { @@ -26,6 +27,14 @@ public RoadPoint(in Road road, double fraction, float azimuth, ISpatialOperation this.Coordinate = spatial.Interpolate(this.Edge.Geometry, this.Fraction); } + public RoadPoint(in Road road, double fraction, in Coordinate2D coordinate, ISpatialOperation spatial) + { + this.Edge = road; + this.Fraction = fraction; + this.Coordinate = coordinate; + this.Azimuth = (float)spatial.Azimuth(road.Geometry, fraction); + } + public RoadPoint(in Road road, double fraction, float azimuth) : this(road, fraction, azimuth, GeographySpatialOperation.Instance) { } @@ -44,7 +53,7 @@ public RoadPoint(in Road road, double fraction) : this(road, fraction, Geography } public override int GetHashCode() => - (this.Edge, this.Fraction).GetHashCode(); + HashCodeHelper.Combine(Edge.GetHashCode(), Fraction.GetHashCode()); public bool Equals(RoadPoint other) => diff --git a/src/Sandwych.MapMatchingKit/Roads/Route.cs b/src/Sandwych.MapMatchingKit/Roads/Route.cs index 31f98b4..60d1713 100644 --- a/src/Sandwych.MapMatchingKit/Roads/Route.cs +++ b/src/Sandwych.MapMatchingKit/Roads/Route.cs @@ -51,14 +51,14 @@ private static IEnumerable GetEdges(RoadPoint startPoint, RoadPoint endPoi public double Cost(Func costFunc) { - var value = Costs.Cost(this.StartPoint.Edge, 1.0 - this.StartPoint.Fraction, costFunc); + var value = Costs.ComputeCost(this.StartPoint.Edge, 1.0 - this.StartPoint.Fraction, costFunc); foreach (var e in _edges) { value += costFunc(e); } - value -= Costs.Cost(this.EndPoint.Edge, 1.0 - this.EndPoint.Fraction, costFunc); + value -= Costs.ComputeCost(this.EndPoint.Edge, 1.0 - this.EndPoint.Fraction, costFunc); return value; } @@ -72,6 +72,11 @@ public ILineString ToGeometry() public bool Equals(Route other) { + if (ReferenceEquals(this, other)) + { + return true; + } + if (!this.StartPoint.Equals(other.StartPoint)) { return false; diff --git a/src/Sandwych.MapMatchingKit/Spatial/Geometries/Coordinate2D.cs b/src/Sandwych.MapMatchingKit/Spatial/Geometries/Coordinate2D.cs index d4a20cd..60c93ee 100644 --- a/src/Sandwych.MapMatchingKit/Spatial/Geometries/Coordinate2D.cs +++ b/src/Sandwych.MapMatchingKit/Spatial/Geometries/Coordinate2D.cs @@ -6,6 +6,7 @@ using System.Runtime.InteropServices; using GeoAPI.Geometries; using System.Text; +using Sandwych.MapMatchingKit.Utility; namespace Sandwych.MapMatchingKit.Spatial.Geometries { @@ -150,8 +151,8 @@ public double this[int index] } [MethodImpl(MethodImplOptions.AggressiveInlining)] - public override int GetHashCode() => - (X, Y).GetHashCode(); + public override int GetHashCode() => + HashCodeHelper.Combine(X.GetHashCode(), Y.GetHashCode()); [MethodImpl(MethodImplOptions.AggressiveInlining)] public double[] ToArray() => new double[2] { this.X, this.Y }; diff --git a/src/Sandwych.MapMatchingKit/Spatial/Geometries/Coordinate2DExtensions.cs b/src/Sandwych.MapMatchingKit/Spatial/Geometries/Coordinate2DExtensions.cs index b613336..271fa52 100644 --- a/src/Sandwych.MapMatchingKit/Spatial/Geometries/Coordinate2DExtensions.cs +++ b/src/Sandwych.MapMatchingKit/Spatial/Geometries/Coordinate2DExtensions.cs @@ -7,10 +7,10 @@ namespace Sandwych.MapMatchingKit.Spatial.Geometries { public static class Coordinate2DExtensions { - public static GeoAPI.Geometries.Coordinate ToGeoAPICoordinate(this Coordinate2D self) => + public static GeoAPI.Geometries.Coordinate ToGeoAPICoordinate(this in Coordinate2D self) => new GeoAPI.Geometries.Coordinate(self.X, self.Y); - public static GeoAPI.Geometries.IPoint ToGeoAPIPoint(this Coordinate2D self) => + public static GeoAPI.Geometries.IPoint ToGeoAPIPoint(this in Coordinate2D self) => new Point(self.X, self.Y); } } diff --git a/src/Sandwych.MapMatchingKit/Spatial/Geometries/ICoordinate2D.cs b/src/Sandwych.MapMatchingKit/Spatial/Geometries/ICoordinate2D.cs index 5471e38..55cda72 100644 --- a/src/Sandwych.MapMatchingKit/Spatial/Geometries/ICoordinate2D.cs +++ b/src/Sandwych.MapMatchingKit/Spatial/Geometries/ICoordinate2D.cs @@ -15,7 +15,7 @@ public interface ICoordinate2D : IComparable public static class ICoordinate2DExtensions { - public static int CompareTo(this T self, T other) + public static int CompareTo(this T self, in T other) where T : ICoordinate2D { if (self.X < other.X) diff --git a/src/Sandwych.MapMatchingKit/Spatial/Geometries/Vector3D.cs b/src/Sandwych.MapMatchingKit/Spatial/Geometries/Vector3D.cs index 97893f5..a6115dc 100644 --- a/src/Sandwych.MapMatchingKit/Spatial/Geometries/Vector3D.cs +++ b/src/Sandwych.MapMatchingKit/Spatial/Geometries/Vector3D.cs @@ -1,4 +1,5 @@ -using System; +using Sandwych.MapMatchingKit.Utility; +using System; using System.Collections.Generic; using System.Runtime.CompilerServices; using System.Text; @@ -15,14 +16,14 @@ namespace Sandwych.MapMatchingKit.Spatial.Geometries public static Vector3D Zero => new Vector3D(0D, 0D, 0D); public static Vector3D One => new Vector3D(1D, 1D, 1D); - public Vector3D(double x, double y, double z) + public Vector3D(double x, double y, double z) : this() { this.X = x; this.Y = y; this.Z = z; } - public Vector3D(double[] array) + public Vector3D(double[] array) : this() { if (array == null) { @@ -101,7 +102,7 @@ public double this[int index] } [MethodImpl(MethodImplOptions.AggressiveInlining)] - public override int GetHashCode() => (X, Y, Z).GetHashCode(); + public override int GetHashCode() => HashCodeHelper.Combine(X.GetHashCode(), Y.GetHashCode(), Z.GetHashCode()); [MethodImpl(MethodImplOptions.AggressiveInlining)] public double[] ToArray() => new double[3] { X, Y, Z }; diff --git a/src/Sandwych.MapMatchingKit/Spatial/Index/AbstractSpatialIndex.cs b/src/Sandwych.MapMatchingKit/Spatial/Index/AbstractSpatialIndex.cs index 51d5571..7594102 100644 --- a/src/Sandwych.MapMatchingKit/Spatial/Index/AbstractSpatialIndex.cs +++ b/src/Sandwych.MapMatchingKit/Spatial/Index/AbstractSpatialIndex.cs @@ -21,9 +21,9 @@ public AbstractSpatialIndex(IEnumerable items, ISpatialOperation spatialS this.AddRange(items); } - public virtual IEnumerable<(TItem Item, double Distance)> Radius(in Coordinate2D c, double radius, int k = -1) + public virtual IEnumerable<(TItem Item, double Distance, Coordinate2D InterpolatedPoint)> Radius(in Coordinate2D c, double radius, int k = -1) { - var neighbors = new List<(TItem Item, double Distance)>(20); + var neighbors = new List<(TItem Item, double Distance, Coordinate2D InterpolatedPoint)>(20); var env = this.Spatial.Envelope(c, radius); var candidates = this.Search(env); foreach (var candidate in candidates) @@ -35,7 +35,7 @@ public AbstractSpatialIndex(IEnumerable items, ISpatialOperation spatialS if (d <= radius) { - neighbors.Add((candidate, f)); + neighbors.Add((candidate, f, p)); } } diff --git a/src/Sandwych.MapMatchingKit/Spatial/Index/ISpatialIndex.cs b/src/Sandwych.MapMatchingKit/Spatial/Index/ISpatialIndex.cs index d179899..57c8351 100644 --- a/src/Sandwych.MapMatchingKit/Spatial/Index/ISpatialIndex.cs +++ b/src/Sandwych.MapMatchingKit/Spatial/Index/ISpatialIndex.cs @@ -17,6 +17,6 @@ public interface ISpatialIndex /// Radius in meters /// maximum number of candidates /// Result set of object(s) that are within a the given radius or overlap the radius, limited by k. - IEnumerable<(TItem Item, double Distance)> Radius(in Coordinate2D c, double radius, int k = -1); + IEnumerable<(TItem Item, double Distance, Coordinate2D InterpolatedPoint)> Radius(in Coordinate2D c, double radius, int k = -1); } } diff --git a/src/Sandwych.MapMatchingKit/Topology/DijkstraRouter.cs b/src/Sandwych.MapMatchingKit/Topology/DijkstraRouter.cs index fd76be0..2f3b465 100644 --- a/src/Sandwych.MapMatchingKit/Topology/DijkstraRouter.cs +++ b/src/Sandwych.MapMatchingKit/Topology/DijkstraRouter.cs @@ -84,8 +84,8 @@ private IReadOnlyDictionary> Ssmt(P source, IEnumerable

foreach (var source in sources) { // initialize sources as start edges - var startcost = source.Edge.Cost(1.0 - source.Fraction, cost); //cost.cost(source.Edge, 1 - source.Fraction); - var startbound = bound != null ? source.Edge.Cost(1.0 - source.Fraction, bound) : 0D; //bound.cost(source.Edge.Cost(), 1 - source.Fraction) : 0.0; + var startcost = source.Edge.ComputeCost(1.0 - source.Fraction, cost); //cost.cost(source.Edge, 1 - source.Fraction); + var startbound = bound != null ? source.Edge.ComputeCost(1.0 - source.Fraction, bound) : 0D; //bound.cost(source.Edge.Cost(), 1 - source.Fraction) : 0.0; if (this.Logger.IsEnabled(LogLevel.Debug)) { @@ -103,8 +103,8 @@ private IReadOnlyDictionary> Ssmt(P source, IEnumerable

{ continue; } - var reachcost = startcost - source.Edge.Cost(1.0 - target.Fraction, cost); // cost.cost(source.Edge, 1 - target.Fraction); - var reachbound = bound != null ? startcost - source.Edge.Cost(1.0 - target.Fraction, bound) : 0D; //, // bound.cost(source.Edge, 1 - target.Fraction) : 0.0; + var reachcost = startcost - source.Edge.ComputeCost(1.0 - target.Fraction, cost); // cost.cost(source.Edge, 1 - target.Fraction); + var reachbound = bound != null ? startcost - source.Edge.ComputeCost(1.0 - target.Fraction, bound) : 0D; //, // bound.cost(source.Edge, 1 - target.Fraction) : 0.0; if (this.Logger.IsEnabled(LogLevel.Debug)) { @@ -223,8 +223,8 @@ private IReadOnlyDictionary> Ssmt(P source, IEnumerable

// reach target edge foreach (var targetEdge in targetEdges[successor]) { - var reachcost = succcost - successor.Cost(1.0 - targetEdge.Fraction, cost); - var reachbound = bound != null ? succbound - successor.Cost(1.0 - targetEdge.Fraction, bound) : 0.0; /// bound(successor, 1 - target.Fraction) : 0.0; + var reachcost = succcost - successor.ComputeCost(1.0 - targetEdge.Fraction, cost); + var reachbound = bound != null ? succbound - successor.ComputeCost(1.0 - targetEdge.Fraction, bound) : 0.0; /// bound(successor, 1 - target.Fraction) : 0.0; if (this.Logger.IsEnabled(LogLevel.Debug)) { this.Logger.LogDebug("reached target {0} with successor edge {1} and fraction {2} with {3} cost", diff --git a/src/Sandwych.MapMatchingKit/Topology/IPath.cs b/src/Sandwych.MapMatchingKit/Topology/IPath.cs index 42917b6..22639bf 100644 --- a/src/Sandwych.MapMatchingKit/Topology/IPath.cs +++ b/src/Sandwych.MapMatchingKit/Topology/IPath.cs @@ -6,7 +6,7 @@ namespace Sandwych.MapMatchingKit.Topology { public interface IPath where TEdge : IGraphEdge - where TPoint : struct, IEdgePoint + where TPoint : IEdgePoint { ref readonly TPoint StartPoint { get; } ref readonly TPoint EndPoint { get; } diff --git a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouter.cs b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouter.cs index 79de075..73dc067 100644 --- a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouter.cs +++ b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraRouter.cs @@ -59,8 +59,8 @@ public IEnumerable Route(P source, P target, Func cost, Fu if (bound != null && !double.IsNaN(max)) { var boundingDistance = edges.Sum(bound); - boundingDistance -= source.Edge.Cost(source.Fraction, bound); - boundingDistance -= target.Edge.Cost(1D - target.Fraction, bound); + boundingDistance -= source.Edge.ComputeCost(source.Fraction, bound); + boundingDistance -= target.Edge.ComputeCost(1D - target.Fraction, bound); if (boundingDistance > max) { return EmptyPath; @@ -78,37 +78,23 @@ public IEnumerable Route(P source, P target, Func cost, Fu private IEnumerable RouteInternal( P source, P target, Func cost, Func bound = null, double max = Double.NaN) { + IEnumerable edges = EmptyPath; //On same road && forward if (source.Edge.Equals(target.Edge) && source.Fraction <= target.Fraction) { - yield return source.Edge; - yield break; + edges = GetPathOnSameRoad(source.Edge); } else if (source.Edge.Target.Equals(target.Edge.Source)) //is neighborhood { - yield return source.Edge; - yield return target.Edge; - yield break; + edges = GetPathOnNeighborhoodRoad(source.Edge, target.Edge); } - - IEnumerable GetPath() + else { - yield return source.Edge; - var foundPath = _precomputedTable.GetPathByVertex(source.Edge.Target, target.Edge.Source); - foreach (var edge in foundPath) - { - yield return edge; - } - yield return target.Edge; + var t = _precomputedTable.GetPathByVertex(source.Edge.Target, target.Edge.Source); + return CombineHeadTailEdges(source.Edge, target.Edge, t.Path); } - IEnumerable edges = EmptyPath; - edges = GetPath(); - - foreach (var edge in edges) - { - yield return edge; - } + return edges; } private PrecomputedDijkstraTable CreateTable() @@ -118,6 +104,29 @@ private PrecomputedDijkstraTable CreateTable() return new PrecomputedDijkstraTable(rows); } + private static IEnumerable GetPathOnSameRoad(TEdge sourceEdge) + { + yield return sourceEdge; + yield break; + } + + private static IEnumerable GetPathOnNeighborhoodRoad(TEdge sourceEdge, TEdge targetEdge) + { + yield return sourceEdge; + yield return targetEdge; + yield break; + } + + private static IEnumerable CombineHeadTailEdges(TEdge sourceEdge, TEdge targetEdge, IEnumerable bodyPath) + { + yield return sourceEdge; + foreach (var e in bodyPath) + { + yield return e; + } + yield return targetEdge; + } + } } diff --git a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTable.cs b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTable.cs index 7ce3fbf..1feff12 100644 --- a/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTable.cs +++ b/src/Sandwych.MapMatchingKit/Topology/PrecomputedDijkstra/PrecomputedDijkstraTable.cs @@ -11,6 +11,8 @@ public sealed class PrecomputedDijkstraTable : Dictionary<(TVert where TEdge : class, IEdge where TVertex : IEquatable { + private readonly static IEnumerable EmptyPath = new TEdge[] { }; + public PrecomputedDijkstraTable() : base() { @@ -58,63 +60,46 @@ public bool HasPathByEdge(TEdge sourceEdge, TEdge targetEdge) } } - public IEnumerable GetPathByEdge(TEdge sourceEdge, TEdge targetEdge) + public (IEnumerable Path, double Distance) GetPathByVertex(TVertex sourceVertex, TVertex targetVertex, double maxDistance = double.PositiveInfinity) { - if (IsSameEdge(sourceEdge, targetEdge)) + if (IsSameVertex(sourceVertex, targetVertex)) { - throw new InvalidOperationException(); + throw new ArgumentException(); } - else if (IsNeighbor(sourceEdge, targetEdge)) + + if (this.TryGetValue((sourceVertex, targetVertex), out var firstRow) && firstRow.Distance <= maxDistance) { - yield return sourceEdge; - yield return targetEdge; - yield break; + return (this.GetPathFrom(firstRow), firstRow.Distance); } else { - var sourceVertex = sourceEdge.Target; - var targetVertex = targetEdge.Source; - var path = this.GetPathByVertex(sourceVertex, targetVertex); - foreach (var edge in path) - { - yield return edge; - } + return (EmptyPath, double.NaN); } - } - public IEnumerable GetPathByVertex(TVertex sourceVertex, TVertex targetVertex) + private IEnumerable GetPathFrom(PrecomputedDijkstraTableRow startRow) { - if (IsSameVertex(sourceVertex, targetVertex)) + var row = startRow; + //now we got the first edge, then we started from the next row + yield return row.SourceEdge; + var currentStart = row.NextVertex; + var sourceVertex = startRow.SourceVertex; + var targetVertex = startRow.TargetVertex; + + while (!currentStart.Equals(targetVertex)) { - throw new ArgumentException(); - } - - if (this.TryGetValue((sourceVertex, targetVertex), out var row)) - { - //now we got the first edge, then we started from the next row - yield return row.SourceEdge; - var currentStart = row.NextVertex; - - while (!currentStart.Equals(targetVertex)) + if (this.TryGetValue((currentStart, targetVertex), out row)) { - if (this.TryGetValue((currentStart, targetVertex), out row)) - { - yield return row.SourceEdge; - currentStart = row.NextVertex; - } - else - { - var msg = string.Format( - "Bad precomputed Dijkstra path: [sourceVertex={0}, targetVertex={1}, currentVertex={2}]", - sourceVertex, targetVertex, currentStart); - throw new BadGraphPathException(msg); - } + yield return row.SourceEdge; + currentStart = row.NextVertex; + } + else + { + var msg = string.Format( + "Bad precomputed Dijkstra path: [sourceVertex={0}, targetVertex={1}, currentVertex={2}]", + sourceVertex, targetVertex, currentStart); + throw new BadGraphPathException(msg); } - } - else - { - yield break; } } diff --git a/src/Sandwych.MapMatchingKit/Topology/RouteMark.cs b/src/Sandwych.MapMatchingKit/Topology/RouteMark.cs index 61a6abb..29d5117 100644 --- a/src/Sandwych.MapMatchingKit/Topology/RouteMark.cs +++ b/src/Sandwych.MapMatchingKit/Topology/RouteMark.cs @@ -1,4 +1,5 @@ -using System; +using Sandwych.MapMatchingKit.Utility; +using System; using System.Collections.Generic; using System.Text; @@ -26,7 +27,7 @@ namespace Sandwych.MapMatchingKit.Topology /// Predecessor {@link AbstractEdge}. /// Cost value to this route mark. /// Bounding cost value to this route mark. - public RouteMark(TEdge markedEdge, TEdge predecessorEdge, Double cost, Double boundingCost) + public RouteMark(TEdge markedEdge, TEdge predecessorEdge, double cost, double boundingCost) { this.MarkedEdge = markedEdge; this.PredecessorEdge = predecessorEdge; @@ -56,7 +57,8 @@ public int CompareTo(RouteMark other) } public override int GetHashCode() => - (this.MarkedEdge, this.PredecessorEdge, this.Cost, this.BoundingCost).GetHashCode(); + PredecessorEdge != null ? HashCodeHelper.Combine(MarkedEdge.GetHashCode(), PredecessorEdge.GetHashCode(), Cost.GetHashCode()) + : HashCodeHelper.Combine(MarkedEdge.GetHashCode(), Cost.GetHashCode()); public bool Equals(RouteMark other) { diff --git a/src/Sandwych.MapMatchingKit/Utility/HashCodeHelper.cs b/src/Sandwych.MapMatchingKit/Utility/HashCodeHelper.cs new file mode 100644 index 0000000..50add87 --- /dev/null +++ b/src/Sandwych.MapMatchingKit/Utility/HashCodeHelper.cs @@ -0,0 +1,65 @@ +//From QuickGraph +//Licensed in MS-PL + +using System; +using System.Collections.Generic; +using System.Runtime.CompilerServices; +using System.Text; + +namespace Sandwych.MapMatchingKit.Utility +{ + public static class HashCodeHelper + { + const Int32 FNV1_prime_32 = 16777619; + const Int32 FNV1_basis_32 = unchecked((int)2166136261); + const Int64 FNV1_prime_64 = 1099511628211; + const Int64 FNV1_basis_64 = unchecked((int)14695981039346656037); + + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public static Int32 GetHashCode(Int64 x) + { + return Combine((Int32)x, (Int32)(((UInt64)x) >> 32)); + } + + [MethodImpl(MethodImplOptions.AggressiveInlining)] + private static Int32 Fold(Int32 hash, byte value) + { + return (hash * FNV1_prime_32) ^ (Int32)value; + } + + [MethodImpl(MethodImplOptions.AggressiveInlining)] + private static Int32 Fold(Int32 hash, Int32 value) + { + return Fold(Fold(Fold(Fold(hash, + (byte)value), + (byte)(((UInt32)value) >> 8)), + (byte)(((UInt32)value) >> 16)), + (byte)(((UInt32)value) >> 24)); + } + + ///

+ /// Combines two hashcodes in a strong way. + /// + /// + /// + /// + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public static Int32 Combine(Int32 x, Int32 y) + { + return Fold(Fold(FNV1_basis_32, x), y); + } + + /// + /// Combines three hashcodes in a strong way. + /// + /// + /// + /// + /// + [MethodImpl(MethodImplOptions.AggressiveInlining)] + public static Int32 Combine(Int32 x, Int32 y, Int32 z) + { + return Fold(Fold(Fold(FNV1_basis_32, x), y), z); + } + } +} diff --git a/test/Sandwych.MapMatchingKit.Tests/Topology/PrecomputedDijkstra/PrecomputedDijkstraTableTest.cs b/test/Sandwych.MapMatchingKit.Tests/Topology/PrecomputedDijkstra/PrecomputedDijkstraTableTest.cs index 21c8d95..4f2c6fe 100644 --- a/test/Sandwych.MapMatchingKit.Tests/Topology/PrecomputedDijkstra/PrecomputedDijkstraTableTest.cs +++ b/test/Sandwych.MapMatchingKit.Tests/Topology/PrecomputedDijkstra/PrecomputedDijkstraTableTest.cs @@ -27,14 +27,14 @@ public void TestGetPathByVertex(string sourceVertex, string targetVertex) var rows = generator.ComputeRows(MyGraph.GraphInstance, e => MyGraph.EdgeCosts[e], e => MyGraph.EdgeCosts[e], maxRadius); var table = new PrecomputedDijkstraTable>(rows); - var actualPath = table.GetPathByVertex(sourceVertex, targetVertex); - var actualDistance = actualPath.Sum(e => MyGraph.EdgeCosts[e]); + var t = table.GetPathByVertex(sourceVertex, targetVertex); + var actualDistance = t.Path.Sum(e => MyGraph.EdgeCosts[e]); Assert.True(naiveDijkstra.TryGetPath(targetVertex, out var expectedPath)); - Assert.NotNull(actualPath); - Assert.NotEmpty(actualPath); + Assert.NotNull(t.Path); + Assert.NotEmpty(t.Path); var expectedDistance = expectedPath.Sum(e => MyGraph.EdgeCosts[e]); - Assert.Equal(expectedPath, actualPath); + Assert.Equal(expectedPath, t.Path); Assert.Equal(expectedDistance, actualDistance, 8); } } From 9531097905a0c123620026353cb6872b5ff3fa9f Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Thu, 8 Mar 2018 00:59:42 +0800 Subject: [PATCH 26/37] add workaround for C# 7.2's (in this Type arg) --- .../Spatial/Geometries/Coordinate2DExtensions.cs | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-) diff --git a/src/Sandwych.MapMatchingKit/Spatial/Geometries/Coordinate2DExtensions.cs b/src/Sandwych.MapMatchingKit/Spatial/Geometries/Coordinate2DExtensions.cs index 271fa52..3778e7e 100644 --- a/src/Sandwych.MapMatchingKit/Spatial/Geometries/Coordinate2DExtensions.cs +++ b/src/Sandwych.MapMatchingKit/Spatial/Geometries/Coordinate2DExtensions.cs @@ -7,10 +7,13 @@ namespace Sandwych.MapMatchingKit.Spatial.Geometries { public static class Coordinate2DExtensions { - public static GeoAPI.Geometries.Coordinate ToGeoAPICoordinate(this in Coordinate2D self) => + //Add workaround for C# 7.2's bug + //(this in Coordinate2D self) + + public static GeoAPI.Geometries.Coordinate ToGeoAPICoordinate(in Coordinate2D self) => new GeoAPI.Geometries.Coordinate(self.X, self.Y); - public static GeoAPI.Geometries.IPoint ToGeoAPIPoint(this in Coordinate2D self) => + public static GeoAPI.Geometries.IPoint ToGeoAPIPoint(in Coordinate2D self) => new Point(self.X, self.Y); } } From cefd38e0a9fc5e92cd6a75ad3f993cb552e51093 Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Thu, 8 Mar 2018 10:07:26 +0800 Subject: [PATCH 27/37] revert last commit --- .../Spatial/Geometries/Coordinate2DExtensions.cs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/Sandwych.MapMatchingKit/Spatial/Geometries/Coordinate2DExtensions.cs b/src/Sandwych.MapMatchingKit/Spatial/Geometries/Coordinate2DExtensions.cs index 3778e7e..40bbe0d 100644 --- a/src/Sandwych.MapMatchingKit/Spatial/Geometries/Coordinate2DExtensions.cs +++ b/src/Sandwych.MapMatchingKit/Spatial/Geometries/Coordinate2DExtensions.cs @@ -10,10 +10,10 @@ public static class Coordinate2DExtensions //Add workaround for C# 7.2's bug //(this in Coordinate2D self) - public static GeoAPI.Geometries.Coordinate ToGeoAPICoordinate(in Coordinate2D self) => + public static GeoAPI.Geometries.Coordinate ToGeoAPICoordinate(this Coordinate2D self) => new GeoAPI.Geometries.Coordinate(self.X, self.Y); - public static GeoAPI.Geometries.IPoint ToGeoAPIPoint(in Coordinate2D self) => + public static GeoAPI.Geometries.IPoint ToGeoAPIPoint(this Coordinate2D self) => new Point(self.X, self.Y); } } From 7e7432556cb628ca9d281874d331564e3ad6af93 Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Thu, 8 Mar 2018 10:18:10 +0800 Subject: [PATCH 28/37] update apppveyor and travis scripts to use cake --- .travis.yml | 18 ++++++++++-------- appveyor.yml | 15 ++++++++------- 2 files changed, 18 insertions(+), 15 deletions(-) diff --git a/.travis.yml b/.travis.yml index 8f39690..aa2cdf5 100644 --- a/.travis.yml +++ b/.travis.yml @@ -2,8 +2,8 @@ language: csharp sudo: false mono: none dotnet: 2.1.4 +mono: 5.10.0 dist: trusty -solution: Sandwych.MapMatchingKit.sln env: global: @@ -18,11 +18,13 @@ branches: - /^.*-wip$/ - /^(.*\/)?ci-.*$/ -install: - - dotnet restore - script: - - dotnet build src/Sandwych.Hmm -f netstandard1.1 - - dotnet build src/Sandwych.MapMatchingKit -f netstandard2.0 - - dotnet test test/Sandwych.Hmm.Tests/Sandwych.Hmm.Tests.csproj - - dotnet test test/Sandwych.MapMatchingKit.Tests/Sandwych.MapMatchingKit.Tests.csproj + - ./build.sh "-target=Travis" + +cache: + directories: + - .packages + - tools + +notifications: + email: false diff --git a/appveyor.yml b/appveyor.yml index 6ddbc7c..aac67c3 100644 --- a/appveyor.yml +++ b/appveyor.yml @@ -1,23 +1,24 @@ image: Visual Studio 2017 init: - git config --global core.autocrlf true + install: - ps: $env:BuildNumber= $env:APPVEYOR_BUILD_NUMBER - ps: $env:DOTNET_SKIP_FIRST_TIME_EXPERIENCE = true - ps: $env:NUGET_XMLDOC_MODE = "skip" - ps: $env:DOTNET_CLI_TELEMETRY_OPTOUT = 1 + - ps: $env:CAKE_SETTINGS_SKIPVERIFICATION = true + build_script: - - dotnet --version - - dotnet restore - - dotnet build -c Release - - dotnet pack -c Release .\src\Sandwych.Hmm\Sandwych.Hmm.csproj - - dotnet pack -c Release .\src\Sandwych.MapMatchingKit\Sandwych.MapMatchingKit.csproj + - ps: .\build.ps1 -Target "Appveyor-Build" + test_script: - - dotnet test .\test\Sandwych.Hmm.Tests\Sandwych.Hmm.Tests.csproj - - dotnet test .\test\Sandwych.MapMatchingKit.Tests\Sandwych.MapMatchingKit.Tests.csproj + - ps: .\build.ps1 -Target "Appveyor-Test" + artifacts: - path: 'src\Sandwych.Hmm\**\*.nupkg' - path: 'src\Sandwych.MapMatchingKit\**\*.nupkg' + deploy: - provider: NuGet on: From cab14155390b78e79e1aa720f16473c4fa3010d0 Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Tue, 13 Mar 2018 12:55:09 +0800 Subject: [PATCH 29/37] update library --- ...andwych.MapMatchingKit.BenchmarkApp.csproj | 2 +- ...pMatchingKit.Examples.HelloWorldApp.csproj | 2 +- .../Markov/AbstractFilter.cs | 80 +++++++++--- .../Markov/CandidateProbability.cs | 18 --- .../Markov/HmmProbabilities.cs | 119 ------------------ src/Sandwych.MapMatchingKit/Markov/KState.cs | 4 +- .../Markov/SampleCandidates.cs | 8 ++ .../Markov/TransitionProbability.cs | 18 --- .../Matching/Matcher.cs | 44 +++---- .../Sandwych.MapMatchingKit.csproj | 2 +- .../Sandwych.Hmm.Tests.csproj | 2 +- .../Markov/FilterTest.cs | 18 +-- .../Matching/MatcherTest.cs | 14 ++- .../Sandwych.MapMatchingKit.Tests.csproj | 2 +- 14 files changed, 116 insertions(+), 217 deletions(-) delete mode 100644 src/Sandwych.MapMatchingKit/Markov/CandidateProbability.cs delete mode 100644 src/Sandwych.MapMatchingKit/Markov/HmmProbabilities.cs create mode 100644 src/Sandwych.MapMatchingKit/Markov/SampleCandidates.cs delete mode 100644 src/Sandwych.MapMatchingKit/Markov/TransitionProbability.cs diff --git a/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/Sandwych.MapMatchingKit.BenchmarkApp.csproj b/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/Sandwych.MapMatchingKit.BenchmarkApp.csproj index fd1b1e6..412bf9a 100644 --- a/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/Sandwych.MapMatchingKit.BenchmarkApp.csproj +++ b/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/Sandwych.MapMatchingKit.BenchmarkApp.csproj @@ -7,7 +7,7 @@ - + diff --git a/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Sandwych.MapMatchingKit.Examples.HelloWorldApp.csproj b/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Sandwych.MapMatchingKit.Examples.HelloWorldApp.csproj index 95d7d3e..ad8d1ee 100644 --- a/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Sandwych.MapMatchingKit.Examples.HelloWorldApp.csproj +++ b/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Sandwych.MapMatchingKit.Examples.HelloWorldApp.csproj @@ -6,7 +6,7 @@ - + diff --git a/src/Sandwych.MapMatchingKit/Markov/AbstractFilter.cs b/src/Sandwych.MapMatchingKit/Markov/AbstractFilter.cs index 3eaac7b..82db1c5 100644 --- a/src/Sandwych.MapMatchingKit/Markov/AbstractFilter.cs +++ b/src/Sandwych.MapMatchingKit/Markov/AbstractFilter.cs @@ -12,13 +12,61 @@ namespace Sandwych.MapMatchingKit.Markov /// Hidden Markov Model (HMM) filter for online and offline inference of states in a stochastic /// process. /// - /// Candidate inherits from {@link StateCandidate}. - /// Transition inherits from {@link StateTransition}. - /// Sample inherits from {@link Sample}. + /// Candidate implements . + /// Transition inherits from {@link Transition}. + /// Sample implements . public abstract class AbstractFilter : IFilter where TCandidate : class, IStateCandidate { + public readonly struct SampleCandidates + { + public TSample Sample { get; } + public IEnumerable Candidates { get; } + + public SampleCandidates(in TSample sample, IEnumerable candidates) + { + this.Sample = sample; + this.Candidates = candidates; + } + } + + public readonly struct SampleCandidate + { + public TSample Sample { get; } + public TCandidate Candidate { get; } + + public SampleCandidate(in TSample sample, TCandidate candidate) + { + this.Sample = sample; + this.Candidate = candidate; + } + } + + public readonly struct CandidateProbability + { + public TCandidate Candidate { get; } + public double Probability { get; } + + public CandidateProbability(TCandidate cand, double prob) + { + this.Candidate = cand; + this.Probability = prob; + } + } + + public readonly struct TransitionProbability + { + public TTransition Transition { get; } + public double Probability { get; } + + public TransitionProbability(TTransition transition, double prob) + { + this.Transition = transition; + this.Probability = prob; + } + } + public ILogger Logger { get; set; } = NullLogger.Instance; /// @@ -28,7 +76,7 @@ public abstract class AbstractFilter : /// Predecessor state candidate st-1. /// Measurement sample. /// Set of tuples consisting of a {@link StateCandidate} and its emission probability. - public abstract IReadOnlyCollection> ComputeCandidates(IEnumerable predecessors, in TSample sample); + public abstract IEnumerable ComputeCandidates(IEnumerable predecessors, in TSample sample); /// @@ -44,7 +92,7 @@ public abstract class AbstractFilter : /// st and its transition probability, or null if there is no /// transition. /// - public abstract TransitionProbability ComputeTransition(in (TSample, TCandidate) predecessor, in (TSample, TCandidate) candidate); + public abstract TransitionProbability ComputeTransition(in SampleCandidate predecessor, in SampleCandidate candidate); /// @@ -65,21 +113,21 @@ public abstract class AbstractFilter : /// all transitions from st-1 to st and its /// transition probability, or null if there no transition. /// - public virtual IDictionary>> ComputeTransitions( - in (TSample, IEnumerable) predecessors, in (TSample, IEnumerable) candidates) + public virtual IDictionary> ComputeTransitions( + in SampleCandidates predecessors, in SampleCandidates candidates) { - TSample sample = candidates.Item1; - TSample previous = predecessors.Item1; + TSample sample = candidates.Sample; + TSample previous = predecessors.Sample; - var map = new Dictionary>>(); + var map = new Dictionary>(); - foreach (TCandidate predecessor in predecessors.Item2) + foreach (TCandidate predecessor in predecessors.Candidates) { - map.Add(predecessor, new Dictionary>()); + map.Add(predecessor, new Dictionary()); - foreach (TCandidate candidate in candidates.Item2) + foreach (TCandidate candidate in candidates.Candidates) { - map[predecessor].Add(candidate, this.ComputeTransition((previous, predecessor), (sample, candidate))); + map[predecessor].Add(candidate, this.ComputeTransition(new SampleCandidate(previous, predecessor), new SampleCandidate(sample, candidate))); } } @@ -118,7 +166,9 @@ public virtual ICollection Execute(IEnumerable predecess { var states = candidates.Select(c => c.Candidate).Distinct(); - var transitions = this.ComputeTransitions((previous, predecessors), (sample, states)); + var transitions = this.ComputeTransitions( + new SampleCandidates(previous, predecessors), + new SampleCandidates(sample, states)); foreach (var candidate in candidates) { diff --git a/src/Sandwych.MapMatchingKit/Markov/CandidateProbability.cs b/src/Sandwych.MapMatchingKit/Markov/CandidateProbability.cs deleted file mode 100644 index eb747e7..0000000 --- a/src/Sandwych.MapMatchingKit/Markov/CandidateProbability.cs +++ /dev/null @@ -1,18 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Text; - -namespace Sandwych.MapMatchingKit.Markov -{ - public readonly struct CandidateProbability - { - public TCandidate Candidate { get; } - public double Probability { get; } - - public CandidateProbability(TCandidate cand, double prob) - { - this.Candidate = cand; - this.Probability = prob; - } - } -} diff --git a/src/Sandwych.MapMatchingKit/Markov/HmmProbabilities.cs b/src/Sandwych.MapMatchingKit/Markov/HmmProbabilities.cs deleted file mode 100644 index a70409a..0000000 --- a/src/Sandwych.MapMatchingKit/Markov/HmmProbabilities.cs +++ /dev/null @@ -1,119 +0,0 @@ -/** - * Copyright (C) 2015-2016, BMW Car IT GmbH and BMW AG - * Author: Stefan Holder (stefan.holder@bmw.de) - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - - -using System; -using System.Collections.Generic; -using System.Text; - -namespace Sandwych.MapMatchingKit.Markov -{ - /// - /// Based on Newson, Paul, and John Krumm. "Hidden Markov map matching through - /// noise and sparseness." Proceedings of the 17th ACM SIGSPATIAL International - /// Conference on Advances in Geographic Information Systems. ACM, 2009. - /// - public class HmmProbabilities - { - - public double Sigma { get; } - public double Beta { get; } - - /// - /// Sets default values for sigma and beta. - /// - public HmmProbabilities() : this(4.07, 0.00959442) - { - } - - /// - /// - /// standard deviation of the normal distribution [m] used for modeling the GPS error - /// beta parameter of the exponential distribution used for modeling transition probabilities - public HmmProbabilities(in double sigma, in double beta) - { - Sigma = sigma; - Beta = beta; - } - - /// - /// Returns the logarithmic emission probability density. - /// - /// - /// Absolute distance [m] between GPS measurement and map matching candidate. - public double EmissionLogProbability(in double distance) - { - return Distributions.LogNormalDistribution(this.Sigma, distance); - } - - /// - /// Returns the logarithmic transition probability density for the given - /// transition parameters. - /// - /// Length of the shortest route [m] between two consecutive map matching candidates. - /// Linear distance [m] between two consecutive GPS measurements. - /// - public double TransitionLogProbability(in double routeLength, in double linearDistance) - { - // Transition metric taken from Newson & Krumm. - var transitionMetric = Math.Abs(linearDistance - routeLength); - - return Distributions.LogExponentialDistribution(this.Beta, transitionMetric); - } - - - /// - /// Returns the logarithmic transition probability density for the given transition - /// parameters. - /// - /// Length of the shortest route [m] between two consecutive map matching candidates. - /// Linear distance [m] between two consecutive GPS measurements. - /// time difference [s] between two consecutive GPS measurements. - /// - public double TransitionLogProbability(double routeLength, double linearDistance, double timeDiff) - { - var transitionMetric = NormalizedTransitionMetric(routeLength, linearDistance, timeDiff); - return Distributions.LogExponentialDistribution(this.Beta, transitionMetric); - } - - - /// - /// Returns a transition metric for the transition between two consecutive map matching - /// candidates. - /// - /// In contrast to Newson and Krumm the absolute distance difference is divided by the quadratic - /// time difference to make the beta parameter of the exponential distribution independent of the - /// sampling interval. - /// - /// - /// - /// - /// - private double NormalizedTransitionMetric(double routeLength, double linearDistance, - double timeDiff) - { - if (timeDiff < 0.0) - { - throw new ArgumentOutOfRangeException(nameof(timeDiff), - "Time difference between subsequent location measurements must be >= 0."); - } - return Math.Abs(linearDistance - routeLength) / (timeDiff * timeDiff); - } - - - } -} diff --git a/src/Sandwych.MapMatchingKit/Markov/KState.cs b/src/Sandwych.MapMatchingKit/Markov/KState.cs index 71ff54f..5ab4160 100644 --- a/src/Sandwych.MapMatchingKit/Markov/KState.cs +++ b/src/Sandwych.MapMatchingKit/Markov/KState.cs @@ -71,7 +71,7 @@ public TSample Sample { if (_sequence.Count == 0) { - return default(TSample); + throw new InvalidOperationException(); } else { @@ -86,7 +86,7 @@ public DateTimeOffset Time { if (_sequence.Count == 0) { - return DateTimeOffset.MaxValue; + throw new InvalidOperationException(); } else { diff --git a/src/Sandwych.MapMatchingKit/Markov/SampleCandidates.cs b/src/Sandwych.MapMatchingKit/Markov/SampleCandidates.cs new file mode 100644 index 0000000..9c1a037 --- /dev/null +++ b/src/Sandwych.MapMatchingKit/Markov/SampleCandidates.cs @@ -0,0 +1,8 @@ +using System; +using System.Collections.Generic; +using System.Text; + +namespace Sandwych.MapMatchingKit.Markov +{ + +} diff --git a/src/Sandwych.MapMatchingKit/Markov/TransitionProbability.cs b/src/Sandwych.MapMatchingKit/Markov/TransitionProbability.cs deleted file mode 100644 index c130197..0000000 --- a/src/Sandwych.MapMatchingKit/Markov/TransitionProbability.cs +++ /dev/null @@ -1,18 +0,0 @@ -using System; -using System.Collections.Generic; -using System.Text; - -namespace Sandwych.MapMatchingKit.Markov -{ - public readonly struct TransitionProbability - { - public TTransition Transition { get; } - public double Probability { get; } - - public TransitionProbability(TTransition transition, double prob) - { - this.Transition = transition; - this.Probability = prob; - } - } -} diff --git a/src/Sandwych.MapMatchingKit/Matching/Matcher.cs b/src/Sandwych.MapMatchingKit/Matching/Matcher.cs index 3d61bd0..de0b153 100644 --- a/src/Sandwych.MapMatchingKit/Matching/Matcher.cs +++ b/src/Sandwych.MapMatchingKit/Matching/Matcher.cs @@ -9,9 +9,6 @@ namespace Sandwych.MapMatchingKit.Matching { - using CandidateProbability = CandidateProbability; - using TransitionProbability = TransitionProbability; - /// /// Matcher filter for Hidden Markov Model (HMM) map matching. It is a HMM filter () @@ -90,7 +87,7 @@ public double Sigma public int MaxCandidates { get; set; } = 8; - public override IReadOnlyCollection ComputeCandidates( + public override IEnumerable ComputeCandidates( IEnumerable predecessors, in MatcherSample sample) { var points_ = this._map.Radius(sample.Coordinate, this.MaxRadius, this.MaxCandidates); @@ -106,54 +103,51 @@ public override IReadOnlyCollection ComputeCandidates( { var pointExisted = dict.TryGetValue(predecessor.Point.Edge.Id, out var point); if (pointExisted && point.Edge != null - && _spatial.Distance(point.Coordinate, predecessor.Point.Coordinate) < this.Sigma - && ((point.Edge.Headeing == Heading.Forward - && point.Fraction < predecessor.Point.Fraction) - || (point.Edge.Headeing == Heading.Backward - && point.Fraction > predecessor.Point.Fraction))) + && ((point.Edge.Headeing == Heading.Forward && point.Fraction < predecessor.Point.Fraction) + || (point.Edge.Headeing == Heading.Backward && point.Fraction > predecessor.Point.Fraction)) + && _spatial.Distance(point.Coordinate, predecessor.Point.Coordinate) < this.Sigma) { points.Remove(point); points.Add(predecessor.Point); } } - var candidates = new List(points.Count); - + var results = new List(points.Count); foreach (var point in points) { - double dz = _spatial.Distance(sample.Coordinate, point.Coordinate); - double emission = this.ComputeEmissionProbability(sample, point, dz); + var dz = _spatial.Distance(sample.Coordinate, point.Coordinate); + var emission = this.ComputeEmissionProbability(sample, point, dz); var candidate = new MatcherCandidate(sample, point); - candidates.Add(new CandidateProbability(candidate, emission)); + var cp = new CandidateProbability(candidate, emission); + results.Add(cp); } - - return candidates; + return results; } public override TransitionProbability ComputeTransition( - in (MatcherSample, MatcherCandidate) predecessor, in (MatcherSample, MatcherCandidate) candidate) + in SampleCandidate predecessor, in SampleCandidate candidate) { throw new NotSupportedException(); } public override IDictionary> ComputeTransitions( - in (MatcherSample, IEnumerable) predecessors, - in (MatcherSample, IEnumerable) candidates) + in SampleCandidates predecessors, + in SampleCandidates candidates) { - var targets = candidates.Item2.Select(c => c.Point); + var targets = candidates.Candidates.Select(c => c.Point); var transitions = new Dictionary>(); - var base_ = 1.0 * _spatial.Distance(predecessors.Item1.Coordinate, candidates.Item1.Coordinate) / 60.0; - var bound = Math.Max(1000.0, Math.Min(this.MaxDistance, (candidates.Item1.Time - predecessors.Item1.Time).TotalSeconds * 100.0)); + var base_ = 1.0 * _spatial.Distance(predecessors.Sample.Coordinate, candidates.Sample.Coordinate) / 60.0; + var bound = Math.Max(1000.0, Math.Min(this.MaxDistance, (candidates.Sample.Time - predecessors.Sample.Time).TotalSeconds * 100.0)); - foreach (var predecessor in predecessors.Item2) + foreach (var predecessor in predecessors.Candidates) { var map = new Dictionary(); //TODO check return var routes = _router.Route(predecessor.Point, targets, _cost, Costs.DistanceCost, bound); - foreach (var candidate in candidates.Item2) + foreach (var candidate in candidates.Candidates) { if (routes.TryGetValue(candidate.Point, out var edges)) { @@ -165,7 +159,7 @@ public override IDictionary - + diff --git a/test/Sandwych.Hmm.Tests/Sandwych.Hmm.Tests.csproj b/test/Sandwych.Hmm.Tests/Sandwych.Hmm.Tests.csproj index fcc9408..0a7493b 100644 --- a/test/Sandwych.Hmm.Tests/Sandwych.Hmm.Tests.csproj +++ b/test/Sandwych.Hmm.Tests/Sandwych.Hmm.Tests.csproj @@ -8,7 +8,7 @@ - + diff --git a/test/Sandwych.MapMatchingKit.Tests/Markov/FilterTest.cs b/test/Sandwych.MapMatchingKit.Tests/Markov/FilterTest.cs index ff80603..a808bbd 100644 --- a/test/Sandwych.MapMatchingKit.Tests/Markov/FilterTest.cs +++ b/test/Sandwych.MapMatchingKit.Tests/Markov/FilterTest.cs @@ -133,24 +133,24 @@ public MockFilter(MockStates states) this.states = states; } - public override IReadOnlyCollection> ComputeCandidates( + public override IEnumerable ComputeCandidates( IEnumerable predecessors, in MockSample sample) { - var candidates = new List>(); + var results = new CandidateProbability[states.NumCandidates]; for (int c = 0; c < states.NumCandidates; ++c) { - candidates.Add(new CandidateProbability(new MockElement(sample, c), states.Emission(c))); + results[c] = new CandidateProbability(new MockElement(sample, c), states.Emission(c)); } - return candidates.ToArray(); + return results; } - public override TransitionProbability ComputeTransition( - in (MockSample, MockElement) predecessor, - in (MockSample, MockElement) candidate) + public override TransitionProbability ComputeTransition( + in SampleCandidate predecessor, + in SampleCandidate candidate) { - return new TransitionProbability( - new MockStateTransition(), states.Transition(predecessor.Item2.Id, candidate.Item2.Id)); + return new TransitionProbability( + new MockStateTransition(), states.Transition(predecessor.Candidate.Id, candidate.Candidate.Id)); } public ICollection Execute() diff --git a/test/Sandwych.MapMatchingKit.Tests/Matching/MatcherTest.cs b/test/Sandwych.MapMatchingKit.Tests/Matching/MatcherTest.cs index 5f3bc96..535c760 100644 --- a/test/Sandwych.MapMatchingKit.Tests/Matching/MatcherTest.cs +++ b/test/Sandwych.MapMatchingKit.Tests/Matching/MatcherTest.cs @@ -14,6 +14,8 @@ namespace Sandwych.MapMatchingKit.Tests.Matching { + using Matcher = Matcher; + public class MatcherTest : TestBase { private readonly ISpatialOperation _spatial = new GeographySpatialOperation(); @@ -56,7 +58,7 @@ public MatcherTest() _map = roadMapBuilder.AddRoads(reader.Roads).Build(); } - private void AssertCandidate(in CandidateProbability candidate, Coordinate2D sample) + private void AssertCandidate(in Matcher.CandidateProbability candidate, Coordinate2D sample) { var polyline = _map.GetEdge(candidate.Candidate.Point.Edge.Id).Geometry; var f = _spatial.Intercept(polyline, sample); @@ -70,7 +72,7 @@ private void AssertCandidate(in CandidateProbability candidate AssertEquals(p, candidate.Probability, 10E-6); } - private void AssertTransition(in TransitionProbability transition, + private void AssertTransition(in Matcher.TransitionProbability transition, in (MatcherCandidate, MatcherSample) source, in (MatcherCandidate, MatcherSample) target, double lambda) { @@ -112,7 +114,7 @@ private ISet RefSet(Coordinate2D sample, double radius) [Fact] public void TestCandidates() { - var filter = new Matcher(_map, _router, _cost, _spatial); + var filter = new Matcher(_map, _router, _cost, _spatial); { filter.MaxRadius = 100D; var sample = new Coordinate2D(11.001, 48.001); @@ -152,7 +154,7 @@ void assertCandidate(double radius, Coordinate2D sample, IEnumerable refse [Fact] public void TestTransitions() { - var filter = new Matcher(_map, _router, _cost, _spatial); + var filter = new Matcher(_map, _router, _cost, _spatial); filter.MaxRadius = 200D; { MatcherSample sample1 = new MatcherSample(0, 0, new Coordinate2D(11.001, 48.001)); @@ -174,7 +176,7 @@ public void TestTransitions() Assert.Equal(2, predecessors.Count); Assert.Equal(4, candidates.Count); - var transitions = filter.ComputeTransitions((sample1, predecessors), (sample2, candidates)); + var transitions = filter.ComputeTransitions(new Matcher.SampleCandidates(sample1, predecessors), new Matcher.SampleCandidates(sample2, candidates)); Assert.Equal(2, transitions.Count); @@ -209,7 +211,7 @@ public void TestTransitions() Assert.Equal(4, predecessors.Count); Assert.Equal(2, candidates.Count); - var transitions = filter.ComputeTransitions((sample1, predecessors), (sample2, candidates)); + var transitions = filter.ComputeTransitions(new Matcher.SampleCandidates(sample1, predecessors), new Matcher.SampleCandidates(sample2, candidates)); Assert.Equal(4, transitions.Count); diff --git a/test/Sandwych.MapMatchingKit.Tests/Sandwych.MapMatchingKit.Tests.csproj b/test/Sandwych.MapMatchingKit.Tests/Sandwych.MapMatchingKit.Tests.csproj index e892c45..1868505 100644 --- a/test/Sandwych.MapMatchingKit.Tests/Sandwych.MapMatchingKit.Tests.csproj +++ b/test/Sandwych.MapMatchingKit.Tests/Sandwych.MapMatchingKit.Tests.csproj @@ -9,7 +9,7 @@ - + From 2a8c9dadd97ab6081398f649726a2da91f008e2a Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Sat, 17 Mar 2018 14:39:01 +0800 Subject: [PATCH 30/37] fix kstate --- src/Sandwych.MapMatchingKit/Markov/KState.cs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/Sandwych.MapMatchingKit/Markov/KState.cs b/src/Sandwych.MapMatchingKit/Markov/KState.cs index 5ab4160..a25c320 100644 --- a/src/Sandwych.MapMatchingKit/Markov/KState.cs +++ b/src/Sandwych.MapMatchingKit/Markov/KState.cs @@ -71,7 +71,7 @@ public TSample Sample { if (_sequence.Count == 0) { - throw new InvalidOperationException(); + return default(TSample); } else { From 137b6decae4750528426ea89dbc4dc8ac34f8cea Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Tue, 11 Sep 2018 21:04:42 +0800 Subject: [PATCH 31/37] update all dep & libs --- .../RoutersBenchmark.cs | 3 --- .../Sandwych.MapMatchingKit.BenchmarkApp.csproj | 6 +++--- .../SpatialIndexBenchmark.cs | 3 --- ....MapMatchingKit.Examples.HelloWorldApp.csproj | 4 ++-- src/Sandwych.Hmm/Directory.Build.props | 2 +- src/Sandwych.Hmm/Sandwych.Hmm.csproj | 2 +- .../Directory.Build.props | 2 +- .../Sandwych.MapMatchingKit.csproj | 11 ++++++----- .../Sandwych.Hmm.Tests/Sandwych.Hmm.Tests.csproj | 16 +++++++++++----- .../Sandwych.MapMatchingKit.Tests.csproj | 16 +++++++++++----- 10 files changed, 36 insertions(+), 29 deletions(-) diff --git a/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/RoutersBenchmark.cs b/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/RoutersBenchmark.cs index b32ba3a..6350614 100644 --- a/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/RoutersBenchmark.cs +++ b/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/RoutersBenchmark.cs @@ -5,9 +5,6 @@ using System.Text; using System.Globalization; using BenchmarkDotNet.Attributes; -using BenchmarkDotNet.Attributes.Columns; -using BenchmarkDotNet.Attributes.Exporters; -using BenchmarkDotNet.Attributes.Jobs; using BenchmarkDotNet.Running; using NetTopologySuite.Features; using NetTopologySuite.IO; diff --git a/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/Sandwych.MapMatchingKit.BenchmarkApp.csproj b/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/Sandwych.MapMatchingKit.BenchmarkApp.csproj index 412bf9a..2356ed0 100644 --- a/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/Sandwych.MapMatchingKit.BenchmarkApp.csproj +++ b/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/Sandwych.MapMatchingKit.BenchmarkApp.csproj @@ -2,12 +2,12 @@ Exe - netcoreapp2.0 + netcoreapp2.1 - - + + diff --git a/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/SpatialIndexBenchmark.cs b/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/SpatialIndexBenchmark.cs index 8cbf5f1..24bc266 100644 --- a/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/SpatialIndexBenchmark.cs +++ b/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/SpatialIndexBenchmark.cs @@ -5,9 +5,6 @@ using System.Text; using System.Globalization; using BenchmarkDotNet.Attributes; -using BenchmarkDotNet.Attributes.Columns; -using BenchmarkDotNet.Attributes.Exporters; -using BenchmarkDotNet.Attributes.Jobs; using BenchmarkDotNet.Running; using NetTopologySuite.Features; using NetTopologySuite.IO; diff --git a/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Sandwych.MapMatchingKit.Examples.HelloWorldApp.csproj b/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Sandwych.MapMatchingKit.Examples.HelloWorldApp.csproj index ad8d1ee..5aa1072 100644 --- a/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Sandwych.MapMatchingKit.Examples.HelloWorldApp.csproj +++ b/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Sandwych.MapMatchingKit.Examples.HelloWorldApp.csproj @@ -2,11 +2,11 @@ Exe - netcoreapp2.0 + netcoreapp2.1 - + diff --git a/src/Sandwych.Hmm/Directory.Build.props b/src/Sandwych.Hmm/Directory.Build.props index 9040677..3d32808 100644 --- a/src/Sandwych.Hmm/Directory.Build.props +++ b/src/Sandwych.Hmm/Directory.Build.props @@ -8,7 +8,7 @@ A general purpose utility library implements Hidden Markov Models (HMM) for time-inhomogeneous Markov processes for .NET. map-matching;markov;hmm;viterbi - 0.1.0 + 0.1.1 beta diff --git a/src/Sandwych.Hmm/Sandwych.Hmm.csproj b/src/Sandwych.Hmm/Sandwych.Hmm.csproj index 0817b07..af72062 100644 --- a/src/Sandwych.Hmm/Sandwych.Hmm.csproj +++ b/src/Sandwych.Hmm/Sandwych.Hmm.csproj @@ -1,7 +1,7 @@ - netstandard1.1;net45 + netstandard2.0;net45 latest diff --git a/src/Sandwych.MapMatchingKit/Directory.Build.props b/src/Sandwych.MapMatchingKit/Directory.Build.props index 5534005..718cc11 100644 --- a/src/Sandwych.MapMatchingKit/Directory.Build.props +++ b/src/Sandwych.MapMatchingKit/Directory.Build.props @@ -6,7 +6,7 @@ A GPS map-matching solution for .NET platform. A GPS map-matching solution for .NET platform. This solution is porting from the "barefoot" project which developed in Java. map;gis;map-matching;osm;spatial - 0.1.4 + 0.1.5 alpha diff --git a/src/Sandwych.MapMatchingKit/Sandwych.MapMatchingKit.csproj b/src/Sandwych.MapMatchingKit/Sandwych.MapMatchingKit.csproj index dad2368..8451a01 100644 --- a/src/Sandwych.MapMatchingKit/Sandwych.MapMatchingKit.csproj +++ b/src/Sandwych.MapMatchingKit/Sandwych.MapMatchingKit.csproj @@ -1,19 +1,20 @@ - netstandard1.6;netstandard2.0;net451;net461; + netstandard2.0;net461; latest false - + - + - + - + + diff --git a/test/Sandwych.Hmm.Tests/Sandwych.Hmm.Tests.csproj b/test/Sandwych.Hmm.Tests/Sandwych.Hmm.Tests.csproj index 0a7493b..7a5f5d6 100644 --- a/test/Sandwych.Hmm.Tests/Sandwych.Hmm.Tests.csproj +++ b/test/Sandwych.Hmm.Tests/Sandwych.Hmm.Tests.csproj @@ -1,17 +1,23 @@ - netcoreapp2.0 + netcoreapp2.1 Library latest - - - - + + + + all + runtime; build; native; contentfiles; analyzers + + + all + runtime; build; native; contentfiles; analyzers + diff --git a/test/Sandwych.MapMatchingKit.Tests/Sandwych.MapMatchingKit.Tests.csproj b/test/Sandwych.MapMatchingKit.Tests/Sandwych.MapMatchingKit.Tests.csproj index 1868505..7ac9190 100644 --- a/test/Sandwych.MapMatchingKit.Tests/Sandwych.MapMatchingKit.Tests.csproj +++ b/test/Sandwych.MapMatchingKit.Tests/Sandwych.MapMatchingKit.Tests.csproj @@ -1,7 +1,7 @@ - netcoreapp2.0 + netcoreapp2.1 Library latest @@ -9,10 +9,16 @@ - - - - + + + + all + runtime; build; native; contentfiles; analyzers + + + all + runtime; build; native; contentfiles; analyzers + From 9a6eb184fa840915c2e6c75ed1462204918740a3 Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Tue, 11 Sep 2018 22:30:27 +0800 Subject: [PATCH 32/37] update travis.yml --- .travis.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.travis.yml b/.travis.yml index aa2cdf5..7cc7d20 100644 --- a/.travis.yml +++ b/.travis.yml @@ -2,8 +2,8 @@ language: csharp sudo: false mono: none dotnet: 2.1.4 -mono: 5.10.0 -dist: trusty +mono: latest +dist: xenial env: global: From 94fb055fa3fb83c8916752efa8b4aae9e9bb285c Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Tue, 11 Sep 2018 22:46:45 +0800 Subject: [PATCH 33/37] Make build.sh executable --- build.sh | 0 1 file changed, 0 insertions(+), 0 deletions(-) mode change 100644 => 100755 build.sh diff --git a/build.sh b/build.sh old mode 100644 new mode 100755 From 63e20d7fc4de445aa72f6a6591bb469e21408eeb Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Tue, 11 Sep 2018 22:59:49 +0800 Subject: [PATCH 34/37] update .net sdk version in .travis.yml --- .travis.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.travis.yml b/.travis.yml index 7cc7d20..a25fe27 100644 --- a/.travis.yml +++ b/.travis.yml @@ -1,7 +1,7 @@ language: csharp sudo: false mono: none -dotnet: 2.1.4 +dotnet: 2.1.401 mono: latest dist: xenial From e38142460b721e2bbe8bf2218f4d47764a97826c Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Wed, 12 Sep 2018 10:43:37 +0800 Subject: [PATCH 35/37] update netcoreapp 2.0 to 2.1 in build.cake --- build.cake | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/build.cake b/build.cake index debfbf6..57ff1b2 100644 --- a/build.cake +++ b/build.cake @@ -60,7 +60,7 @@ Task("Run-Unit-Tests") { var settings = new DotNetCoreTestSettings { - Framework = "netcoreapp2.0", + Framework = "netcoreapp2.1", NoBuild = true, NoRestore = true, Configuration = configuration, From 2ff1e51fee496be1bae885e2a1970a4fde5cc480 Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Sat, 11 May 2019 10:12:59 +0800 Subject: [PATCH 36/37] upgrade libs --- .../Sandwych.MapMatchingKit.BenchmarkApp.csproj | 4 ++-- .../Sandwych.MapMatchingKit.Examples.HelloWorldApp.csproj | 2 +- .../Sandwych.MapMatchingKit.csproj | 4 ++-- test/Sandwych.Hmm.Tests/Sandwych.Hmm.Tests.csproj | 8 ++++---- .../Sandwych.MapMatchingKit.Tests.csproj | 8 ++++---- 5 files changed, 13 insertions(+), 13 deletions(-) diff --git a/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/Sandwych.MapMatchingKit.BenchmarkApp.csproj b/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/Sandwych.MapMatchingKit.BenchmarkApp.csproj index 2356ed0..4bc5d69 100644 --- a/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/Sandwych.MapMatchingKit.BenchmarkApp.csproj +++ b/benchmark/Sandwych.MapMatchingKit.BenchmarkApp/Sandwych.MapMatchingKit.BenchmarkApp.csproj @@ -6,8 +6,8 @@ - - + + diff --git a/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Sandwych.MapMatchingKit.Examples.HelloWorldApp.csproj b/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Sandwych.MapMatchingKit.Examples.HelloWorldApp.csproj index 5aa1072..e3654cf 100644 --- a/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Sandwych.MapMatchingKit.Examples.HelloWorldApp.csproj +++ b/examples/Sandwych.MapMatchingKit.Examples.HelloWorldApp/Sandwych.MapMatchingKit.Examples.HelloWorldApp.csproj @@ -6,7 +6,7 @@ - + diff --git a/src/Sandwych.MapMatchingKit/Sandwych.MapMatchingKit.csproj b/src/Sandwych.MapMatchingKit/Sandwych.MapMatchingKit.csproj index 8451a01..90a4565 100644 --- a/src/Sandwych.MapMatchingKit/Sandwych.MapMatchingKit.csproj +++ b/src/Sandwych.MapMatchingKit/Sandwych.MapMatchingKit.csproj @@ -7,11 +7,11 @@ - + - + diff --git a/test/Sandwych.Hmm.Tests/Sandwych.Hmm.Tests.csproj b/test/Sandwych.Hmm.Tests/Sandwych.Hmm.Tests.csproj index 7a5f5d6..aaa4d21 100644 --- a/test/Sandwych.Hmm.Tests/Sandwych.Hmm.Tests.csproj +++ b/test/Sandwych.Hmm.Tests/Sandwych.Hmm.Tests.csproj @@ -8,13 +8,13 @@ - - - + + + all runtime; build; native; contentfiles; analyzers - + all runtime; build; native; contentfiles; analyzers diff --git a/test/Sandwych.MapMatchingKit.Tests/Sandwych.MapMatchingKit.Tests.csproj b/test/Sandwych.MapMatchingKit.Tests/Sandwych.MapMatchingKit.Tests.csproj index 7ac9190..86030b0 100644 --- a/test/Sandwych.MapMatchingKit.Tests/Sandwych.MapMatchingKit.Tests.csproj +++ b/test/Sandwych.MapMatchingKit.Tests/Sandwych.MapMatchingKit.Tests.csproj @@ -9,13 +9,13 @@ - - - + + + all runtime; build; native; contentfiles; analyzers - + all runtime; build; native; contentfiles; analyzers From ce0048f6bb21bc70f0b28f4bdda672bd71ee1ff4 Mon Sep 17 00:00:00 2001 From: "Wei \"oldrev\" Li" Date: Sat, 11 May 2019 10:14:46 +0800 Subject: [PATCH 37/37] update version to 0.1.5.1 --- src/Sandwych.Hmm/Directory.Build.props | 2 +- src/Sandwych.MapMatchingKit/Directory.Build.props | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/Sandwych.Hmm/Directory.Build.props b/src/Sandwych.Hmm/Directory.Build.props index 3d32808..396e66d 100644 --- a/src/Sandwych.Hmm/Directory.Build.props +++ b/src/Sandwych.Hmm/Directory.Build.props @@ -8,7 +8,7 @@ A general purpose utility library implements Hidden Markov Models (HMM) for time-inhomogeneous Markov processes for .NET. map-matching;markov;hmm;viterbi - 0.1.1 + 0.1.1.1 beta diff --git a/src/Sandwych.MapMatchingKit/Directory.Build.props b/src/Sandwych.MapMatchingKit/Directory.Build.props index 718cc11..99583c5 100644 --- a/src/Sandwych.MapMatchingKit/Directory.Build.props +++ b/src/Sandwych.MapMatchingKit/Directory.Build.props @@ -6,7 +6,7 @@ A GPS map-matching solution for .NET platform. A GPS map-matching solution for .NET platform. This solution is porting from the "barefoot" project which developed in Java. map;gis;map-matching;osm;spatial - 0.1.5 + 0.1.5.1 alpha