Calculate Distances Between Addresses Without Google Maps - maps

I bascially want to create a search in our Sales Orders database to find items that where shipped within a range of a particular address.
I can't use Google's API because:
It will be a report and there is no way to display a Map at runtime, which violates the terms of service.
Google limits you to 1,600 requests a day, so comparing and arbitrary address to all our sales orders would violate that before 1 search completed.
I imagine running the directions API to compare the address to each order in our database would take forever.

A lot of this will depend on the precision and exactly what you want to do.
For example, if you want Line of Sight calculations, you can use a service like this one http://geocoder.us/ to get the Latitude and Longitude of each address, from this you can do a simple calculation to get the "as the crow flies" distance between this point and another.
if you want true driving direction distance, that will be much more complicated.

You could use the Yahoo! geocoding API and cache the lat/lons to the database, and then use the lat/lons and standard mapping library calls to determine the distance to your point of interest.

Have you looked at other geocoding APIs, like Yahoo or Bing?
There's also this one, which says it's free and offers a few .NET code samples.

Related

Search 10 nearest Locations in Datastore

I have a lot of Entities containing geoPoints stored in Google's Datastore.
Now I need to get the 10 nearest locations based on a Location sent to a Google Cloud Function.
I saw, that there is a distance() function in Google's App Engine, but nothing comparable in Google Cloud Functions, not even the possible to calculate anything in the Database.
Is it possible to get the 10 nearest Locations from Datastore only using Google Cloud Functions or do I need to use a different Database for that ?
Best Regards,
Pascal
We run a geospatial-heavy service on AppEngine.
Our solution is to store the locations on Memcache and doing the calculations directly instead of relying on the database.
This obviously depends on the amount of locations, but if you are clever about how you store the locations, you can search very quickly.
R-Trees are a very good example: https://en.wikipedia.org/wiki/R-tree
I had a similar need, and I solved it with a grid-based clustering scheme.
Essentially I created a Computed String Property that was the string concatenation of the latitude & longitude with the decimals chopped off.
If an entity had obj.latitude = 37.123456 & obj.longitude = 45.234567 then obj.grid_id="37:45"
When performing a search, I determine the grid of the search latitude & longitude as well as the 8 other surrounding grids and queried for all entities that resided in those 9 grids.
# for search latitude = 37.456 & longitude = 45.67
query = SomeModel.query(SomeModel.grid_id.IN([
'36:44', '36:45', '36:46',
'37:44', '37:45', '37:46',
'38:44', '38:45', '38:46',
]))
You would then find the 10 nearest in code.
Depending on your needs you may want to make grids id include decimal positions (obj.grid_id="37.1:45.2") or make them less precise(obj.grid_id="30:40")
This may or may not work for you depending on the distribution of you data points, in which case Zebs suggestion to use R-Tree is more robust, but this was simple to implement and sufficed my needs.
please have a look at the following post
Geospatial Query at Google App Engine Datastore
Unfortunately it is not possible to get the nearest location from the google cloud datastore itself. You have to implement your own logic or you have to use a different database

How to find all towns/cities within a driving distance of a particular city?

I am looking for an API to return a list of cities, given the current city (may be coordinates) and some specified driving distance. If driving distance is unfeasible, the list of cities within a radius is also acceptable. Any suggestions on what I can use to accomplish this?
I'm not quite sure why you would do something like that, but you have multiple ways to do so.
Easy way:
You need to get an area and create multiple location around your point (or your given city that you would geocode) and then you can use services that give you a multiple reverse geocoding feature like Here Platform does for example. In this way, you would get multiple cities and then you could filter the duplicated entries.
See: https://developer.here.com/rest-apis/documentation/geocoder/topics/request-first-multi-reverse-geocode.html
Complicated way but way more powerful:
Using the Here Platform, you can retrieve Drivetime area (also called isochronous) so based on a location and a duration, you can retrieve the geometry based on the selected transport mode.
See: http://developer.here.com/rest-apis/documentation/enterprise-routing/topics/resource-calculate-isoline.html#resource-calculate-isoline
Based on this geometry, you can create point as explained before or you can use your own database to query on which would contain city geometries for example.
Hope this helps, I know it's only explained and not coded (no code samples here), but it works for sure. I'll try to put more concrete cases but I'm sorry not now.

