From: Sarah Hoffmann Date: Tue, 3 Jul 2012 20:44:06 +0000 (+0200) Subject: excluded place nodes outside parent boundaries from addresses X-Git-Tag: v2.0.0~43^2~1 X-Git-Url: https://git.openstreetmap.org/nominatim.git/commitdiff_plain/afc429fd928be4be76a3d74179a431ce7a9a8b0d?ds=sidebyside excluded place nodes outside parent boundaries from addresses Changes slightly the logic which decides if a guessed places (i.e. a place node) is included in an address: it will be part of the address only if it is inside the next lower available boundary. This fixes problematic cases where neighbouring entities have additional admin levels. --- diff --git a/sql/functions.sql b/sql/functions.sql index 03ea4011..0a53fd64 100644 --- a/sql/functions.sql +++ b/sql/functions.sql @@ -1213,6 +1213,8 @@ DECLARE location_rank_search INTEGER; location_distance FLOAT; + location_parent GEOMETRY; + location_isaddress BOOLEAN; tagpairid INTEGER; @@ -1629,22 +1631,35 @@ BEGIN -- Process area matches location_rank_search := 100; location_distance := 0; --- RAISE WARNING ' getNearFeatures(%,''%'',%,''%'')',NEW.partition, place_centroid, search_maxrank, isin_tokens; + location_parent := NULL; + -- RAISE WARNING ' getNearFeatures(%,''%'',%,''%'')',NEW.partition, place_centroid, search_maxrank, isin_tokens; FOR location IN SELECT * from getNearFeatures(NEW.partition, place_centroid, search_maxrank, isin_tokens) LOOP --RAISE WARNING ' AREA: %',location; IF location.rank_search < location_rank_search THEN location_rank_search := location.rank_search; - location_distance := location.distance * 1.5; + location_distance := location.distance * 0.5; END IF; IF location.distance < location_distance OR NOT location.isguess THEN + location_isaddress := NOT address_havelevel[location.rank_address]; + IF location_isaddress AND location.isguess AND location_parent IS NOT NULL THEN + location_isaddress := ST_Contains(location_parent,location.centroid); + END IF; + + -- RAISE WARNING '% isaddress: %', location.place_id, location_isaddress; -- Add it to the list of search terms nameaddress_vector := array_merge(nameaddress_vector, location.keywords::integer[]); - INSERT INTO place_addressline VALUES (NEW.place_id, location.place_id, true, NOT address_havelevel[location.rank_address], location.distance, location.rank_address); - address_havelevel[location.rank_address] := true; + INSERT INTO place_addressline VALUES (NEW.place_id, location.place_id, true, location_isaddress, location.distance, location.rank_address); + + IF location_isaddress THEN + address_havelevel[location.rank_address] := true; + IF NOT location.isguess THEN + SELECT geometry FROM placex WHERE place_id = location.place_id INTO location_parent; + END IF; + END IF; --RAISE WARNING ' Terms: (%) %',location, nameaddress_vector; @@ -1690,7 +1705,7 @@ BEGIN IF location.rank_search < location_rank_search THEN location_rank_search := location.rank_search; - location_distance := location.distance * 1.5; + location_distance := location.distance * 0.5; END IF; IF location.distance < location_distance THEN diff --git a/sql/partitions.src.sql b/sql/partitions.src.sql index df4b3b16..324f35bb 100644 --- a/sql/partitions.src.sql +++ b/sql/partitions.src.sql @@ -13,6 +13,17 @@ create type nearfeature as ( isguess boolean ); +drop type nearfeaturecentr cascade; +create type nearfeaturecentr as ( + place_id BIGINT, + keywords int[], + rank_address integer, + rank_search integer, + distance float, + isguess boolean, + centroid GEOMETRY +); + CREATE TABLE location_area_country () INHERITS (location_area_large); CREATE INDEX idx_location_area_country_geometry ON location_area_country USING GIST (geometry); @@ -46,21 +57,21 @@ CREATE INDEX idx_location_road_-partition-_place_id ON location_road_-partition- -- end -create or replace function getNearFeatures(in_partition INTEGER, point GEOMETRY, maxrank INTEGER, isin_tokens INT[]) RETURNS setof nearfeature AS $$ +create or replace function getNearFeatures(in_partition INTEGER, point GEOMETRY, maxrank INTEGER, isin_tokens INT[]) RETURNS setof nearfeaturecentr AS $$ DECLARE - r nearfeature%rowtype; + r nearfeaturecentr%rowtype; BEGIN -- start IF in_partition = -partition- THEN FOR r IN - SELECT place_id, keywords, rank_address, rank_search, min(ST_Distance(point, centroid)) as distance, isguess FROM ( + SELECT place_id, keywords, rank_address, rank_search, min(ST_Distance(point, centroid)) as distance, isguess, centroid FROM ( SELECT * FROM location_area_large_-partition- WHERE ST_Contains(geometry, point) and rank_search < maxrank UNION ALL SELECT * FROM location_area_country WHERE ST_Contains(geometry, point) and rank_search < maxrank ) as location_area GROUP BY place_id, keywords, rank_address, rank_search, isguess, centroid - ORDER BY rank_address desc, isin_tokens && keywords desc, isguess asc, + ORDER BY rank_address, isin_tokens && keywords desc, isguess asc, ST_Distance(point, centroid) * CASE WHEN rank_address = 16 AND rank_search = 15 THEN 0.2 -- capital city