I am learning postgis 2.1. I created a postgis table from a shapefile and imported it into the DB. It made a table like this:
db=# \d districts
...
geog | geography(MultiPolygon,4326) |
I also created a table "callsforservice" importing tabular data from a CSV, which I then converted into points with a SRID = 4326.
db=# update callsforservice set latlongpointdetails = ST_SetSRID(latlongpoint, 4326);
I want to know which callsforservice.latlongpointdetails
are included in which districts.geogs
I tried with this query, which takes very, very, very long time. The limit 1 is only to shorten the time the query is running. After 2 min or so I kill it:
select * from callsforservice, districts where ST_Within(geometry(districts.geog), callsforservice.latlongpointdetails) limit 1;
If I add an additional condition to the where clause (where districts.district='1-1'
) — this query returns immediately with 0 rows, even though districts does have a row with this ID.
Do I have the syntax right for finding out which calls came in what districts?
The docs for ST_within say "the source geometries must both be of the same coordinate projection, having the same SRID." If I examine the two tables with the \dt
command then the geog column in districts shows type geography(MultiPolygon,4326)
but the latlongpointdetails
column in callsforservices only shows type geometry — without parenthesis like in the districts table. Maybe this is the reason for the failures of ST_Within? Where am I going wrong?
Best Answer
You shouldn't be mixing geometry with geography in your query. If all you are going to do is convert your geography to geometry (which is what geometry(districts.geog) does), there isn't any point in having it as geography. What would make more sense is to change your callsforservice.latlongpointdetails to geography type since geography is more correct.
You also want to make sure that your latlongpointdetails is in long,lat (not lat,long). You don't need && if you are comparing apples with apples. ST_Within has a && call built into it. Also I don't think ST_Within is supported for geography (well not listed, though surprise it doesn't), and your ST_Within (should be point within polygon not polygon within point) call looks backward to me so not sure how you are getting anything back. Use ST_Covers instead -- http://postgis.net/docs/manual-2.1/ST_Covers.html