]> granicus.if.org Git - postgresql/commitdiff
Fix support for some operators (&<, &>, $<|, |&>) in box operator class
authorTeodor Sigaev <teodor@sigaev.ru>
Tue, 21 Mar 2017 13:23:10 +0000 (16:23 +0300)
committerTeodor Sigaev <teodor@sigaev.ru>
Tue, 21 Mar 2017 13:23:10 +0000 (16:23 +0300)
of SP-GiST.

Bug exists since initial commit of box opclass for SP-GiST,
so backpath to 9.6

Author: Nikita Glukhov with minor editorization of tests by me
Reviewed-by: Kyotaro Horiguchi, Anastasia Lubennikova
https://commitfest.postgresql.org/13/981/

src/backend/utils/adt/geo_spgist.c
src/test/regress/expected/box.out
src/test/regress/expected/sanity_check.out
src/test/regress/sql/box.sql

index aacb3409bd2be3033e68e56e714c4c345bad8364..f6334bae14edda87d688b11c73e1a4366020a258 100644 (file)
@@ -286,6 +286,14 @@ lower2D(RangeBox *range_box, Range *query)
                FPlt(range_box->right.low, query->low);
 }
 
+/* Can any range from range_box not extend to the right side of the query? */
+static bool
+overLower2D(RangeBox *range_box, Range *query)
+{
+       return FPle(range_box->left.low, query->high) &&
+               FPle(range_box->right.low, query->high);
+}
+
 /* Can any range from range_box to be higher than this argument? */
 static bool
 higher2D(RangeBox *range_box, Range *query)
@@ -294,6 +302,14 @@ higher2D(RangeBox *range_box, Range *query)
                FPgt(range_box->right.high, query->high);
 }
 
+/* Can any range from range_box not extend to the left side of the query? */
+static bool
+overHigher2D(RangeBox *range_box, Range *query)
+{
+       return FPge(range_box->left.high, query->low) &&
+               FPge(range_box->right.high, query->low);
+}
+
 /* Can any rectangle from rect_box be left of this argument? */
 static bool
 left4D(RectBox *rect_box, RangeBox *query)
@@ -305,7 +321,7 @@ left4D(RectBox *rect_box, RangeBox *query)
 static bool
 overLeft4D(RectBox *rect_box, RangeBox *query)
 {
-       return lower2D(&rect_box->range_box_x, &query->right);
+       return overLower2D(&rect_box->range_box_x, &query->left);
 }
 
 /* Can any rectangle from rect_box be right of this argument? */
@@ -319,7 +335,7 @@ right4D(RectBox *rect_box, RangeBox *query)
 static bool
 overRight4D(RectBox *rect_box, RangeBox *query)
 {
-       return higher2D(&rect_box->range_box_x, &query->right);
+       return overHigher2D(&rect_box->range_box_x, &query->left);
 }
 
 /* Can any rectangle from rect_box be below of this argument? */
@@ -333,7 +349,7 @@ below4D(RectBox *rect_box, RangeBox *query)
 static bool
 overBelow4D(RectBox *rect_box, RangeBox *query)
 {
-       return lower2D(&rect_box->range_box_y, &query->left);
+       return overLower2D(&rect_box->range_box_y, &query->right);
 }
 
 /* Can any rectangle from rect_box be above of this argument? */
