I frequently use the distanceFromLocation method for CLLocation objects to get their distance from other locations. Enumerating through an array of CLLocations, I then compare each to my reference location using this method.
I'm curious to know the processing/memory implications for using distanceFromLocation, especially for a large number of CLLocation objects in succession. How does this method work - does it connect to the server to get the data, or does it calculate the distance based on some mathematical formula, such as the Haversine Formula?
Is there a more efficient method to compare distances between 1 reference location and an array of CLLocation objects?
They are likely are using the Spherical Law of Cosines instead of the Haversine (why? see this question).
If all you want to do is compare many points against one point to see which is closest, then maybe you don't care about the accuracy of the computed distance and just about performance. In that case perhaps using Pythagoras' theorem would work for you.
All of these algorithms are detailed on this web page, which says in part:
If performance is an issue and accuracy less important, for small
distances Pythagoras’ theorem can be used on an equirectangular
projection:*
You could implement a function using Pythagoras' theorem then benchmark it against the one in CLLocation and against my implementation of distanceInMetersFromRadians that uses the Spherical Law of Cosines to see how much performance difference there is.
From the documentation:
distanceFromLocation:
This method measures the distance between the two locations by tracing a line between them that follows the curvature of the Earth. The resulting arc is a smooth curve and does not take into account specific altitude changes between the two locations.
So yes, I assume it is using the Haversine Formula (or a modification of it).
Have you used Instruments and measured it? Until you have done, it's pointless.
You can take shortcuts. Let's say you want the nearest point. Find a formula that gives you roughly the right result. Usually there's a square root involved, so get a formula for the square of the distance - that's quicker and works just as well. Find the nearest point with your formula. Now say the nearest point is 178.96 meters apart according to your formula. You can then check all points that are say less than 180 meters away with the exact formula.
For small distances and on iOS 9, I have found that the values obtained by distanceFromLocation are reliably close to those found by the Vincenty formula using the WGS-84 ellipsoid. In my experience, they are accurate within about 7 or 8 significant figures.
A spherical model, such as the law of cosines or the Haversine formula, does not compare well for small distances.
For more information, see the geopy documentation and a table of values for comparison.
Related
I have an array of MKLocationCoordinate2D in iOS and I'd like to create a heat map of those points based on the clustering of them.
i.e. the more there are in a certain area then the higher the weight.
I've found a load of different frameworks for generating the heat maps and they all require the weights to be calculated yourself (which makes sense).
I'm just not sure where to start with the calculation.
I could do something like calculating the mean distance between each point and every other point but I'm not sure if that's a good idea.
Could someone point me in the direction of how to weight each point based on it's closeness to other points.
Thanks
I solved this by implementing a quad tree and using that to quickly get the number of neighbours within a certain radius.
I can then change the radius to tweak it but it will very quickly return weights based on how many neighbours each point has.
I am still new with the idea of A* Search. I understand some of the Heuristic that A* Search have such as Straight-Line Distance (Euclidean Distance), Manhattan Distance and Misplaced Tiles (for 8 puzzle game).
For the 2-d grid world,
Which is better admissible heuristic than Straight-Line Distance. I have my mind on Manhattan Distance. Any other suggestion?
When using A* there are two properties that must hold for the heuristic, in order for the search to be optimal (finding the best solution).
The heuristic must be admissible
The heuristic must be monotonistic
In reality it's pretty hard to come up with a non-monotonistic (also called inconsistent) heuristic, so lets stick with the first requirement.
A heuristic is admissible if it never overestimates the distance between two nodes (in this case points). As such the manhattan-distance heuristic is not admissible if diagonal movements are allowed - simply because of pythagoras theorem (the combined length of the two catheti, is longer than the squareroot of the hypothenuse), so in this case the straight line distance heuristic is the better - since it's admissible.
However if diagonal movements are not allowed in the 2D grid, then both heuristics are admissible, since neither will overestimate the distance, but hte manhattan distance heuristic is the preferred, because it makes better estimates, i.e. estimates closer to the actual distance.
Use a heuristic that agrees with the allowed movement:
For 4-directions, use Manhattan distance (L1)
For 8-directions, use Chebyshev distance (L-Infinity)
For any direction, you can use Euclidean distance, but an alternative map representation may be better (e.g. using Waypoints)
Amit Patel has produced fantastic reference material for this subject. See his page at RedBlobGames.com for an introduction to A* and his page on Stanford's Game Programming Page for a description of several grid-world Heuristics . His Stanford page also describes several methods for reducing size of the open set when optimality is not required.
There are also extensions for A* to take advantage of symmetry in grids with constant movement cost. Daniel Harabor introduced two in his doctoral thesis--Jump Point Search (JPS) and Rectangular Symmetry Reduction (RSR). He describes these in an article he posted on AiGameDev.com
perhaps this is a simple question.
I have 3 GPS coordinates (one is the current user location). What I want now is to calculate the angle between the user location and the two GPS coordinates. Imagine the user location in the center of the two other points, the three points can be seen as a triangle. And I want to calculate the angle at the user location.
I hope someone can help me because I have no idea how to do this with spherical coordinates like the GPS coordinates I have.
THX - nekro
For short distances (less than 100km, say) you can safely ignore the spherical nature of the calculation and treat the problem as a 2 cartesian coordinate problem. For large distances the spherical geometry gets pretty gnarly. I could probably figure it out, but I don't want to think that hard right now.
Edit:
All you need to do is to convert both coordinates to KM, and then treat it as a cartesian problem. (At a small scale, you can ignore the curved nature of the "lines" and treat them as normal cartesian grid lines, since the curvature is small enough to ignore at that scale)
The distance per degree of latitude is constant. The distance for a degree of longitude changes based on latitude.
Do a google search on "KM per degree of longitude" and find a link that explains it clearly. Here's one: http://www.colorado.edu/geography/gcraft/warmup/aquifer/html/distance.html
You could use thessien polygons and calculate the geometry on those from a strictly GIS perspective. If you have qgis or arcgis this should be fairly simple. These packages offer APIs which might suit your needs.
You're essentially doing two calculations (bearing to (or from) current position to two other positions) and not crosstrack (distance from a great circle line between to other points).
However, both can be found in Ed William's Aviation Formulary which has the most comprehensive collection of formulas for spherical calculations I've found.
You would be looking for "Course between points" which is listed as:
tc1=mod(atan2(sin(lon1-lon2)*cos(lat2),
cos(lat1)*sin(lat2)-sin(lat1)*cos(lat2)*cos(lon1-lon2)), 2*pi)
I have a list of latitude and longitude values in a database. Based on a user’s location I need to extract the closest location from the database based on walking distances. For this purpose, I need to first get all values from the database into an array and then calculate WALKING distances to each and then return the lat/long of the shortest distance.
Note: I have no problem extracting the database values. I need help with the calculation of walking distances between 2 points.
I have so far found threads here which either show straight line distances. Is there any way to get walking distances between 2 points? If so, I would appreciate if you could point me in the right direction (link/previous question) or provide some guidance on what classes or functions to use.
You can get the distance in meter using the
CLLocationDistance distance = [locationOne distanceFromLocation:locationTwo];
you can acoordingly convert it into CentiMeter or Kilometer, this may serve your purpose
I'm starting a project where I am mapping a set of points on the Earth using google maps. I want to find the point on the globe which is the average (shortest total distance to all points), but I'm unsure how to handle it considering the distance may be shorter going the other way around the earth. (-178 degrees to 178 degrees longitude is only 4 degrees longitude apart, not 356). What is the best way to approach this, either via an api call or from a mathematical perspective?
I highly doubt there is a slick geometric argument giving a closed form expression for the desired point. Nonetheless here's a simple-minded algorithm which gives an answer to within any desired precision:
https://gist.github.com/amitkgupta/5019163
If you want a mathematically more satisfying solution, I recommend asking over at http://math.stackexchange.com, or they don't avail you, escalate it to http://mathoverflow.net.
I can suggest simple and fast solution (but not to exact initial task). Find the center of gravity of points, then there may be 2 situations:
it's located at center of sphere - don't know what to do (if initial points distributed close to each other - this will not happen)
in other case - consider vector with center of mass and center of sphere as finish and start points, find where such vector intersects surface of sphere, that point - is the answer.
So, you'll get point somewhat similar to 'mid-point', but only in cases when surface under consideration is very small (may be all point lay within the same city). But it is also has nothing to do with minimal average distances from result to initial points.