Use a combined centroid/categories index for category search
The plain ltree index on categories is not spatial, so a category
search bounded by a viewbox or a search area had to combine it with
a second index and AND two large bitmaps together. On a full planet
that made the near search take 510ms and the bounded POI search
106ms, against 22ms and 0.7ms for the place_classtype tables they
replace.
Put the centroid in front of the categories in a combined GiST index
instead. Measured on a full planet import, that brings the POI search
to 1.2ms and the near search to 74ms.
Two details on the definition. The centroid comes first because a
GiST index is ineffective when its first column has few distinct
values, which is exactly what the lossy signatures of the categories
column are; it also builds faster and smaller (12:22 and 5125MB
against 19:45 and 5376MB for the other order). The index is not
partial because the predicate would otherwise make it unusable for
queries on the centroid alone, which cost only 10 to 20% on the
category queries but takes a plain centroid lookup from a sequential
scan to an index scan.
siglen=8 keeps the size manageable. The default for gist__ltree_ops
is 28 bytes, which on a planet with full category coverage would put
the index well above the 22GB it takes now.
The index gets a new name, so the now unused idx_placex_categories
is simply dropped from the earlier migration rather than replaced.
Since that migration is already released, the new index needs a
migration step of its own.