@@ -347,7 +363,7 @@ above4D(RectBox *rect_box, RangeBox *query)
 static bool
 overAbove4D(RectBox *rect_box, RangeBox *query)
 {
-       return higher2D(&rect_box->range_box_y, &query->right);
+       return overHigher2D(&rect_box->range_box_y, &query->right);
 }
 
 /*
index 5f8b9455e8bf0504172ea1579b450bcefb824c4d..49af242c8ce7f45e560808f1e3f4997216440078 100644 (file)
@@ -455,3 +455,107 @@ EXPLAIN (COSTS OFF) SELECT * FROM box_temp WHERE f1 ~= '(20,20),(40,40)';
 
 RESET enable_seqscan;
 DROP INDEX box_spgist;
+--
+-- Test the SP-GiST index on the larger volume of data
+--
+CREATE TABLE quad_box_tbl (b box);
+INSERT INTO quad_box_tbl
+       SELECT box(point(x * 10, y * 10), point(x * 10 + 5, y * 10 + 5))
+       FROM generate_series(1, 100) x,
+                generate_series(1, 100) y;
+-- insert repeating data to test allTheSame
+INSERT INTO quad_box_tbl
+       SELECT '((200, 300),(210, 310))'
+       FROM generate_series(1, 1000);
+INSERT INTO quad_box_tbl
+       VALUES
+               (NULL),
+               (NULL),
+               ('((-infinity,-infinity),(infinity,infinity))'),
+               ('((-infinity,100),(-infinity,500))'),
+               ('((-infinity,-infinity),(700,infinity))');
+CREATE INDEX quad_box_tbl_idx ON quad_box_tbl USING spgist(b);
+SET enable_seqscan = OFF;
+SET enable_indexscan = ON;
+SET enable_bitmapscan = ON;
+SELECT count(*) FROM quad_box_tbl WHERE b <<  box '((100,200),(300,500))';
+ count 
+-------
+   901
+(1 row)
+
+SELECT count(*) FROM quad_box_tbl WHERE b &<  box '((100,200),(300,500))';
+ count 
+-------
+  3901
+(1 row)
+
+SELECT count(*) FROM quad_box_tbl WHERE b &&  box '((100,200),(300,500))';
+ count 
+-------
+  1653
+(1 row)
+
+SELECT count(*) FROM quad_box_tbl WHERE b &>  box '((100,200),(300,500))';
+ count 
+-------
+ 10100
+(1 row)
+
+SELECT count(*) FROM quad_box_tbl WHERE b >>  box '((100,200),(300,500))';
+ count 
+-------
+  7000
+(1 row)
+
+SELECT count(*) FROM quad_box_tbl WHERE b >>  box '((100,200),(300,500))';
+ count 
+-------
+  7000
+(1 row)
+
+SELECT count(*) FROM quad_box_tbl WHERE b <<| box '((100,200),(300,500))';
+ count 
+-------
+  1900
+(1 row)
+
+SELECT count(*) FROM quad_box_tbl WHERE b &<| box '((100,200),(300,500))';
+ count 
+-------
+  5901
+(1 row)
+
+SELECT count(*) FROM quad_box_tbl WHERE b |&> box '((100,200),(300,500))';
+ count 
+-------
+  9100
+(1 row)
+
+SELECT count(*) FROM quad_box_tbl WHERE b |>> box '((100,200),(300,500))';
+ count 
+-------
+  5000
+(1 row)
+
+SELECT count(*) FROM quad_box_tbl WHERE b @>  box '((201,301),(202,303))';
+ count 
+-------
+  1003
+(1 row)
+
+SELECT count(*) FROM quad_box_tbl WHERE b <@  box '((100,200),(300,500))';
+ count 
+-------
+  1600
+(1 row)
+
+SELECT count(*) FROM quad_box_tbl WHERE b ~=  box '((200,300),(205,305))';
+ count 
+-------
+     1
+(1 row)
+
+RESET enable_seqscan;
+RESET enable_indexscan;
+RESET enable_bitmapscan;
index b5eff55e9b31752fae3359ea2c1d98a0eb96ff2d..88b4c973a1650482623f9932d31ed58ead4ab3ef 100644 (file)
@@ -155,6 +155,7 @@ pg_type|t
 pg_user_mapping|t
 point_tbl|t
 polygon_tbl|t
+quad_box_tbl|t
 quad_point_tbl|t
 radix_text_tbl|t
 ramp|f
index 128a016963520e854812922750ca850356f15a12..135ac108ebdb28e7cf96ca0d72d4826afedef2ed 100644 (file)
@@ -179,3 +179,50 @@ EXPLAIN (COSTS OFF) SELECT * FROM box_temp WHERE f1 ~= '(20,20),(40,40)';
 RESET enable_seqscan;
 
 DROP INDEX box_spgist;
+
+--
+-- Test the SP-GiST index on the larger volume of data
+--
+CREATE TABLE quad_box_tbl (b box);
+
+INSERT INTO quad_box_tbl
+       SELECT box(point(x * 10, y * 10), point(x * 10 + 5, y * 10 + 5))
+       FROM generate_series(1, 100) x,
+                generate_series(1, 100) y;
+
+-- insert repeating data to test allTheSame
+INSERT INTO quad_box_tbl
+       SELECT '((200, 300),(210, 310))'
+       FROM generate_series(1, 1000);
+
+INSERT INTO quad_box_tbl
+       VALUES
+               (NULL),
+               (NULL),
+               ('((-infinity,-infinity),(infinity,infinity))'),
+               ('((-infinity,100),(-infinity,500))'),
+               ('((-infinity,-infinity),(700,infinity))');
+
+CREATE INDEX quad_box_tbl_idx ON quad_box_tbl USING spgist(b);
+
+SET enable_seqscan = OFF;
+SET enable_indexscan = ON;
+SET enable_bitmapscan = ON;
+
+SELECT count(*) FROM quad_box_tbl WHERE b <<  box '((100,200),(300,500))';
+SELECT count(*) FROM quad_box_tbl WHERE b &<  box '((100,200),(300,500))';
+SELECT count(*) FROM quad_box_tbl WHERE b &&  box '((100,200),(300,500))';
+SELECT count(*) FROM quad_box_tbl WHERE b &>  box '((100,200),(300,500))';
+SELECT count(*) FROM quad_box_tbl WHERE b >>  box '((100,200),(300,500))';
+SELECT count(*) FROM quad_box_tbl WHERE b >>  box '((100,200),(300,500))';
+SELECT count(*) FROM quad_box_tbl WHERE b <<| box '((100,200),(300,500))';
+SELECT count(*) FROM quad_box_tbl WHERE b &<| box '((100,200),(300,500))';
+SELECT count(*) FROM quad_box_tbl WHERE b |&> box '((100,200),(300,500))';
+SELECT count(*) FROM quad_box_tbl WHERE b |>> box '((100,200),(300,500))';
+SELECT count(*) FROM quad_box_tbl WHERE b @>  box '((201,301),(202,303))';
+SELECT count(*) FROM quad_box_tbl WHERE b <@  box '((100,200),(300,500))';
+SELECT count(*) FROM quad_box_tbl WHERE b ~=  box '((200,300),(205,305))';
+
+RESET enable_seqscan;
+RESET enable_indexscan;
+RESET enable_bitmapscan;