Database solution for route matching

i'm working on an application that lets users search for trips from point A to point B.
it needs to solve the following use cases:
find trips that go from point A to point B
find trips that start in some other point, but go trough point A to point B
I'm now looking for a database solution that would be best to support such use cases.
For now we are using MongoDB. But i had to figure out a workaround for the first use case and i have a feling that it's not possible to solve the second use case with it.
It seems to me that all the available noSql dbs that support spatial features allow only for one geospatial index on a document,node etc. This is fine for queries like show me all shops in radius of 5km from this point and the like.
So i'm looking for a solution that could solve both use cases. Is there something like that available?
pgRouting could be used, indeed. First solution, that pops into mind: when first user has entered New York and Columbus as source and destination of his trip, perform routing query and store path as PostGIS linestring geometry.
When second user enters From: Pittsburgh To: Columbus into search form, geocode city names to locations and make PostGIS queries, how far are those points (or city boundaries) from first user's route path. If they are close enough and first user drives on suitable direction, they could share car.
Second idea: after first user has entered trip details, perform routing query and store all place names, that are passed by route, into database.
Both solutions could be easily implemented with Postgres+PostGIS+pgRouting. Biggest disadvantage of pgRouting is low speed (it's possible to improve performance by reducing data in routing graph; routing speed is not so important etc). It's also possible to export road data to external files; use some high-speed routing engines (like OSRM, MoNav etc); and, if necessary, write result back to PostGIS. But this requires definitely much more effort.
Also, if you choose to avoid the Database route (no pun intended), you could use GeoTools graphing Java library.
http://docs.geotools.org/latest/userguide/extension/graph/index.html
Here is some example code and data I produced myself to demonstrate how it can be used.
http://usefulpracticalgeoblog.blogspot.ch/2012/09/geotools-routing.html
It is pretty flexible in terms of the spatial data formats that can be used to build the street network graph, and how the results can be outputted.
Then to find if the starting point of trip B is close to the pre-calculated route for Trip A, you could use JTS (Java Topology Suite), which is part of the GeoTools library. Here is an example of the analysis you might use.
https://gis.stackexchange.com/questions/7699/for-a-given-feature-find-the-closest-point-along-a-given-path
Postgresql with postgis and pgrouting. You need nothing else.

distance between two points across land using sql server

I am looking to calculate the shortest distance between two points inside SQL Server 2008 taking into account land mass only.
I have used the geography data type along with STDistance() to work out point x distance to point y as the crow flies, however this sometimes crosses the sea which i am trying to avoid.
I have also created a polygon around the land mass boundary I am interested in.
I believe that I need to combine these two methods to ensure that STDistance always remains within polygon - unless there is a simpler solution.
Thanks for any advice
Use STIntersects - http://msdn.microsoft.com/en-us/library/bb933899%28v=SQL.105%29.aspx to find out what part of the line is over land.
After reading your comment your requirement makes sense. However I'm pretty sure there are no inbuilt techniques to do this in SQL Server. I'm assuming you are ignoring roads, and taking an as-the-crow-flies approach but over land only.
The only way I can think to do this would be to convert your area into a raster (grid cells) and perform a cost path analysis. You would set the area of sea to have a prohibitively high cost so the algorithm would route around the sea. See this link for description of technique:
http://webhelp.esri.com/arcgisdesktop/9.3/index.cfm?TopicName=cost_path
Otherwise try implementing the algorithm below!
http://bit.ly/ckvciz
There may be other libraries that do this. Alteratively how about using the new Google Directions API between the two cities - you'd get actual road distances then.
http://code.google.com/apis/maps/documentation/directions/

Clustering Lat/Longs in a Database

I'm trying to see if anyone knows how to cluster some Lat/Long results, using a database, to reduce the number of results sent over the wire to the application.
There are a number of resources about how to cluster, either on the client side OR in the server (application) side .. but not in the database side :(
This is a similar question, asked by a fellow S.O. member. The solutions are server side based (ie. C# code behind).
Has anyone had any luck or experience with solving this, but in a database? Are there any database guru's out there who are after a hawt and sexy DB challenge?
please help :)
EDIT 1: Clarification - by clustering, i'm hoping to group x number of points into a single point, for an area. So, if i say cluster everything in a 1 mile / 1 km square, then all the results in that 'square' are GROUP'D into a single result (say ... the middle of the square).
EDIT 2: I'm using MS Sql 2008, but i'm open to hearing if there are other solutions in other DB's.
I'd probably use a modified* version of k-means clustering using the cartesian (e.g. WGS-84 ECF) coordinates for your points. It's easy to implement & converges quickly, and adapts to your data no matter what it looks like. Plus, you can pick k to suit your bandwidth requirements, and each cluster will have the same number of associated points (mod k).
I'd make a table of cluster centroids, and add a field to the original data table to indicate what cluster it belonged too. You'd obviously want to update the clustering periodically if your data is at all dynamic. I don't know if you could do that with a stored procedure & trigger, but perhaps.
*The "modification" would be to adjust the length of the computed centroid vectors so they'd be on the surface of the earth. Otherwise you'd end up with a bunch of points with negative altitude (when converted back to LLH).
If you're clustering on geographic location, and I can't imagine it being anything else :-), you could store the "cluster ID" in the database along with the lat/long co-ordinates.
What I mean by that is to divide the world map into (for example) a 100x100 matrix (10,000 clusters) and each co-ordinate gets assigned to one of those clusters.
Then, you can detect very close coordinates by selecting those in the same square and moderately close ones by selecting those in adjacent squares.
The size of your squares (and therefore the number of them) will be decided by how accurate you need the clustering to be. Obviously, if you only have a 2x2 matrix, you could get some clustering of co-ordinates that are a long way apart.
You will always have the edge cases such as two points close together but in different clusters (one northernmost in one cluster, the other southernmost in another) but you could adjust the cluster size OR post-process the results on the client side.
I did a similar thing for a geographic application where I wanted to ensure I could cache point sets easily. My geohashing code looks like this:
def compute_chunk(latitude, longitude)
(floor_lon(longitude) * 0x1000) | floor_lat(latitude)
end
def floor_lon(longitude)
((longitude + 180) * 10).to_i
end
def floor_lat(latitude)
((latitude + 90) * 10).to_i
end
Everything got really easy from there. I had some code for grabbing all of the chunks from a given point to a given radius that would translate into a single memcache multiget (and some code to backfill that when it was missing).
For movielandmarks.com I used the clustering code from Mike Purvis, one of the authors of Beginning Google Maps Applications with PHP and AJAX. It builds trees of clusters/points for different zoom levels using PHP and MySQL, storing it in the database so that recall is very fast. Some of it may be useful to you even if you are using a different database.
Why not testing multiple approaches?
translate the weka library in .NET CLI with IKVM.NET
add an assembly resulted from your code and weka.dll (use ilmerge) into your database
Make some tests, that is. No specific clustering works better than anyone else.
I believe you can use MSSQL's spatial data types. If they are similar to other spatial data types I know, they will store your points in a tree of rectangles, and then you can go to the lower-resolution rectangles to get implicit clusters.
If you end up wanting to explore Geohash's (which were invented at exactly the same time you posted this question), here's a more fleshed-out implementation of Geohash related functions for SQL Server's TSQL in which you might be interested.
QalGeohash-TSQL
I have used the Integer version of the Geohash extensively to cluster results to reduce data sent to a client for a limited viewport.

Resources