Home » Extra libraries, Code snippets, applications etc. » Applications created with U++ » Distance - geodesic - Vincenty - very accurate
| Distance - geodesic - Vincenty - very accurate [message #25894] |
Thu, 18 March 2010 03:37  |
nlneilson
Messages: 644 Registered: January 2010 Location: U.S. California. Mojave &...
|
Contributor |
|
|
This is a small app that incorporates the Vincenty formulas, Inverse and Direct, to calculate the geodesic distance on the ellipsoidal Earth, WGS84. It also calculates the starting and ending angles. Or with a starting point, direction and distance it will calculate the end point and final angle.
Input/output can be in any of the commonly used formats.
This can be used alone but interacts with a NASA WorldWind application written in Java through a socket.
This was previously done with Python, Java and now with C++ using Upp, a very good IDE/application.
http://www.nlneilson.com/geocalc.html
edit: updated link
[Updated on: Sun, 02 January 2011 13:01] Report message to a moderator
|
|
|
|
|
|
|
|
| Re: Distance - geodesic - Vincenty - very accurate [message #25927 is a reply to message #25923] |
Sat, 20 March 2010 15:39   |
nlneilson
Messages: 644 Registered: January 2010 Location: U.S. California. Mojave &...
|
Contributor |
|
|
No, this can be used separately.
The latlon for the points can be typed or pasted in (then push Enter) for the calculations (Calculate->Distance). Many web sites have locations in latlon that can be copied and pasted into the app. It should be comma delimited so that may need to be added. There have been a few instances with the upp app where the text format was a problem, pasting the latlon into notepad and then into the app removed the formatting.
It will take data in decimal degrees, degrees minutes, deg min sec. And for distance meters, km, feet, mi, nmi.
The app can be used to convert also, km->mi, dms->deg, etc., and all to 8 decimal places or whatever you change the settings to. The data is retained in the app to 9 decimal places (degrees,meters), the Settings just change how it is displayed.
It works in Linux (Ubuntu 9.10) with Wine.
In theIDE it was much easier to do this than it was in Java.
[Updated on: Sat, 20 March 2010 16:46] Report message to a moderator
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| Re: Distance - geodesic - Vincenty - very accurate [message #25947 is a reply to message #25944] |
Sun, 21 March 2010 10:41   |
nlneilson
Messages: 644 Registered: January 2010 Location: U.S. California. Mojave &...
|
Contributor |
|
|
| Mindtraveller wrote on Sun, 21 March 2010 08:44 | Cool.
What is the accuracy/drift of your calculations?
|
The Vincenty formulas are VERY accurate. With the Python code running it through a series of locations using the
Inverse formula and the returned values input to the Direct formula the result coincided usually to 10 decimal places
but did not exceed +/- 1 in the 9th decimal place. 9 decimal places is one billionth of a meter. The accuracy will not be
affected by the calculations. The accuracy of data input for locations, distance and starting angle, for all intent and
purposes, will determine the accuracy of the output.
The calculations are just math, no drift. Any "drift" would come from the input data.
Here is data on Tectonic Plate velocity or "drift"
http://hypertextbook.com/facts/ZhenHuang.shtml
using 5 cm per year
.05 / (365 * 24 * 60 * 60) = meters per second so the code
Distance<<=Format("m/sec %.9f", .05 / (365 * 24 * 60 * 60));
returns m/sec 0.000000002
2 in the 9th decimal place so it would take only 5 sec to make a
change in the 8th decimal place. 8 decimal places is the highest I have in the Distance app.
[Updated on: Sun, 21 March 2010 10:43] Report message to a moderator
|
|
|
|
| Re: Distance - geodesic - Vincenty - very accurate [message #25951 is a reply to message #25947] |
Sun, 21 March 2010 18:11   |
 |
koldo
Messages: 3460 Registered: August 2008
|
Senior Veteran |
|
|
Hello nlnelson
Here there is the Chris Veness Vicentry direct formula
http://www.movable-type.co.uk/scripts/latlong-vincenty-direc t.html
The LGPL javascript code is this:
function destVincenty(lat1, lon1, brng, dist) {
var a = 6378137, b = 6356752.3142, f = 1/298.257223563; // WGS-84 ellipsiod
var s = dist;
var alpha1 = brng.toRad();
var sinAlpha1 = Math.sin(alpha1);
var cosAlpha1 = Math.cos(alpha1);
var tanU1 = (1-f) * Math.tan(lat1.toRad());
var cosU1 = 1 / Math.sqrt((1 + tanU1*tanU1)), sinU1 = tanU1*cosU1;
var sigma1 = Math.atan2(tanU1, cosAlpha1);
var sinAlpha = cosU1 * sinAlpha1;
var cosSqAlpha = 1 - sinAlpha*sinAlpha;
var uSq = cosSqAlpha * (a*a - b*b) / (b*b);
var A = 1 + uSq/16384*(4096+uSq*(-768+uSq*(320-175*uSq)));
var B = uSq/1024 * (256+uSq*(-128+uSq*(74-47*uSq)));
var sigma = s / (b*A), sigmaP = 2*Math.PI;
while (Math.abs(sigma-sigmaP) > 1e-12) {
var cos2SigmaM = Math.cos(2*sigma1 + sigma);
var sinSigma = Math.sin(sigma);
var cosSigma = Math.cos(sigma);
var deltaSigma = B*sinSigma*(cos2SigmaM+B/4*(cosSigma*(-1+2*cos2SigmaM*cos2SigmaM)-
B/6*cos2SigmaM*(-3+4*sinSigma*sinSigma)*(-3+4*cos2SigmaM*cos2SigmaM)));
sigmaP = sigma;
sigma = s / (b*A) + deltaSigma;
}
var tmp = sinU1*sinSigma - cosU1*cosSigma*cosAlpha1;
var lat2 = Math.atan2(sinU1*cosSigma + cosU1*sinSigma*cosAlpha1,
(1-f)*Math.sqrt(sinAlpha*sinAlpha + tmp*tmp));
var lambda = Math.atan2(sinSigma*sinAlpha1, cosU1*cosSigma - sinU1*sinSigma*cosAlpha1);
var C = f/16*cosSqAlpha*(4+f*(4-3*cosSqAlpha));
var L = lambda - (1-C) * f * sinAlpha *
(sigma + C*sinSigma*(cos2SigmaM+C*cosSigma*(-1+2*cos2SigmaM*cos2SigmaM)));
var revAz = Math.atan2(sinAlpha, -tmp); // final bearing
return new LatLon(lat2.toDeg(), lon1+L.toDeg());
}
Like the inverse, it seems easy to convert to C and LGPL license is pretty open.
Best regards
Iñaki
|
|
|
|
|
|
| Re: Distance - geodesic - Vincenty - very accurate [message #25954 is a reply to message #25953] |
Sun, 21 March 2010 22:10   |
nlneilson
Messages: 644 Registered: January 2010 Location: U.S. California. Mojave &...
|
Contributor |
|
|
It may be 10+ years since I ported the Fortran to Python.
Then to C++ and later to Java, both are fast but I have the C++ optimized to run through the Inverse code in 10.7 micro seconds on a single core 1.60 Ghz notebook.
When I used this in Upp I just made that into a header file.
I don't recall what changes were necessary there, I did that with Eclipse CDT first, maybe just copied the header file from Eclipse to Upp.
I like to tinker with numbers, my major in college was Physics.
[Updated on: Sun, 21 March 2010 22:54] Report message to a moderator
|
|
|
|
| Re: Distance - geodesic - Vincenty - very accurate [message #25974 is a reply to message #25935] |
Mon, 22 March 2010 22:20   |
nlneilson
Messages: 644 Registered: January 2010 Location: U.S. California. Mojave &...
|
Contributor |
|
|
| Didier wrote on Sat, 20 March 2010 22:29 | But why not publish a linux version ...?
|
I was able to get Upp/theIDE to run in Ubuntu 10.04b.
Trying to make a linux version of Distance.exe the first error was re #include <windows.h>, just commented that and here is an excerpt of the errors:
error: call of overloaded ‘abs(double)’ is ambiguous
/usr/include/stdlib.h:766: note: candidates are: int abs(int)
/home/neil/upp/uppsrc/Core/Core.h:300: note: Upp::int64 abs(Upp::int64)
/usr/include/c++/4.4/cstdlib:170: note: long long int __gnu_cxx::abs(long long int)
/usr/include/c++/4.4/cstdlib:139: note: long int std::abs(long int)
/home/neil/MyApps/Distance/VincFormula.h: In function ‘std::string
It make take some time but I will try to get a Linux version that will run without Wine.
[Updated on: Mon, 22 March 2010 22:25] Report message to a moderator
|
|
|
|
|
|
| Re: Distance - geodesic - Vincenty - very accurate [message #25976 is a reply to message #25975] |
Mon, 22 March 2010 22:57   |
nlneilson
Messages: 644 Registered: January 2010 Location: U.S. California. Mojave &...
|
Contributor |
|
|
Thanks Koldo, the fabs took care of that error.
Now I get:
/home/neil/MyApps/Distance/Distance.cpp:280: error: extra qualification ‘MyApp::’ on member ‘Key’
at this line:
bool MyApp::Key(dword key, int count){
edit: I deleted "MyApp::" and it works in debug.
I will make a few changes like the default dir for the file chooser, I had that as C:\ for win.
I changed it so it has a frame and can be dragged.
[Updated on: Mon, 22 March 2010 23:14] Report message to a moderator
|
|
|
|
|
|
| Re: Distance - geodesic - Vincenty - very accurate [message #25979 is a reply to message #25894] |
Mon, 22 March 2010 23:44   |
nlneilson
Messages: 644 Registered: January 2010 Location: U.S. California. Mojave &...
|
Contributor |
|
|
Here is the Linux version.
edit: The link was removed, still have a glitch when downloaded.
I have not tried all the functions yet, what I have tried worked.
I will change the dir for the file chooser later, that is only used to interact with another app.
This can be used by itself.
Now the hard part, making a Help file to explain how it can be used. Since it is menu driven most functions are self explanatory.
One thing to remember is after typing or pasting in the latlon for a point (or distance,angle) press Enter, I forget sometimes.
The latlon should be comma separated.
Neil
[Updated on: Tue, 23 March 2010 04:04] Report message to a moderator
|
|
|
|
| Re: Distance - geodesic - Vincenty - very accurate [message #25981 is a reply to message #25979] |
Tue, 23 March 2010 02:49   |
nlneilson
Messages: 644 Registered: January 2010 Location: U.S. California. Mojave &...
|
Contributor |
|
|
Strange error.
I download the Linux Distance from the above link (1499004 bytes) and try and run it:
Could not display "/home/neil/Downloads/Distance".
There is no application installed for executable files
It runs fine from /upp.out/GCC.Force_size.Gui.Shared/
I copied it (1499004 bytes) from upp.out/... to another dir and it works fine.
I replaced the file in upp.out/... with the downloaded file, same error.
I deleted it from the website and uploaded it 3 times, same error.
This is with Ubuntu 10.04b on the same computer used with theIDE to compile it.
[Updated on: Tue, 23 March 2010 03:04] Report message to a moderator
|
|
|
|
|
|
|
|
|
|
| Re: Distance - geodesic - Vincenty - very accurate [message #26020 is a reply to message #26007] |
Fri, 26 March 2010 11:09   |
nlneilson
Messages: 644 Registered: January 2010 Location: U.S. California. Mojave &...
|
Contributor |
|
|
I found where the glitch was. It had nothing to do with Ubuntu 10.04b (although I will drop that until the 10.04 release for other problems).
I ran some tests with the Linux version and found a problem.
The copy and paste from a web site for a location in deg,min,sec was not parsed correctly.
In another Java app, Location.jar, I spent a considerable amount of time parsing the different ways the location in lat,lon format is specified on the web.
http://www.nlneilson.com/nww.html
For the Distance app, Java or C++, unless the latlon is in decimal degrees, the lat and lon should be comma delimited, this eliminated many problems with odd ball formats.
The format that was a problem in the C++ Linux version is also a problem in the Win .exe version, I just did not catch that. I will go back into the parsing code and correct that.
The Java version worked but there were two function there:
.replaceAll("\\s+", " "); // This replaces several spaces with a single space
.trim(); // this removes leading and trailing spaces
I did not know the corresponding functions in C++, my error as usual.
[Updated on: Fri, 26 March 2010 11:27] Report message to a moderator
|
|
|
|
|
|
| Re: Distance - geodesic - Vincenty - very accurate [message #26022 is a reply to message #26021] |
Fri, 26 March 2010 13:08   |
nlneilson
Messages: 644 Registered: January 2010 Location: U.S. California. Mojave &...
|
Contributor |
|
|
TrimBoth(); I will try that.
One thing I noticed that seemed odd in upp:
The character for the degree symbol ° as int = -80
I thought that should be 176
I am handling it in upp with:
// if (ic>122 || ch=='°' || ch==''' || ch=='"') ic = 32;
if (ic>122 || ic==-80 || ic==39 || ic==34) ic = 32;
That could have something to do with the problem.
Sometimes for ° ic = -62 AND ch = -62 rather than ch = '°'
With my code the ° should be replaced with a space.
To take care of some strange stuff I have:
if (ic < 0) continue;
I could change that to:
if (ic < 0) ic = 32;
and then a few lines of code in C++ to check/remove the consecutive space/s similar to .replaceAll("\\s+", " "); in Java.
[Updated on: Fri, 26 March 2010 14:09] Report message to a moderator
|
|
|
|
|
|
|
|
| Re: Distance - geodesic - Vincenty - very accurate [message #26056 is a reply to message #26055] |
Sat, 27 March 2010 05:31   |
nlneilson
Messages: 644 Registered: January 2010 Location: U.S. California. Mojave &...
|
Contributor |
|
|
That glitch is fixed, not yet for all instances.
if (ic < 0) ic = 32;
And for the multiple spaces:
changed if (j==1) to if (j==1 && Dms!="")
I tried this and several others:
12°34'56"N,12°34'56"W
12° 34' 56" N , 12° 34' 56" W
http://nlneilson.com/apps/Distance.exe
It still seems strange the integer representation of
any character would be less than 0.
edit: Still have a glitch, works fine in theIDE and then
when it is copied to a directory with other apps.
When I upload and then download the .exe has problems with the extra spaces.
With Build->clean, Build->Clean UPPOUT I could get the error re extra spaces
using Debug->Execute but Debug->Run(in debugger) only the break points in the main would work.
Downloaded 2272 and the break points work OK.
This is with Vista, I think I will try with XP, Vista has been a real pain.
I found the problem with the break points (it had nothing to do with theIDE)
and only some times with extra spaces.
It checks the latlon for decimal degrees first and I have a comment:
// with ',' ' ' '~' but only one
I will add a count for spaces and if >1 get out of that loop.
The code will also work with the input of a GGA GPS sentence so it gets a bit complicated.
[Updated on: Sat, 27 March 2010 07:42] Report message to a moderator
|
|
|
|
| Re: Distance - geodesic - Vincenty - very accurate [message #26057 is a reply to message #26056] |
Sat, 27 March 2010 08:05   |
nlneilson
Messages: 644 Registered: January 2010 Location: U.S. California. Mojave &...
|
Contributor |
|
|
Dumb mistake, I really mess up sometimes.
When I port from one language to another I copy and paste and if
several lines are nearly the same I paste that in more than once
and then change what is necessary.
In Java I used dLat for a double and sLat for a String.
In Upp I used lat for a double and Lat for a String.
In the parse decimal degrees loop:
if (lon<=180 && lat>=-180)
should be lon
if (lon<=180 && lon>=-180)
This catches most error that would be caused by more than one space.
If I ever get an error caused by multiple spaces, or a report of one
I will count the spaces in the code and kick it out.
In Java this took care of it: .replaceAll("\\s+", " ");
I uploaded the file with FileZilla, downloaded and tried it, works OK.
[Updated on: Sat, 27 March 2010 08:22] Report message to a moderator
|
|
|
|
| Re: Distance - geodesic - Vincenty - very accurate [message #26058 is a reply to message #26056] |
Sat, 27 March 2010 10:23   |
|
|
Hi nlneilson
| Quote: | The character for the degree symbol ° as int = -80
I thought that should be 176
|
| Quote: | It still seems strange the integer representation of
any character would be less than 0.
|
It is not that strange as it looks. Internally, only last byte of int is considered, that is like if you performed modulo 256 operation. In your case, -80+255=176, so it is the same char, '°' But I agree, it is kind of obfuscating, maybe it should be changed.
Regards,
Honza
|
|
|
|
| Re: Distance - geodesic - Vincenty - very accurate [message #26065 is a reply to message #26058] |
Sun, 28 March 2010 14:25  |
nlneilson
Messages: 644 Registered: January 2010 Location: U.S. California. Mojave &...
|
Contributor |
|
|
| dolik.rce wrote on Sat, 27 March 2010 10:23 | In your case, -80+255=176, so it is the same char, '°' But I agree, it is kind of obfuscating, maybe it should be changed.
|
Thanks for the explanation, usually anything strange is from my code. A change for this in upp would be good.
Koldo: "Probably there is not only one option for º"
Usually it is -80, only with Vista, and then rarely but enough to cause errors has it been -62, maybe the format of the character.
if (ic < 0) ic = 32; takes care of it.
[Updated on: Sun, 28 March 2010 14:27] Report message to a moderator
|
|
|
|
Goto Forum:
Current Time: Wed Jun 03 19:42:06 GMT+2 2026
Total time taken to generate the page: 0.01039 seconds
|