-
Notifications
You must be signed in to change notification settings - Fork 1
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Subtraction of LatLon #2
Comments
The fundamental problem here is that there isn't just one way to do coordinate arithmetic. For example, I'd argue that the following operation can have two very different results, both of which are perfectly reasonable in their own way. x = LatLon(0,0) + 2*(LatLon(0,180) - LatLon(0,0))
Things get even trickier if we take differences at one latitude and then apply them at a different latitude. For example, what should the result of this expression be? y = LatLon(45,0) + 2*(LatLon(0,180) - LatLon(0,0)) I'd say all of the following are sensible answers:
Finally, what if even the difference is not taken at a single latitude? z = LatLon(45,0) + 2*(LatLon(30,180) - LatLon(0,0)) Should The rationale behind the current API is that while its results may not always be particularly useful, at least it is very easy to explain what is going on: coordinate arithmetic is always executed elementwise; you as the user are responsible for choosing the coordinates such that elementwise arithmetic does what you want! We actually have already seen an instance of this: in the current form of MapMaths, we have julia> LatLon(45,0)[] .+ 2 .* (LatLon(0,180)[] .- LatLon(0,0)[])
(45.0, 360.0) If instead of the rotation you want cartesian arithmetic, well then convert your arguments to ECEF beforehand: julia> ECEF(LatLon(45,0))[] .+ 2 .* (ECEF(LatLon(0,180))[] .- ECEF(LatLon(0,0))[])
(-2.0994957121151067e7, 0.0, 4.48734840886592e6) Finally, if instead of counting rotations you want to count distance, then convert your arguments to julia> EastNorth(LatLon(45,0))[] .+ 2 .* (EastNorth(LatLon(0,180))[] .- EastNorth(LatLon(0,0))[]) |> EastNorth |> LatLon
LatLon{Float64}(44.999999999999986, 508.2641127930218) All this is not to say that the current system is perfect. For example, I was quite shocked to see this: julia> norm(ECEF(LatLon(1.214914, 103.851194)) - ECEF(LatLon(1.214986, 103.851527)))
37.90659161709082
julia> norm(EastNorth(LatLon(1.214914, 103.851194))[] .- EastNorth(LatLon(1.214986, 103.851527))[])
37.607499239327225 Clearly, the difference between tunnel and surface distance cannot be 30cm over a range of 37m, and even more importantly, the surface distance cannot be less than the tunnel distance. What is happening here is that one point is about 8m further north than the other, and since Apart from "hard" / "numeric" bugs like the one described just now, I guess there is also plenty of scope for more syntactic sugar. For example, it might be nice to have a macro @coordinate(ECEF, x + 2*(y - z)) which expands to ECEF(x) + 2*(ECEF(y) - ECEF(z))) Finally, broken / missing methods like #3 and |
I see the primary use for math on lat-lon is to stay on the surface or earth. In most cases, a locally flat coordinate system around a given lat-lon is sufficient for this. In cases, where the distances are large, accounting for the earth's curvature is nice. Thing's I'd typically want to do:
|
I believe all of these objectives can be achieved without obstructing any other use case by defining coordinate arithmetic as follows.
The three actions that you mentioned could then be implemented as follows:
I hope I can get CoordRefSystems to adopt these conventions... |
Currently, if I subtract two
LatLon
coordinates, I get aLatLon
with the differences:While this may seem reasonable, it is incorrect. The differences between latitudes is not a latitude, and the differences between longitude is not a longitude. This becomes important when the latitude-longitude differences later need to be converted to east-north distances:
which is quite different from:
The essential problem is that the actual latitude-longitude is lost in taking the difference, and then the east-north conversion wrongly treats the differences as being located at the origin of the latitude-longitude coordinate system.
Perhaps we need a different data type to represent differences in latitude-longitude, rather than returning them as a latitude-longitude pair?
The text was updated successfully, but these errors were encountered: