]> granicus.if.org Git - postgis/commitdiff
#1069: Support for specifying max_results to return. Regress already committed
authorRegina Obe <lr@pcorp.us>
Wed, 29 Jun 2011 10:35:21 +0000 (10:35 +0000)
committerRegina Obe <lr@pcorp.us>
Wed, 29 Jun 2011 10:35:21 +0000 (10:35 +0000)
git-svn-id: http://svn.osgeo.org/postgis/trunk@7518 b70326c6-7e19-0410-871a-916f4a2858ee

doc/extras_tigergeocoder.xml
extras/tiger_geocoder/tiger_2010/geocode/geocode.sql
extras/tiger_geocoder/tiger_2010/upgrade_geocode.sql

index c2d6f989ae0558062bb05f173fed6d7835b1b6e6..02bc7603ce923a954f2a3407a3be206a9b8672c9 100644 (file)
@@ -43,7 +43,8 @@
                <funcsynopsis>
                  <funcprototype>
                        <funcdef>setof record <function>geocode</function></funcdef>
-                       <paramdef><type>address </type> <parameter>varchar</parameter></paramdef>
+                       <paramdef><type>varchar </type> <parameter>address</parameter></paramdef>
+                       <paramdef><type choice='opt'>integer </type> <parameter>max_results=10</parameter></paramdef>
                        <paramdef><type>norm_addy </type> <parameter>OUT addy</parameter></paramdef>
                        <paramdef><type>geometry </type> <parameter>OUT geomout</parameter></paramdef>
                        <paramdef><type>integer </type> <parameter>OUT rating</parameter></paramdef>
@@ -51,6 +52,7 @@
                  <funcprototype>
                        <funcdef>setof record <function>geocode</function></funcdef>
                        <paramdef><type>norm_addy </type> <parameter>in_addy</parameter></paramdef>
+                       <paramdef><type choice='opt'>integer </type> <parameter>max_results=10</parameter></paramdef>
                        <paramdef><type>norm_addy </type> <parameter>OUT addy</parameter></paramdef>
                        <paramdef><type>geometry </type> <parameter>OUT geomout</parameter></paramdef>
                        <paramdef><type>integer </type> <parameter>OUT rating</parameter></paramdef>
@@ -64,9 +66,8 @@
                <para>Takes in an address as a string (or already normalized address) and outputs a set of possible locations which include a point geometry in NAD 83 long lat, a <varname>normalized_address</varname> (addy) for each, and the rating.  The lower the rating the more likely the match.  
                        Results are sorted by lowest rating first.  Uses Tiger data (edges,faces,addr), PostgreSQL fuzzy string matching (soundex,levenshtein) and PostGIS line interpolation functions to interpolate address along the Tiger edges. The higher the rating the less likely the geocode is right.</para>
 
-               <para>Enhanced: 2.0.0 to support Tiger 2010 structured data and revised some logic to improve speed.</para>
-
-
+               <para>Enhanced: 2.0.0 to support Tiger 2010 structured data and revised some logic to improve speed and accuracy of geocoding. New parameter max_results useful for specifying ot just return the best result.</para>
+               
          </refsection>
 
 
      70 | POINT(-71.0646 42.35105)  |   31 | Stuart  | St   | Boston        | MA | 02116
 (11 rows)      </programlisting>
 
-<para>Using to do a batch geocode of addresses. USE DISTINCT ON to return the best address match (lowest rating), when more than one match is returned. Only process those not yet geocoded (have no rating).</para>
+<para>Using to do a batch geocode of addresses. Easiest is to set <varname>max_results=1</varname>. Only process those not yet geocoded (have no rating).</para>
 <programlisting>CREATE TABLE addresses_to_geocode(addid serial PRIMARY KEY, address text,
                lon numeric, lat numeric, new_address text, rating integer);
 
@@ -122,30 +123,30 @@ VALUES ('529 Main Street, Boston MA, 02129'),
  ('124 Mount Auburn St, Cambridge, Massachusetts 02138'),
  ('950 Main Street, Worcester, MA 01610');
  
--- only update the first two addresses (850 ms) --
+-- only update the first two addresses (323-704 ms -  there are caching and shared memory effects so first geocode you do is always slower) --
 -- for large numbers of addresses you don't want to update all at once
 -- since the whole geocode must commit at once 
 UPDATE addresses_to_geocode
   SET  (rating, new_address, lon, lat) 
-       = (g.rating, pprint_addy(g.addy),
-          ST_X(g.geomout)::numeric(8,5), ST_Y(g.geomout)::numeric(8,5) )
-FROM (SELECT DISTINCT ON (addid) addid, (g1.geo).*
-       FROM (SELECT addid,  (geocode(address)) As geo
-FROM addresses_to_geocode As ag
-       WHERE ag.rating IS NULL ) As g1
-ORDER BY addid, rating LIMIT 2) As g
+       = ( (g.geo).rating, pprint_addy((g.geo).addy),
+          ST_X((g.geo).geomout)::numeric(8,5), ST_Y((g.geo).geomout)::numeric(8,5) )
+FROM (SELECT addid, (geocode(address,1)) As geo
+    FROM addresses_to_geocode As ag
+       WHERE ag.rating IS NULL ORDER BY addid LIMIT 5) As g
 WHERE g.addid = addresses_to_geocode.addid;
 
 result
 -----
-2 rows affected, 850 ms execution time.
+5 rows affected, 345 ms execution time.
 
 SELECT * FROM addresses_to_geocode WHERE rating is not null;
-
- addid |                   address                    |    lon    |   lat    |              new_address                  | rating
- ------+----------------------------------------------+-----------+----------+-------------------------------------------+--------
-     1 | 529 Main Street, Boston MA, 02129            | -71.07187 | 42.38351 | 529 Main St, Boston, MA 02129             |      0
-     2 | 77 Massachusetts Avenue, Cambridge, MA 02139 | -71.09436 | 42.35981 | 77 Massachusetts Ave, Cambridge, MA 02139 |      0
+ addid |                       address                       |    lon    |   lat    |                new_address                | rating 
+-------+-----------------------------------------------------+-----------+----------+-------------------------------------------+--------
+     1 | 529 Main Street, Boston MA, 02129                   | -71.07187 | 42.38351 | 529 Main St, Boston, MA 02129             |      0
+     2 | 77 Massachusetts Avenue, Cambridge, MA 02139        | -71.09436 | 42.35981 | 77 Massachusetts Ave, Cambridge, MA 02139 |      0
+     3 | 28 Capen Street, Medford, MA                        | -71.12370 | 42.41108 | 28 Capen St, Medford, MA 02155            |      0
+     4 | 124 Mount Auburn St, Cambridge, Massachusetts 02138 | -71.12298 | 42.37336 | 124 Mount Auburn St, Cambridge, MA 02138  |      0
+     5 | 950 Main Street, Worcester, MA 01610                | -71.82361 | 42.24948 | 950 Main St, Worcester, MA 01610          |      0
 </programlisting>
          </refsection>
 
index e09170a79118978931832d7991f15b34f7054936..34b0bcf6ba139f3ddf3cefafa8adfd72b8ff6966 100644 (file)
@@ -1,6 +1,6 @@
 --$Id$
 CREATE OR REPLACE FUNCTION geocode(
-    input VARCHAR,
+    input VARCHAR, max_results integer DEFAULT 10,
     OUT ADDY NORM_ADDY,
     OUT GEOMOUT GEOMETRY,
     OUT RATING INTEGER
@@ -20,7 +20,7 @@ BEGIN
     RETURN;
   END IF;
 
-  FOR rec IN SELECT * FROM geocode(ADDY)
+/*  FOR rec IN SELECT * FROM geocode(ADDY)
   LOOP
 
     ADDY := rec.addy;
@@ -28,16 +28,16 @@ BEGIN
     RATING := rec.rating;
 
     RETURN NEXT;
-  END LOOP;
-
-  RETURN;
+  END LOOP;*/
+  RETURN QUERY SELECT g.addy, g.geomout, g.rating FROM geocode(ADDY, max_results) As g ORDER BY g.rating;
 
 END;
 $_$ LANGUAGE plpgsql STABLE;
 
 
 CREATE OR REPLACE FUNCTION geocode(
-    IN_ADDY NORM_ADDY,
+    IN_ADDY NORM_ADDY, max_results integer DEFAULT 10,
     OUT ADDY NORM_ADDY,
     OUT GEOMOUT GEOMETRY,
     OUT RATING INTEGER
@@ -85,7 +85,7 @@ BEGIN
               (a.addy).zip,
               a.rating
           ) as b
-        ORDER BY b.rating
+        ORDER BY b.rating LIMIT max_results
     LOOP
 
       ADDY := rec.addy;
index fc03a30df5447e49ffdc6beba95c854c0647d5d0..9be9edcb118e86863f66a8ee84b3bdbd26424ec0 100644 (file)
@@ -24,6 +24,8 @@ CREATE INDEX tiger_place_the_geom_gist ON place USING gist(the_geom);
 CREATE INDEX tiger_edges_the_geom_gist ON edges USING gist(the_geom);
 CREATE INDEX tiger_state_the_geom_gist ON faces USING gist(the_geom);
 DROP FUNCTION IF EXISTS reverse_geocode(geometry); /** changed to use default parameters **/
+DROP FUNCTION IF EXISTS geocode(varchar); /** changed to include default parameter for max_results **/
+DROP FUNCTION IF EXISTS geocode(norm_addy); /** changed to include default parameter for max_results **/
 
 -- TODO: Put in logic to update lookup tables as they change.  street_type_lookup has changed since initial release --
 CREATE TABLE zcta5