From 66dde8a54ecf91d97eb1ae4a6209e0e2dddcec97 Mon Sep 17 00:00:00 2001 From: Monty Date: Wed, 16 Nov 2022 14:52:47 +0200 Subject: [PATCH] Added rowid_filter support to Aria This includes: - cleanup and optimization of filtering and pushdown engine code. - Adjusted costs for rowid filters (based on extensive testing and profiling). This made a small two changes to the handler_rowid_filter_is_active() API: - One should not call it with a zero pointer! - One does not need to call handler_rowid_filter_is_active() for every row anymore. It is enough to check if filter is active by calling it call it during index_init() or when handler::rowid_filter_changed() is called The changes was to avoid unnecessary function calls and checks if pushdown conditions and rowid_filter is not used. Updated costs for rowid_filter_lookup() to be closer to reality. The old cost was based only on rowid_compare_cost. This is now changed to take into account the overhead in checking the rowid. Changed the Range_rowid_filter class to use DYNAMIC_ARRAY directly instead of Dynamic_array<>. This was done to be able to use the new append_dynamic() functions which gives a notable speed improvment compared to the old code. Removing the abstraction also makes the code easier to understand. The cost of filtering is now slightly lower than before, which is reflected in some test cases that is now using rowid filters. --- include/my_compare.h | 1 - include/my_sys.h | 12 + mysql-test/main/opt_trace.result | 22 +- mysql-test/main/opt_trace_index_merge.result | 31 +- mysql-test/main/optimizer_costs.result | 4 +- mysql-test/main/range.result | 2 +- mysql-test/main/rowid_filter.result | 692 ------ mysql-test/main/rowid_filter.test | 408 ---- mysql-test/main/rowid_filter_aria.result | 2217 ++++++++++++++++++ mysql-test/main/rowid_filter_aria.test | 9 + mysql-test/main/rowid_filter_innodb.result | 692 ------ mysql-test/main/rowid_filter_myisam.result | 673 ++++++ mysql-test/main/rowid_filter_myisam.test | 404 ++++ mysql-test/suite/maria/icp.result | 2 +- mysys/array.c | 43 +- sql/handler.cc | 3 +- sql/handler.h | 19 +- sql/optimizer_defaults.h | 7 + sql/rowid_filter.cc | 59 +- sql/rowid_filter.h | 68 +- sql/sql_analyze_stmt.h | 3 +- sql/uniques.cc | 3 +- storage/innobase/row/row0sel.cc | 6 +- storage/maria/ha_maria.cc | 45 +- storage/maria/ha_maria.h | 2 + storage/maria/ma_extra.c | 9 + storage/maria/ma_info.c | 8 - storage/maria/ma_key.c | 40 +- storage/maria/ma_rkey.c | 1 + storage/maria/maria_def.h | 30 +- storage/myisam/ha_myisam.cc | 30 +- storage/myisam/ha_myisam.h | 5 +- storage/myisam/mi_extra.c | 4 +- storage/myisam/mi_key.c | 42 +- storage/myisam/mi_rkey.c | 2 +- storage/myisam/myisamdef.h | 13 +- 36 files changed, 3614 insertions(+), 1997 deletions(-) create mode 100644 mysql-test/main/rowid_filter_aria.result create mode 100644 mysql-test/main/rowid_filter_aria.test diff --git a/include/my_compare.h b/include/my_compare.h index c2cb9ae46b9..62bb6ac0ed4 100644 --- a/include/my_compare.h +++ b/include/my_compare.h @@ -154,6 +154,5 @@ typedef enum check_result { typedef check_result_t (*index_cond_func_t)(void *param); typedef check_result_t (*rowid_filter_func_t)(void *param); -typedef int (*rowid_filter_is_active_func_t)(void *param); #endif /* _my_compare_h */ diff --git a/include/my_sys.h b/include/my_sys.h index 58141fda9a9..f52510d629e 100644 --- a/include/my_sys.h +++ b/include/my_sys.h @@ -353,6 +353,14 @@ typedef struct st_dynamic_array myf malloc_flags; } DYNAMIC_ARRAY; + +typedef struct st_dynamic_array_append +{ + DYNAMIC_ARRAY *array; + uchar *pos, *end; +} DYNAMIC_ARRAY_APPEND; + + typedef struct st_my_tmpdir { DYNAMIC_ARRAY full_list; @@ -856,6 +864,10 @@ extern void freeze_size(DYNAMIC_ARRAY *array); #define push_dynamic(A,B) insert_dynamic((A),(B)) #define reset_dynamic(array) ((array)->elements= 0) #define sort_dynamic(A,cmp) my_qsort((A)->buffer, (A)->elements, (A)->size_of_element, (cmp)) +extern void init_append_dynamic(DYNAMIC_ARRAY_APPEND *append, + DYNAMIC_ARRAY *array); +extern my_bool append_dynamic(DYNAMIC_ARRAY_APPEND *append, + const void * element); extern my_bool init_dynamic_string(DYNAMIC_STRING *str, const char *init_str, size_t init_alloc,size_t alloc_increment); diff --git a/mysql-test/main/opt_trace.result b/mysql-test/main/opt_trace.result index 158df0b1e9a..70c59092dbd 100644 --- a/mysql-test/main/opt_trace.result +++ b/mysql-test/main/opt_trace.result @@ -12239,16 +12239,16 @@ explain select * from t1 where a<10 and b between 10 and 50 and c < 10 { "rowid_filter_index": "b", "index_only_cost": 0.001515222, "filter_startup_cost": 3.004222e-4, - "find_key_and_filter_lookup_cost": 6.445451e-4, + "find_key_and_filter_lookup_cost": 7.827422e-4, "filter_selectivity": 0.021, "original_rows": 9, "new_rows": 0.189, "original_access_cost": 0.011516778, - "with_filter_access_cost": 0.0023698, + "with_filter_access_cost": 0.002507997, "original_found_rows_cost": 0.010001556, "with_filter_found_rows_cost": 2.100327e-4, "org_cost": 0.011804778, - "filter_cost": 0.00267627, + "filter_cost": 0.002814467, "filter_used": true }, "access_type": "range", @@ -12256,7 +12256,7 @@ explain select * from t1 where a<10 and b between 10 and 50 and c < 10 { "rows": 9, "rows_after_filter": 0.189, "rows_out": 0.017766, - "cost": 0.00267627, + "cost": 0.002814467, "chosen": true } ], @@ -12264,7 +12264,7 @@ explain select * from t1 where a<10 and b between 10 and 50 and c < 10 { "type": "range", "rows_read": 0.189, "rows_out": 0.017766, - "cost": 0.00267627, + "cost": 0.002814467, "uses_join_buffering": false, "rowid_filter_index": "b" } @@ -12276,7 +12276,7 @@ explain select * from t1 where a<10 and b between 10 and 50 and c < 10 { "plan_prefix": "", "table": "t1", "rows_for_plan": 0.017766, - "cost_for_plan": 0.00267627, + "cost_for_plan": 0.002814467, "pushdown_cond_selectivity": 0.094, "filtered": 0.1974, "rows_out": 0.017766 @@ -12286,7 +12286,7 @@ explain select * from t1 where a<10 and b between 10 and 50 and c < 10 { { "best_join_order": ["t1"], "rows": 0.017766, - "cost": 0.00267627 + "cost": 0.002814467 }, { "table": "t1", @@ -12674,20 +12674,20 @@ explain format=json select * from three, t1 where t1.a=three.a and t1.b<5000 and "rowid_filter_index": "b", "index_only_cost": 0.092006157, "filter_startup_cost": 0.149564727, - "find_key_and_filter_lookup_cost": 0.085742374, + "find_key_and_filter_lookup_cost": 0.129350121, "filter_selectivity": 0.4312, "original_rows": 1000, "new_rows": 431.2, "original_access_cost": 1.203290157, - "with_filter_access_cost": 0.656934192, + "with_filter_access_cost": 0.700541939, "original_found_rows_cost": 1.111284, "with_filter_found_rows_cost": 0.479185661, "org_cost": 3.705870471, - "filter_cost": 2.161762502, + "filter_cost": 2.292585745, "filter_used": true }, "rows": 431.2, - "cost": 2.161762502, + "cost": 2.292585745, "chosen": true }, { diff --git a/mysql-test/main/opt_trace_index_merge.result b/mysql-test/main/opt_trace_index_merge.result index 7d2833f1bd2..1970511a401 100644 --- a/mysql-test/main/opt_trace_index_merge.result +++ b/mysql-test/main/opt_trace_index_merge.result @@ -329,7 +329,7 @@ set optimizer_trace='enabled=on'; # 3-way ROR-intersection explain select key1,key2,key3 from t1 where key1=100 and key2=100 and key3=100; id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ref|filter key1,key2,key3 key1|key2 5|5 const 2243 (3%) Using where; Using rowid filter +1 SIMPLE t1 index_merge key1,key2,key3 key1,key2 5,5 NULL 77 Using intersect(key1,key2); Using where select JSON_DETAILED(JSON_EXTRACT(trace, '$**.analyzing_range_alternatives')) from INFORMATION_SCHEMA.OPTIMIZER_TRACE; JSON_DETAILED(JSON_EXTRACT(trace, '$**.analyzing_range_alternatives')) [ @@ -423,22 +423,6 @@ JSON_DETAILED(JSON_EXTRACT(trace, '$**.analyzing_range_alternatives')) }, "analyzing_index_merge_union": [] - }, - { - "range_scan_alternatives": - [ - { - "index": "key2", - "ranges": - ["(100) <= (key2) <= (100)"], - "rowid_ordered": true, - "using_mrr": false, - "index_only": true, - "rows": 2243, - "cost": 0.312832109, - "chosen": true - } - ] } ] select JSON_DETAILED(JSON_EXTRACT(trace, '$**.chosen_range_access_summary')) from INFORMATION_SCHEMA.OPTIMIZER_TRACE; @@ -473,19 +457,6 @@ JSON_DETAILED(JSON_EXTRACT(trace, '$**.chosen_range_access_summary')) "rows_for_plan": 77, "cost_for_plan": 0.572490756, "chosen": true - }, - { - "range_access_plan": - { - "type": "range_scan", - "index": "key2", - "rows": 2243, - "ranges": - ["(100) <= (key2) <= (100)"] - }, - "rows_for_plan": 2243, - "cost_for_plan": 0.312832109, - "chosen": true } ] # ROR-union(ROR-intersection, ROR-range) diff --git a/mysql-test/main/optimizer_costs.result b/mysql-test/main/optimizer_costs.result index a00673df02c..fefc03ae411 100644 --- a/mysql-test/main/optimizer_costs.result +++ b/mysql-test/main/optimizer_costs.result @@ -31,8 +31,8 @@ OPTIMIZER_DISK_READ_RATIO 0.020000 OPTIMIZER_ROW_COPY_COST 0.060866 OPTIMIZER_ROW_LOOKUP_COST 0.130839 OPTIMIZER_ROW_NEXT_FIND_COST 0.045916 -OPTIMIZER_ROWID_COMPARE_COST 0.001000 -OPTIMIZER_ROWID_COPY_COST 0.001000 +OPTIMIZER_ROWID_COMPARE_COST 0.002653 +OPTIMIZER_ROWID_COPY_COST 0.002653 ENGINE default OPTIMIZER_DISK_READ_COST 10.240000 OPTIMIZER_INDEX_BLOCK_COPY_COST 0.035600 diff --git a/mysql-test/main/range.result b/mysql-test/main/range.result index 0bd56723d4b..34c0c27f897 100644 --- a/mysql-test/main/range.result +++ b/mysql-test/main/range.result @@ -1967,7 +1967,7 @@ select count(*) from t2 left join t1 on (t1.key1 < 3 or t1.key1 between 920 and 930) and t1.key2 < 1000; id select_type table type possible_keys key key_len ref rows Extra 1 SIMPLE t2 ALL NULL NULL NULL NULL 64 -1 SIMPLE t1 range|filter i1,i2 i1|i2 4|4 NULL 12 (89%) Using where; Using join buffer (flat, BNL join); Using rowid filter +1 SIMPLE t1 range i1,i2 i1 4 NULL 12 Using where; Using join buffer (flat, BNL join) select count(*) from t2 left join t1 on (t1.key1 < 3 or t1.key1 between 920 and 930) and t1.key2 < 1000; count(*) diff --git a/mysql-test/main/rowid_filter.result b/mysql-test/main/rowid_filter.result index 48a01b31e64..0b79e5fff6a 100644 --- a/mysql-test/main/rowid_filter.result +++ b/mysql-test/main/rowid_filter.result @@ -2214,695 +2214,3 @@ ALTER TABLE orders DROP COLUMN o_totaldiscount; DROP VIEW v1; DROP DATABASE dbt3_s001; use test; -# -# MDEV-18816: potential range filter for one join table with -# impossible WHERE for another -# -create table t1 ( -pk int not null primary key, c2 varchar(10) , i1 int,key (c2) -) engine=myisam; -insert into t1 values (1,'a',-5),(2,'a',null); -create table t2 ( -pk int, i1 int, c1 varchar(30) , key c1 (c1(30)), key i1 (i1) -) engine=myisam; -insert into t2 values -(1,-5,'a'),(2,null,'a'),(3,null,'a'),(4,null,'a'),(5,5,'a'),(6,null,'a'), -(7,4,'a'),(8,55,'a'),(9,null,'a'),(10,null,'a'),(11,null,'a'),(12,-5,'a'), -(13,-5,'a'),(14,null,'a'),(15,null,'a'),(16,-5,'a'),(17,-5,'a'); -select 1 -from t1 -left join -t2 join t1 as t1_a on t2.i1 = t1_a.pk -on t1.c2 = t2.c1 -where t1_a.pk is null and t1_a.i1 != 3; -1 -explain extended select 1 -from t1 -left join -t2 join t1 as t1_a on t2.i1 = t1_a.pk -on t1.c2 = t2.c1 -where t1_a.pk is null and t1_a.i1 != 3; -id select_type table type possible_keys key key_len ref rows filtered Extra -1 SIMPLE NULL NULL NULL NULL NULL NULL NULL NULL Impossible WHERE noticed after reading const tables -Warnings: -Note 1003 select 1 AS `1` from `test`.`t1` join `test`.`t2` join `test`.`t1` `t1_a` where 0 -drop table t1,t2; -# -# MDEV-18640: TABLE::prune_range_rowid_filters: Conditional jump or -# move depends on uninitialized value -# -CREATE TABLE t1 ( -pk INT, i INT, PRIMARY KEY (pk), KEY (pk,i) -) ENGINE=MyISAM; -INSERT INTO t1 VALUES (1,10), (7,70), (2,20); -SELECT * FROM t1 WHERE pk < 5; -pk i -1 10 -2 20 -DROP TABLE t1; -# -# MDEV-18956: Possible rowid filter for subquery for which -# in_to_exists strategy has been chosen -# -CREATE TABLE t1 (pk int) engine=myisam ; -INSERT INTO t1 VALUES (1),(2); -CREATE TABLE t2 ( -pk int auto_increment PRIMARY KEY, -i1 int, i2 int, c2 varchar(1), -KEY (i1), KEY (i2) -) engine=myisam; -INSERT INTO t2 VALUES -(1,8,6,'t'),(2,5,7,'i'),(3,4,4,'h'),(4,207,38,'d'),(5,183,206,'b'), -(6,7,null,'o'),(7,1,2,'j'),(8,17,36,'s'),(9,4,5,'q'),(10,0,6,'l'), -(11,1,9,'j'),(12,5,6,'y'),(13,null,0,'i'),(14,7,7,'x'),(15,5,2,'u'); -SELECT * FROM t1 HAVING (7, 9) IN (SELECT t2.i1, t2.i2 FROM t2 WHERE t2.i1 = 3); -pk -EXPLAIN EXTENDED -SELECT * FROM t1 HAVING (7, 9) IN (SELECT t2.i1, t2.i2 FROM t2 WHERE t2.i1 = 3); -id select_type table type possible_keys key key_len ref rows filtered Extra -1 PRIMARY NULL NULL NULL NULL NULL NULL NULL NULL Impossible HAVING -2 SUBQUERY NULL NULL NULL NULL NULL NULL NULL NULL no matching row in const table -Warnings: -Note 1003 /* select#1 */ select `test`.`t1`.`pk` AS `pk` from `test`.`t1` having 0 -DROP TABLE t1,t2; -# -# MDEV-19255: rowid range filter built for range condition -# that uses in expensive subquery -# -CREATE TABLE t1 ( -pk1 INT PRIMARY KEY, a1 INT, b1 VARCHAR(1), KEY(a1), KEY(b1) -) ENGINE=MyISAM; -INSERT INTO t1 VALUES -(10,0,'z'),(11,3,'j'),(12,8,'f'),(13,8,'p'),(14,6,'w'),(15,0,'c'),(16,1,'j'), -(17,1,'f'),(18,5,'v'),(19,3,'f'),(20,2,'q'),(21,8,'y'),(22,0,'a'),(23,9,'w'), -(24,3,'e'),(25,1,'b'),(26,9,'r'),(27,2,'k'),(28,5,'c'),(29,3,'k'),(30,9,'b'), -(31,8,'j'),(32,1,'t'),(33,8,'n'),(34,3,'z'),(35,0,'u'),(36,3,'a'),(37,3,'g'), -(38,1,'f'),(39,6,'p'),(40,6,'m'),(41,6,'t'),(42,7,'i'),(43,4,'h'),(44,3,'d'), -(45,2,'b'),(46,1,'o'),(47,2,'j'),(48,6,'s'),(49,5,'q'),(50,6,'l'),(51,9,'j'), -(52,6,'y'),(53,0,'i'),(54,7,'x'),(55,2,'u'),(56,6,'t'),(57,4,'b'),(58,5,'m'), -(59,4,'x'),(60,8,'x'),(61,6,'v'),(62,8,'m'),(63,4,'j'),(64,8,'z'),(65,2,'a'), -(66,9,'i'),(67,4,'g'),(68,8,'h'),(69,1,'p'),(70,8,'a'),(71,0,'x'),(72,2,'s'), -(73,6,'k'),(74,0,'m'),(75,6,'e'),(76,9,'y'),(77,7,'d'),(78,7,'w'),(79,6,'y'), -(80,9,'s'),(81,9,'x'),(82,6,'l'),(83,9,'f'),(84,8,'x'),(85,1,'p'),(86,7,'y'), -(87,6,'p'),(88,1,'g'),(89,3,'c'),(90,5,'h'),(91,3,'p'),(92,2,'b'),(93,1,NULL), -(94,3,NULL),(95,2,'y'),(96,7,'s'),(97,7,'x'),(98,6,'i'),(99,9,'t'),(100,5,'j'), -(101,0,'u'),(102,7,'r'),(103,2,'x'),(104,8,'e'),(105,8,'i'),(106,5,'q'), -(107,8,'z'),(108,3,'k'),(109,65,NULL); -CREATE TABLE t2 (pk2 INT PRIMARY KEY, a2 INT, b2 VARCHAR(1)) ENGINE=MyISAM; -INSERT INTO t2 VALUES (1,1,'i'); -INSERT INTO t2 SELECT * FROM t1; -INSERT INTO t1 SELECT pk1+200, a1, b1 FROM t1; -INSERT INTO t1 SELECT pk1+400, a1, b1 FROM t1; -ANALYZE TABLE t1,t2 PERSISTENT FOR ALL; -Table Op Msg_type Msg_text -test.t1 analyze status Engine-independent statistics collected -test.t1 analyze status OK -test.t2 analyze status Engine-independent statistics collected -test.t2 analyze status OK -SELECT * FROM t1 INNER JOIN t2 ON ( pk1+1 = pk2+2 AND a1 = a2 ) -WHERE b1 <= ( SELECT MAX(b2) FROM t2 WHERE pk2 <= 1 ); -pk1 a1 b1 pk2 a2 b2 -17 1 f 16 1 j -37 3 g 36 3 a -105 8 i 104 8 e -EXPLAIN EXTENDED SELECT * FROM t1 INNER JOIN t2 ON ( pk1+1 = pk2+2 AND a1 = a2 ) -WHERE b1 <= ( SELECT MAX(b2) FROM t2 WHERE pk2 <= 1 ); -id select_type table type possible_keys key key_len ref rows filtered Extra -1 PRIMARY t2 ALL NULL NULL NULL NULL 101 100.00 -1 PRIMARY t1 ALL a1,b1 NULL NULL NULL 400 2.61 Using where; Using join buffer (flat, BNL join) -2 SUBQUERY t2 range PRIMARY PRIMARY 4 NULL 1 100.00 Using index condition -Warnings: -Note 1003 /* select#1 */ select `test`.`t1`.`pk1` AS `pk1`,`test`.`t1`.`a1` AS `a1`,`test`.`t1`.`b1` AS `b1`,`test`.`t2`.`pk2` AS `pk2`,`test`.`t2`.`a2` AS `a2`,`test`.`t2`.`b2` AS `b2` from `test`.`t1` join `test`.`t2` where `test`.`t1`.`a1` = `test`.`t2`.`a2` and `test`.`t1`.`b1` <= (/* select#2 */ select max(`test`.`t2`.`b2`) from `test`.`t2` where `test`.`t2`.`pk2` <= 1) and `test`.`t1`.`pk1` + 1 = `test`.`t2`.`pk2` + 2 -set @@optimizer_where_cost=0.0356*4; -EXPLAIN EXTENDED SELECT * FROM t1 INNER JOIN t2 ON ( pk1+1 = pk2+2 AND a1 = a2 ) -WHERE b1 <= ( SELECT MAX(b2) FROM t2 WHERE pk2 <= 1 ); -id select_type table type possible_keys key key_len ref rows filtered Extra -1 PRIMARY t2 ALL NULL NULL NULL NULL 101 100.00 Using where -1 PRIMARY t1 ref|filter a1,b1 a1|b1 5|4 test.t2.a2 36 (29%) 28.75 Using where; Using rowid filter -2 SUBQUERY t2 range PRIMARY PRIMARY 4 NULL 1 100.00 Using index condition -Warnings: -Note 1003 /* select#1 */ select `test`.`t1`.`pk1` AS `pk1`,`test`.`t1`.`a1` AS `a1`,`test`.`t1`.`b1` AS `b1`,`test`.`t2`.`pk2` AS `pk2`,`test`.`t2`.`a2` AS `a2`,`test`.`t2`.`b2` AS `b2` from `test`.`t1` join `test`.`t2` where `test`.`t1`.`a1` = `test`.`t2`.`a2` and `test`.`t1`.`b1` <= (/* select#2 */ select max(`test`.`t2`.`b2`) from `test`.`t2` where `test`.`t2`.`pk2` <= 1) and `test`.`t1`.`pk1` + 1 = `test`.`t2`.`pk2` + 2 -EXPLAIN FORMAT=JSON SELECT * FROM t1 INNER JOIN t2 ON ( pk1+1 = pk2+2 AND a1 = a2 ) -WHERE b1 <= ( SELECT MAX(b2) FROM t2 WHERE pk2 <= 1 ); -EXPLAIN -{ - "query_block": { - "select_id": 1, - "nested_loop": [ - { - "table": { - "table_name": "t2", - "access_type": "ALL", - "rows": 101, - "filtered": 100, - "attached_condition": "t2.a2 is not null" - } - }, - { - "table": { - "table_name": "t1", - "access_type": "ref", - "possible_keys": ["a1", "b1"], - "key": "a1", - "key_length": "5", - "used_key_parts": ["a1"], - "ref": ["test.t2.a2"], - "rowid_filter": { - "range": { - "key": "b1", - "used_key_parts": ["b1"] - }, - "rows": 115, - "selectivity_pct": 28.75 - }, - "rows": 36, - "filtered": 28.75, - "attached_condition": "t1.b1 <= (subquery#2) and t1.pk1 + 1 = t2.pk2 + 2" - } - } - ], - "subqueries": [ - { - "query_block": { - "select_id": 2, - "nested_loop": [ - { - "table": { - "table_name": "t2", - "access_type": "range", - "possible_keys": ["PRIMARY"], - "key": "PRIMARY", - "key_length": "4", - "used_key_parts": ["pk2"], - "rows": 1, - "filtered": 100, - "index_condition": "t2.pk2 <= 1" - } - } - ] - } - } - ] - } -} -set @@optimizer_where_cost=default; -DROP TABLE t1,t2; -# -# MDEV-21794: Optimizer flag rowid_filter leads to long query -# -create table t10(a int); -insert into t10 values (0),(1),(2),(3),(4),(5),(6),(7),(8),(9); -create table t11(a int); -insert into t11 select A.a + B.a* 10 + C.a * 100 from t10 A, t10 B, t10 C; -CREATE TABLE t1 ( -el_id int(10) unsigned NOT NULL , -el_index blob NOT NULL, -el_index_60 varbinary(60) NOT NULL, -filler blob, -PRIMARY KEY (el_id), -KEY el_index (el_index(60)), -KEY el_index_60 (el_index_60,el_id) -); -insert into t1 -select -A.a+1000*B.a, -A.a+1000*B.a + 10000, -A.a+1000*B.a + 10000, -'filler-data-filler-data' -from -t11 A, t10 B; -analyze table t1 persistent for all; -Table Op Msg_type Msg_text -test.t1 analyze status Engine-independent statistics collected -test.t1 analyze Warning Engine-independent statistics are not collected for column 'el_index' -test.t1 analyze Warning Engine-independent statistics are not collected for column 'filler' -test.t1 analyze status Table is already up to date -# This must not use rowid_filter with key=el_index|el_index_60: -explain -select * from t1 -where el_index like '10%' and (el_index_60 like '10%' or el_index_60 like '20%'); -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 range el_index,el_index_60 el_index 62 NULL 645 Using where -drop table t10, t11, t1; -# -# MDEV-22160: SIGSEGV in st_join_table::save_explain_data on SELECT -# -set @save_optimizer_switch= @@optimizer_switch; -SET @@optimizer_switch="index_merge_sort_union=OFF"; -CREATE TABLE t1 (a INT, b INT, INDEX(a), INDEX(b)); -INSERT INTO t1 VALUES (0,0),(0,0),(1,0),(-1,1), (-2,1), (-2,3), (-3,4), (-2,4),(3,3),(3,4),(3,5),(8,8),(8,9),(1,0),(2,0),(0,0),(0,0); -explain -SELECT * FROM t1 WHERE a > 0 AND b=0; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ref|filter a,b b|a 5|5 const 7 (47%) Using where; Using rowid filter -SELECT * FROM t1 WHERE a > 0 AND b=0; -a b -1 0 -1 0 -2 0 -drop table t1; -SET @@optimizer_switch=@save_optimizer_switch; -# -# MDEV-28846: Poor performance when rowid filter contains no elements -# -create table t1 ( -pk int primary key auto_increment, -nm varchar(32), -fl1 tinyint default 0, -fl2 tinyint default 0, -index idx1(nm, fl1), -index idx2(fl2) -) engine=myisam; -create table name ( -pk int primary key auto_increment, -nm bigint -) engine=myisam; -create table flag2 ( -pk int primary key auto_increment, -fl2 tinyint -) engine=myisam; -insert into name(nm) select seq from seq_1_to_1000 order by rand(17); -insert into flag2(fl2) select seq mod 2 from seq_1_to_1000 order by rand(19); -insert into t1(nm,fl2) -select nm, fl2 from name, flag2 where name.pk = flag2.pk; -analyze table t1 persistent for all; -Table Op Msg_type Msg_text -test.t1 analyze status Engine-independent statistics collected -test.t1 analyze status Table is already up to date -select '500%' as a; -a -500% -set optimizer_switch='rowid_filter=on'; -explain -select * from t1 where nm like '500%' AND fl2 = 0; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 range idx1,idx2 idx1 35 NULL 1 Using index condition; Using where -analyze format=json -select * from t1 where nm like '500%' AND fl2 = 0; -ANALYZE -{ - "query_optimization": { - "r_total_time_ms": "REPLACED" - }, - "query_block": { - "select_id": 1, - "r_loops": 1, - "r_total_time_ms": "REPLACED", - "nested_loop": [ - { - "table": { - "table_name": "t1", - "access_type": "range", - "possible_keys": ["idx1", "idx2"], - "key": "idx1", - "key_length": "35", - "used_key_parts": ["nm"], - "r_loops": 1, - "rows": 1, - "r_rows": 1, - "r_table_time_ms": "REPLACED", - "r_other_time_ms": "REPLACED", - "filtered": 49.20000076, - "r_filtered": 100, - "index_condition": "t1.nm like '500%'", - "attached_condition": "t1.fl2 = 0" - } - } - ] - } -} -select * from t1 where nm like '500%' AND fl2 = 0; -pk nm fl1 fl2 -517 500 0 0 -truncate table name; -truncate table flag2; -truncate table t1; -insert into name(nm) select seq from seq_1_to_1000 order by rand(17); -insert into flag2(fl2) select seq mod 2 from seq_1_to_1000 order by rand(19); -insert into t1(nm,fl2) -select nm, fl2 from name, flag2 where name.pk = flag2.pk; -analyze table t1 persistent for all; -Table Op Msg_type Msg_text -test.t1 analyze status Engine-independent statistics collected -test.t1 analyze status Table is already up to date -set optimizer_switch='rowid_filter=off'; -explain -select * from t1 where nm like '500%' AND fl2 = 0; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 range idx1,idx2 idx1 35 NULL 1 Using index condition; Using where -analyze format=json -select * from t1 where nm like '500%' AND fl2 = 0; -ANALYZE -{ - "query_optimization": { - "r_total_time_ms": "REPLACED" - }, - "query_block": { - "select_id": 1, - "r_loops": 1, - "r_total_time_ms": "REPLACED", - "nested_loop": [ - { - "table": { - "table_name": "t1", - "access_type": "range", - "possible_keys": ["idx1", "idx2"], - "key": "idx1", - "key_length": "35", - "used_key_parts": ["nm"], - "r_loops": 1, - "rows": 1, - "r_rows": 1, - "r_table_time_ms": "REPLACED", - "r_other_time_ms": "REPLACED", - "filtered": 49.20000076, - "r_filtered": 100, - "index_condition": "t1.nm like '500%'", - "attached_condition": "t1.fl2 = 0" - } - } - ] - } -} -select * from t1 where nm like '500%' AND fl2 = 0; -pk nm fl1 fl2 -517 500 0 0 -truncate table name; -truncate table flag2; -truncate table t1; -insert into name(nm) select seq from seq_1_to_1000 order by rand(17); -insert into flag2(fl2) select seq mod 10 from seq_1_to_1000 order by rand(19); -insert into t1(nm,fl2) -select nm, fl2 from name, flag2 where name.pk = flag2.pk; -analyze table t1 persistent for all; -Table Op Msg_type Msg_text -test.t1 analyze status Engine-independent statistics collected -test.t1 analyze status Table is already up to date -select '607%' as a; -a -607% -set optimizer_switch='rowid_filter=on'; -explain -select * from t1 where nm like '607%' AND fl2 = 0; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 range idx1,idx2 idx1 35 NULL 1 Using index condition; Using where -select * from t1 where nm like '607%' AND fl2 = 0; -pk nm fl1 fl2 -721 607 0 0 -truncate table name; -truncate table flag2; -truncate table t1; -insert into name(nm) select seq from seq_1_to_10000 order by rand(17); -insert into flag2(fl2) select seq mod 100 from seq_1_to_10000 order by rand(19); -insert into t1(nm,fl2) -select nm, fl2 from name, flag2 where name.pk = flag2.pk; -analyze table t1 persistent for all; -Table Op Msg_type Msg_text -test.t1 analyze status Engine-independent statistics collected -test.t1 analyze status Table is already up to date -select '75%' as a; -a -75% -set optimizer_switch='rowid_filter=on'; -explain -select * from t1 where nm like '75%' AND fl2 = 0; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ref|filter idx1,idx2 idx2|idx1 2|35 const 55 (1%) Using where; Using rowid filter -analyze format=json -select * from t1 where nm like '75%' AND fl2 = 0; -ANALYZE -{ - "query_optimization": { - "r_total_time_ms": "REPLACED" - }, - "query_block": { - "select_id": 1, - "r_loops": 1, - "r_total_time_ms": "REPLACED", - "nested_loop": [ - { - "table": { - "table_name": "t1", - "access_type": "ref", - "possible_keys": ["idx1", "idx2"], - "key": "idx2", - "key_length": "2", - "used_key_parts": ["fl2"], - "ref": ["const"], - "rowid_filter": { - "range": { - "key": "idx1", - "used_key_parts": ["nm"] - }, - "rows": 115, - "selectivity_pct": 1.15, - "r_rows": 111, - "r_lookups": 100, - "r_selectivity_pct": 2, - "r_buffer_size": "REPLACED", - "r_filling_time_ms": "REPLACED" - }, - "r_loops": 1, - "rows": 55, - "r_rows": 2, - "r_table_time_ms": "REPLACED", - "r_other_time_ms": "REPLACED", - "filtered": 1.149999976, - "r_filtered": 100, - "attached_condition": "t1.nm like '75%'" - } - } - ] - } -} -select * from t1 where nm like '75%' AND fl2 = 0; -pk nm fl1 fl2 -4543 7503 0 0 -7373 7518 0 0 -drop table name, flag2; -drop table t1; -create table t1 ( -pk int primary key auto_increment, -nm char(255), -fl1 tinyint default 0, -fl2 int default 0, -index idx1(nm, fl1), -index idx2(fl2) -) engine=myisam; -create table name ( -pk int primary key auto_increment, -nm bigint -) engine=myisam; -create table flag2 ( -pk int primary key auto_increment, -fl2 int -) engine=myisam; -insert into name(nm) select seq from seq_1_to_10000 order by rand(17); -insert into flag2(fl2) select seq mod 10 from seq_1_to_10000 order by rand(19); -insert into t1(nm,fl2) -select nm, fl2 from name, flag2 where name.pk = flag2.pk; -analyze table t1 persistent for all; -Table Op Msg_type Msg_text -test.t1 analyze status Engine-independent statistics collected -test.t1 analyze status Table is already up to date -select * from t1 -where -( -nm like '3400%' or nm like '3402%' or nm like '3403%' or -nm like '3404%' or nm like '3405%' or nm like '3406%' or nm like '3407%' or -nm like '3409%' or -nm like '3411%' or nm like '3412%' or nm like '3413%' or -nm like '3414%' or nm like '3415%' or nm like '3416%' or nm like '3417%' or -nm like '3418%' or nm like '3419%' or -nm like '3421%' or nm like '3422%' or nm like '3423%' or -nm like '3424%' or nm like '3425%' or nm like '3426%' or nm like '3427%' or -nm like '3428%' or nm like '3429%' or -nm like '3430%' or nm like '3431%' or nm like '3432%' or nm like '3433%' or -nm like '3434%' or nm like '3435%' or nm like '3436%' or nm like '3437%' or -nm like '3439%' or -nm like '3440%' or nm like '3441%' or nm like '3442%' or nm like '3443%' or -nm like '3444%' or nm like '3445%' or nm like '3446%' or nm like '3447%' or -nm like '3448%' -) and fl2 = 0; -pk nm fl1 fl2 -analyze format=json select * from t1 -where -( -nm like '3400%' or nm like '3402%' or nm like '3403%' or -nm like '3404%' or nm like '3405%' or nm like '3406%' or nm like '3407%' or -nm like '3409%' or -nm like '3411%' or nm like '3412%' or nm like '3413%' or -nm like '3414%' or nm like '3415%' or nm like '3416%' or nm like '3417%' or -nm like '3418%' or nm like '3419%' or -nm like '3421%' or nm like '3422%' or nm like '3423%' or -nm like '3424%' or nm like '3425%' or nm like '3426%' or nm like '3427%' or -nm like '3428%' or nm like '3429%' or -nm like '3430%' or nm like '3431%' or nm like '3432%' or nm like '3433%' or -nm like '3434%' or nm like '3435%' or nm like '3436%' or nm like '3437%' or -nm like '3439%' or -nm like '3440%' or nm like '3441%' or nm like '3442%' or nm like '3443%' or -nm like '3444%' or nm like '3445%' or nm like '3446%' or nm like '3447%' or -nm like '3448%' -) and fl2 = 0; -ANALYZE -{ - "query_optimization": { - "r_total_time_ms": "REPLACED" - }, - "query_block": { - "select_id": 1, - "r_loops": 1, - "r_total_time_ms": "REPLACED", - "nested_loop": [ - { - "table": { - "table_name": "t1", - "access_type": "range", - "possible_keys": ["idx1", "idx2"], - "key": "idx1", - "key_length": "256", - "used_key_parts": ["nm"], - "rowid_filter": { - "range": { - "key": "idx2", - "used_key_parts": ["fl2"] - }, - "rows": 863, - "selectivity_pct": 8.63, - "r_rows": 1000, - "r_lookups": 44, - "r_selectivity_pct": 0, - "r_buffer_size": "REPLACED", - "r_filling_time_ms": "REPLACED" - }, - "r_loops": 1, - "rows": 44, - "r_rows": 0, - "r_table_time_ms": "REPLACED", - "r_other_time_ms": "REPLACED", - "filtered": 8.630000114, - "r_filtered": 100, - "index_condition": "t1.nm like '3400%' or t1.nm like '3402%' or t1.nm like '3403%' or t1.nm like '3404%' or t1.nm like '3405%' or t1.nm like '3406%' or t1.nm like '3407%' or t1.nm like '3409%' or t1.nm like '3411%' or t1.nm like '3412%' or t1.nm like '3413%' or t1.nm like '3414%' or t1.nm like '3415%' or t1.nm like '3416%' or t1.nm like '3417%' or t1.nm like '3418%' or t1.nm like '3419%' or t1.nm like '3421%' or t1.nm like '3422%' or t1.nm like '3423%' or t1.nm like '3424%' or t1.nm like '3425%' or t1.nm like '3426%' or t1.nm like '3427%' or t1.nm like '3428%' or t1.nm like '3429%' or t1.nm like '3430%' or t1.nm like '3431%' or t1.nm like '3432%' or t1.nm like '3433%' or t1.nm like '3434%' or t1.nm like '3435%' or t1.nm like '3436%' or t1.nm like '3437%' or t1.nm like '3439%' or t1.nm like '3440%' or t1.nm like '3441%' or t1.nm like '3442%' or t1.nm like '3443%' or t1.nm like '3444%' or t1.nm like '3445%' or t1.nm like '3446%' or t1.nm like '3447%' or t1.nm like '3448%'", - "attached_condition": "t1.fl2 = 0" - } - } - ] - } -} -create table t0 select * from t1 where nm like '34%'; -delete from t1 using t1,t0 where t1.nm=t0.nm; -analyze format=json select * from t1 -where -( -nm like '3400%' or nm like '3402%' or nm like '3403%' or -nm like '3404%' or nm like '3405%' or nm like '3406%' or nm like '3407%' or -nm like '3409%' or -nm like '3411%' or nm like '3412%' or nm like '3413%' or -nm like '3414%' or nm like '3415%' or nm like '3416%' or nm like '3417%' or -nm like '3418%' or nm like '3419%' or -nm like '3421%' or nm like '3422%' or nm like '3423%' or -nm like '3424%' or nm like '3425%' or nm like '3426%' or nm like '3427%' or -nm like '3428%' or nm like '3429%' or -nm like '3430%' or nm like '3431%' or nm like '3432%' or nm like '3433%' or -nm like '3434%' or nm like '3435%' or nm like '3436%' or nm like '3437%' or -nm like '3439%' or -nm like '3440%' or nm like '3441%' or nm like '3442%' or nm like '3443%' or -nm like '3444%' or nm like '3445%' or nm like '3446%' or nm like '3447%' or -nm like '3448%' -) and fl2 = 0; -ANALYZE -{ - "query_optimization": { - "r_total_time_ms": "REPLACED" - }, - "query_block": { - "select_id": 1, - "r_loops": 1, - "r_total_time_ms": "REPLACED", - "nested_loop": [ - { - "table": { - "table_name": "t1", - "access_type": "range", - "possible_keys": ["idx1", "idx2"], - "key": "idx1", - "key_length": "256", - "used_key_parts": ["nm"], - "rowid_filter": { - "range": { - "key": "idx2", - "used_key_parts": ["fl2"] - }, - "rows": 853, - "selectivity_pct": 8.53, - "r_rows": 987, - "r_lookups": 0, - "r_selectivity_pct": 0, - "r_buffer_size": "REPLACED", - "r_filling_time_ms": "REPLACED" - }, - "r_loops": 1, - "rows": 44, - "r_rows": 0, - "r_table_time_ms": "REPLACED", - "r_other_time_ms": "REPLACED", - "filtered": 8.529999733, - "r_filtered": 100, - "index_condition": "t1.nm like '3400%' or t1.nm like '3402%' or t1.nm like '3403%' or t1.nm like '3404%' or t1.nm like '3405%' or t1.nm like '3406%' or t1.nm like '3407%' or t1.nm like '3409%' or t1.nm like '3411%' or t1.nm like '3412%' or t1.nm like '3413%' or t1.nm like '3414%' or t1.nm like '3415%' or t1.nm like '3416%' or t1.nm like '3417%' or t1.nm like '3418%' or t1.nm like '3419%' or t1.nm like '3421%' or t1.nm like '3422%' or t1.nm like '3423%' or t1.nm like '3424%' or t1.nm like '3425%' or t1.nm like '3426%' or t1.nm like '3427%' or t1.nm like '3428%' or t1.nm like '3429%' or t1.nm like '3430%' or t1.nm like '3431%' or t1.nm like '3432%' or t1.nm like '3433%' or t1.nm like '3434%' or t1.nm like '3435%' or t1.nm like '3436%' or t1.nm like '3437%' or t1.nm like '3439%' or t1.nm like '3440%' or t1.nm like '3441%' or t1.nm like '3442%' or t1.nm like '3443%' or t1.nm like '3444%' or t1.nm like '3445%' or t1.nm like '3446%' or t1.nm like '3447%' or t1.nm like '3448%'", - "attached_condition": "t1.fl2 = 0" - } - } - ] - } -} -drop table t0; -set optimizer_switch='rowid_filter=default'; -drop table name, flag2; -drop table t1; -set @@use_stat_tables=@save_use_stat_tables; -# -# MDEV-21633 -# Assertion `tmp >= 0' failed in best_access_path with rowid_filter=ON -# -set @save_optimizer_switch= @@optimizer_switch; -SET optimizer_switch='rowid_filter=on'; -CREATE TABLE t1 ( -pk INT AUTO_INCREMENT, -a INT, -b VARCHAR(8), -KEY(a), -PRIMARY KEY(pk), -KEY (a,pk) -) ENGINE=MyISAM; -INSERT INTO t1 (a,b) VALUES -(NULL,'d'),(9,'b'),(2,'x'),(5,'k'),(NULL,'d'),(3,'s'),(5,'k'),(1,'r'), -(8,'l'),(3,'z'),(1,'c'),(1,'q'),(NULL,'x'),(NULL,'p'),(NULL,'z'),(7,'a'), -(0,'i'),(3,'s'),(NULL,'h'),(4,'p'),(1,'i'),(4,'f'),(1,'c'),(NULL,'a'), -(NULL,'x'),(1,'b'),(NULL,'n'),(NULL,'h'),(5,'i'),(6,'e'),(NULL,'i'), -(7,'e'),(1,'r'),(NULL,'z'),(1,'i'),(14,'c'),(6,'u'),(3,'b'),(4,'z'), -(2,'c'),(70,'d'),(NULL,'p'),(21,'j'),(6,'e'),(5,'c'),(13,'i'),(42,'d'), -(80,'s'),(14,'t'),(9,'a'),(0,'2'),(0,NULL),(0,NULL),(0,NULL),(0,''), -(0,''),(0,'1'),(0,''),(0,''),(0,''),(0,''),(0,NULL),(0,''),(0,''),(0,''), -(0,NULL),(0,''),(0,''),(0,''),(0,''),(0,''),(0,''),(0,NULL),(0,NULL), -(0,NULL),(0,''),(0,''),(0,''),(0,''),(0,NULL),(0,''),(0,NULL),(0,NULL), -(0,''),(0,''),(0,''),(0,NULL),(0,''),(0,NULL),(0,''),(0,''),(0,''),(0,''), -(0,''),(0,''),(0,''),(0,NULL),(0,''),(0,NULL),(0,''); -CREATE TABLE t2 (c INT) ENGINE=MyISAM; -INSERT INTO t2 VALUES (1),(2),(3),(4),(5),(6); -SELECT * FROM t1 JOIN t2 WHERE a = c AND pk BETWEEN 4 AND 7 AND a BETWEEN 2 AND 12 AND b != 'foo'; -pk a b c -6 3 s 3 -4 5 k 5 -7 5 k 5 -explain SELECT * FROM t1 JOIN t2 WHERE a = c AND pk BETWEEN 4 AND 7 AND a BETWEEN 2 AND 12 AND b != 'foo'; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 range|filter PRIMARY,a,a_2 PRIMARY|a 4|5 NULL 4 (11%) Using index condition; Using where; Using rowid filter -1 SIMPLE t2 ALL NULL NULL NULL NULL 6 Using where; Using join buffer (flat, BNL join) -SET optimizer_switch='rowid_filter=off'; -SELECT * FROM t1 JOIN t2 WHERE a = c AND pk BETWEEN 4 AND 7 AND a BETWEEN 2 AND 12 AND b != 'foo'; -pk a b c -6 3 s 3 -4 5 k 5 -7 5 k 5 -SET @@optimizer_switch=@save_optimizer_switch; -DROP TABLE t1, t2; diff --git a/mysql-test/main/rowid_filter.test b/mysql-test/main/rowid_filter.test index 519723b4f29..8ba4cc64845 100644 --- a/mysql-test/main/rowid_filter.test +++ b/mysql-test/main/rowid_filter.test @@ -250,411 +250,3 @@ DROP VIEW v1; DROP DATABASE dbt3_s001; use test; - ---echo # ---echo # MDEV-18816: potential range filter for one join table with ---echo # impossible WHERE for another ---echo # - -create table t1 ( - pk int not null primary key, c2 varchar(10) , i1 int,key (c2) -) engine=myisam; -insert into t1 values (1,'a',-5),(2,'a',null); - -create table t2 ( - pk int, i1 int, c1 varchar(30) , key c1 (c1(30)), key i1 (i1) -) engine=myisam; -insert into t2 values - (1,-5,'a'),(2,null,'a'),(3,null,'a'),(4,null,'a'),(5,5,'a'),(6,null,'a'), - (7,4,'a'),(8,55,'a'),(9,null,'a'),(10,null,'a'),(11,null,'a'),(12,-5,'a'), - (13,-5,'a'),(14,null,'a'),(15,null,'a'),(16,-5,'a'),(17,-5,'a'); - -let $q= -select 1 - from t1 - left join - t2 join t1 as t1_a on t2.i1 = t1_a.pk - on t1.c2 = t2.c1 -where t1_a.pk is null and t1_a.i1 != 3; - -eval $q; -eval explain extended $q; - -drop table t1,t2; - ---echo # ---echo # MDEV-18640: TABLE::prune_range_rowid_filters: Conditional jump or ---echo # move depends on uninitialized value ---echo # - -CREATE TABLE t1 ( - pk INT, i INT, PRIMARY KEY (pk), KEY (pk,i) -) ENGINE=MyISAM; -INSERT INTO t1 VALUES (1,10), (7,70), (2,20); - -SELECT * FROM t1 WHERE pk < 5; - -DROP TABLE t1; - ---echo # ---echo # MDEV-18956: Possible rowid filter for subquery for which ---echo # in_to_exists strategy has been chosen ---echo # - -CREATE TABLE t1 (pk int) engine=myisam ; -INSERT INTO t1 VALUES (1),(2); - -CREATE TABLE t2 ( - pk int auto_increment PRIMARY KEY, - i1 int, i2 int, c2 varchar(1), - KEY (i1), KEY (i2) -) engine=myisam; - -INSERT INTO t2 VALUES - (1,8,6,'t'),(2,5,7,'i'),(3,4,4,'h'),(4,207,38,'d'),(5,183,206,'b'), - (6,7,null,'o'),(7,1,2,'j'),(8,17,36,'s'),(9,4,5,'q'),(10,0,6,'l'), - (11,1,9,'j'),(12,5,6,'y'),(13,null,0,'i'),(14,7,7,'x'),(15,5,2,'u'); - -SELECT * FROM t1 HAVING (7, 9) IN (SELECT t2.i1, t2.i2 FROM t2 WHERE t2.i1 = 3); -EXPLAIN EXTENDED -SELECT * FROM t1 HAVING (7, 9) IN (SELECT t2.i1, t2.i2 FROM t2 WHERE t2.i1 = 3); - -DROP TABLE t1,t2; - ---echo # ---echo # MDEV-19255: rowid range filter built for range condition ---echo # that uses in expensive subquery ---echo # - -CREATE TABLE t1 ( - pk1 INT PRIMARY KEY, a1 INT, b1 VARCHAR(1), KEY(a1), KEY(b1) -) ENGINE=MyISAM; -INSERT INTO t1 VALUES -(10,0,'z'),(11,3,'j'),(12,8,'f'),(13,8,'p'),(14,6,'w'),(15,0,'c'),(16,1,'j'), -(17,1,'f'),(18,5,'v'),(19,3,'f'),(20,2,'q'),(21,8,'y'),(22,0,'a'),(23,9,'w'), -(24,3,'e'),(25,1,'b'),(26,9,'r'),(27,2,'k'),(28,5,'c'),(29,3,'k'),(30,9,'b'), -(31,8,'j'),(32,1,'t'),(33,8,'n'),(34,3,'z'),(35,0,'u'),(36,3,'a'),(37,3,'g'), -(38,1,'f'),(39,6,'p'),(40,6,'m'),(41,6,'t'),(42,7,'i'),(43,4,'h'),(44,3,'d'), -(45,2,'b'),(46,1,'o'),(47,2,'j'),(48,6,'s'),(49,5,'q'),(50,6,'l'),(51,9,'j'), -(52,6,'y'),(53,0,'i'),(54,7,'x'),(55,2,'u'),(56,6,'t'),(57,4,'b'),(58,5,'m'), -(59,4,'x'),(60,8,'x'),(61,6,'v'),(62,8,'m'),(63,4,'j'),(64,8,'z'),(65,2,'a'), -(66,9,'i'),(67,4,'g'),(68,8,'h'),(69,1,'p'),(70,8,'a'),(71,0,'x'),(72,2,'s'), -(73,6,'k'),(74,0,'m'),(75,6,'e'),(76,9,'y'),(77,7,'d'),(78,7,'w'),(79,6,'y'), -(80,9,'s'),(81,9,'x'),(82,6,'l'),(83,9,'f'),(84,8,'x'),(85,1,'p'),(86,7,'y'), -(87,6,'p'),(88,1,'g'),(89,3,'c'),(90,5,'h'),(91,3,'p'),(92,2,'b'),(93,1,NULL), -(94,3,NULL),(95,2,'y'),(96,7,'s'),(97,7,'x'),(98,6,'i'),(99,9,'t'),(100,5,'j'), -(101,0,'u'),(102,7,'r'),(103,2,'x'),(104,8,'e'),(105,8,'i'),(106,5,'q'), -(107,8,'z'),(108,3,'k'),(109,65,NULL); - -CREATE TABLE t2 (pk2 INT PRIMARY KEY, a2 INT, b2 VARCHAR(1)) ENGINE=MyISAM; -INSERT INTO t2 VALUES (1,1,'i'); -INSERT INTO t2 SELECT * FROM t1; - -INSERT INTO t1 SELECT pk1+200, a1, b1 FROM t1; -INSERT INTO t1 SELECT pk1+400, a1, b1 FROM t1; - -ANALYZE TABLE t1,t2 PERSISTENT FOR ALL; - -let $q= -SELECT * FROM t1 INNER JOIN t2 ON ( pk1+1 = pk2+2 AND a1 = a2 ) - WHERE b1 <= ( SELECT MAX(b2) FROM t2 WHERE pk2 <= 1 ); - -eval $q; -eval EXPLAIN EXTENDED $q; -set @@optimizer_where_cost=0.0356*4; -eval EXPLAIN EXTENDED $q; -eval EXPLAIN FORMAT=JSON $q; -set @@optimizer_where_cost=default; - -DROP TABLE t1,t2; - ---echo # ---echo # MDEV-21794: Optimizer flag rowid_filter leads to long query ---echo # -create table t10(a int); -insert into t10 values (0),(1),(2),(3),(4),(5),(6),(7),(8),(9); - -create table t11(a int); -insert into t11 select A.a + B.a* 10 + C.a * 100 from t10 A, t10 B, t10 C; - -CREATE TABLE t1 ( - el_id int(10) unsigned NOT NULL , - el_index blob NOT NULL, - el_index_60 varbinary(60) NOT NULL, - filler blob, - - PRIMARY KEY (el_id), - KEY el_index (el_index(60)), - KEY el_index_60 (el_index_60,el_id) -); - -insert into t1 -select - A.a+1000*B.a, - A.a+1000*B.a + 10000, - A.a+1000*B.a + 10000, - 'filler-data-filler-data' -from - t11 A, t10 B; -analyze table t1 persistent for all; - ---echo # This must not use rowid_filter with key=el_index|el_index_60: -explain -select * from t1 -where el_index like '10%' and (el_index_60 like '10%' or el_index_60 like '20%'); - -drop table t10, t11, t1; - - ---echo # ---echo # MDEV-22160: SIGSEGV in st_join_table::save_explain_data on SELECT ---echo # - -set @save_optimizer_switch= @@optimizer_switch; -SET @@optimizer_switch="index_merge_sort_union=OFF"; -CREATE TABLE t1 (a INT, b INT, INDEX(a), INDEX(b)); -INSERT INTO t1 VALUES (0,0),(0,0),(1,0),(-1,1), (-2,1), (-2,3), (-3,4), (-2,4),(3,3),(3,4),(3,5),(8,8),(8,9),(1,0),(2,0),(0,0),(0,0); -explain -SELECT * FROM t1 WHERE a > 0 AND b=0; -SELECT * FROM t1 WHERE a > 0 AND b=0; -drop table t1; -SET @@optimizer_switch=@save_optimizer_switch; - ---echo # ---echo # MDEV-28846: Poor performance when rowid filter contains no elements ---echo # - ---source include/have_sequence.inc - -create table t1 ( - pk int primary key auto_increment, - nm varchar(32), - fl1 tinyint default 0, - fl2 tinyint default 0, - index idx1(nm, fl1), - index idx2(fl2) -) engine=myisam; - -create table name ( - pk int primary key auto_increment, - nm bigint -) engine=myisam; - -create table flag2 ( - pk int primary key auto_increment, - fl2 tinyint -) engine=myisam; - -insert into name(nm) select seq from seq_1_to_1000 order by rand(17); -insert into flag2(fl2) select seq mod 2 from seq_1_to_1000 order by rand(19); - -insert into t1(nm,fl2) - select nm, fl2 from name, flag2 where name.pk = flag2.pk; - -analyze table t1 persistent for all; - -let $a= -`select concat((select nm from t1 where fl2=0 order by RAND(13) limit 1),'%')`; -eval select '$a' as a; - -set optimizer_switch='rowid_filter=on'; -eval -explain -select * from t1 where nm like '$a' AND fl2 = 0; ---source include/analyze-format.inc -eval -analyze format=json -select * from t1 where nm like '$a' AND fl2 = 0; -eval -select * from t1 where nm like '$a' AND fl2 = 0; - -truncate table name; -truncate table flag2; -truncate table t1; - -insert into name(nm) select seq from seq_1_to_1000 order by rand(17); -insert into flag2(fl2) select seq mod 2 from seq_1_to_1000 order by rand(19); - -insert into t1(nm,fl2) - select nm, fl2 from name, flag2 where name.pk = flag2.pk; - -analyze table t1 persistent for all; - -set optimizer_switch='rowid_filter=off'; -eval -explain -select * from t1 where nm like '$a' AND fl2 = 0; ---source include/analyze-format.inc -eval -analyze format=json -select * from t1 where nm like '$a' AND fl2 = 0; -eval -select * from t1 where nm like '$a' AND fl2 = 0; - -truncate table name; -truncate table flag2; -truncate table t1; - -insert into name(nm) select seq from seq_1_to_1000 order by rand(17); -insert into flag2(fl2) select seq mod 10 from seq_1_to_1000 order by rand(19); - -insert into t1(nm,fl2) - select nm, fl2 from name, flag2 where name.pk = flag2.pk; - -analyze table t1 persistent for all; - -let $a= -`select concat((select nm from t1 where fl2=0 order by RAND(13) limit 1),'%')`; -eval select '$a' as a; - -set optimizer_switch='rowid_filter=on'; -eval -explain -select * from t1 where nm like '$a' AND fl2 = 0; -eval -select * from t1 where nm like '$a' AND fl2 = 0; - -truncate table name; -truncate table flag2; -truncate table t1; - -insert into name(nm) select seq from seq_1_to_10000 order by rand(17); -insert into flag2(fl2) select seq mod 100 from seq_1_to_10000 order by rand(19); - -insert into t1(nm,fl2) - select nm, fl2 from name, flag2 where name.pk = flag2.pk; - -analyze table t1 persistent for all; - -let $a= -`select concat(left((select nm from t1 where fl2=0 order by RAND(13) limit 1),2),'%')`; -eval select '$a' as a; - -set optimizer_switch='rowid_filter=on'; -eval -explain -select * from t1 where nm like '$a' AND fl2 = 0; ---source include/analyze-format.inc -eval -analyze format=json -select * from t1 where nm like '$a' AND fl2 = 0; -eval -select * from t1 where nm like '$a' AND fl2 = 0; - -drop table name, flag2; -drop table t1; - -# This test shows that if the container is empty there are no lookups into it - -create table t1 ( - pk int primary key auto_increment, - nm char(255), - fl1 tinyint default 0, - fl2 int default 0, - index idx1(nm, fl1), - index idx2(fl2) -) engine=myisam; - -create table name ( - pk int primary key auto_increment, - nm bigint -) engine=myisam; - -create table flag2 ( - pk int primary key auto_increment, - fl2 int -) engine=myisam; - -insert into name(nm) select seq from seq_1_to_10000 order by rand(17); -insert into flag2(fl2) select seq mod 10 from seq_1_to_10000 order by rand(19); - -insert into t1(nm,fl2) - select nm, fl2 from name, flag2 where name.pk = flag2.pk; - -analyze table t1 persistent for all; - -let $q= -select * from t1 -where -( - nm like '3400%' or nm like '3402%' or nm like '3403%' or - nm like '3404%' or nm like '3405%' or nm like '3406%' or nm like '3407%' or - nm like '3409%' or - nm like '3411%' or nm like '3412%' or nm like '3413%' or - nm like '3414%' or nm like '3415%' or nm like '3416%' or nm like '3417%' or - nm like '3418%' or nm like '3419%' or - nm like '3421%' or nm like '3422%' or nm like '3423%' or - nm like '3424%' or nm like '3425%' or nm like '3426%' or nm like '3427%' or - nm like '3428%' or nm like '3429%' or - nm like '3430%' or nm like '3431%' or nm like '3432%' or nm like '3433%' or - nm like '3434%' or nm like '3435%' or nm like '3436%' or nm like '3437%' or - nm like '3439%' or - nm like '3440%' or nm like '3441%' or nm like '3442%' or nm like '3443%' or - nm like '3444%' or nm like '3445%' or nm like '3446%' or nm like '3447%' or - nm like '3448%' -) and fl2 = 0; - -eval $q; ---source include/analyze-format.inc -eval analyze format=json $q; - -create table t0 select * from t1 where nm like '34%'; -delete from t1 using t1,t0 where t1.nm=t0.nm; ---source include/analyze-format.inc -eval analyze format=json $q; - -drop table t0; - -set optimizer_switch='rowid_filter=default'; - -drop table name, flag2; -drop table t1; - -set @@use_stat_tables=@save_use_stat_tables; - ---echo # ---echo # MDEV-21633 ---echo # Assertion `tmp >= 0' failed in best_access_path with rowid_filter=ON ---echo # - -set @save_optimizer_switch= @@optimizer_switch; -SET optimizer_switch='rowid_filter=on'; - -CREATE TABLE t1 ( - pk INT AUTO_INCREMENT, - a INT, - b VARCHAR(8), - KEY(a), - PRIMARY KEY(pk), - KEY (a,pk) -) ENGINE=MyISAM; - -INSERT INTO t1 (a,b) VALUES - (NULL,'d'),(9,'b'),(2,'x'),(5,'k'),(NULL,'d'),(3,'s'),(5,'k'),(1,'r'), - (8,'l'),(3,'z'),(1,'c'),(1,'q'),(NULL,'x'),(NULL,'p'),(NULL,'z'),(7,'a'), - (0,'i'),(3,'s'),(NULL,'h'),(4,'p'),(1,'i'),(4,'f'),(1,'c'),(NULL,'a'), - (NULL,'x'),(1,'b'),(NULL,'n'),(NULL,'h'),(5,'i'),(6,'e'),(NULL,'i'), - (7,'e'),(1,'r'),(NULL,'z'),(1,'i'),(14,'c'),(6,'u'),(3,'b'),(4,'z'), - (2,'c'),(70,'d'),(NULL,'p'),(21,'j'),(6,'e'),(5,'c'),(13,'i'),(42,'d'), - (80,'s'),(14,'t'),(9,'a'),(0,'2'),(0,NULL),(0,NULL),(0,NULL),(0,''), - (0,''),(0,'1'),(0,''),(0,''),(0,''),(0,''),(0,NULL),(0,''),(0,''),(0,''), - (0,NULL),(0,''),(0,''),(0,''),(0,''),(0,''),(0,''),(0,NULL),(0,NULL), - (0,NULL),(0,''),(0,''),(0,''),(0,''),(0,NULL),(0,''),(0,NULL),(0,NULL), - (0,''),(0,''),(0,''),(0,NULL),(0,''),(0,NULL),(0,''),(0,''),(0,''),(0,''), - (0,''),(0,''),(0,''),(0,NULL),(0,''),(0,NULL),(0,''); - -CREATE TABLE t2 (c INT) ENGINE=MyISAM; -INSERT INTO t2 VALUES (1),(2),(3),(4),(5),(6); - -SELECT * FROM t1 JOIN t2 WHERE a = c AND pk BETWEEN 4 AND 7 AND a BETWEEN 2 AND 12 AND b != 'foo'; - -explain SELECT * FROM t1 JOIN t2 WHERE a = c AND pk BETWEEN 4 AND 7 AND a BETWEEN 2 AND 12 AND b != 'foo'; - -SET optimizer_switch='rowid_filter=off'; - -SELECT * FROM t1 JOIN t2 WHERE a = c AND pk BETWEEN 4 AND 7 AND a BETWEEN 2 AND 12 AND b != 'foo'; - -SET @@optimizer_switch=@save_optimizer_switch; - -# Cleanup -DROP TABLE t1, t2; diff --git a/mysql-test/main/rowid_filter_aria.result b/mysql-test/main/rowid_filter_aria.result new file mode 100644 index 00000000000..8cc3d3be008 --- /dev/null +++ b/mysql-test/main/rowid_filter_aria.result @@ -0,0 +1,2217 @@ +SET SESSION DEFAULT_STORAGE_ENGINE='Aria'; +DROP DATABASE IF EXISTS dbt3_s001; +CREATE DATABASE dbt3_s001; +use dbt3_s001; +CREATE INDEX i_l_quantity ON lineitem(l_quantity); +CREATE INDEX i_o_totalprice ON orders(o_totalprice); +set @save_use_stat_tables= @@use_stat_tables; +set @@use_stat_tables=preferably; +ANALYZE TABLE lineitem, orders; +show create table lineitem; +Table Create Table +lineitem CREATE TABLE `lineitem` ( + `l_orderkey` int(11) NOT NULL DEFAULT 0, + `l_partkey` int(11) DEFAULT NULL, + `l_suppkey` int(11) DEFAULT NULL, + `l_linenumber` int(11) NOT NULL DEFAULT 0, + `l_quantity` double DEFAULT NULL, + `l_extendedprice` double DEFAULT NULL, + `l_discount` double DEFAULT NULL, + `l_tax` double DEFAULT NULL, + `l_returnflag` char(1) DEFAULT NULL, + `l_linestatus` char(1) DEFAULT NULL, + `l_shipDATE` date DEFAULT NULL, + `l_commitDATE` date DEFAULT NULL, + `l_receiptDATE` date DEFAULT NULL, + `l_shipinstruct` char(25) DEFAULT NULL, + `l_shipmode` char(10) DEFAULT NULL, + `l_comment` varchar(44) DEFAULT NULL, + PRIMARY KEY (`l_orderkey`,`l_linenumber`), + KEY `i_l_shipdate` (`l_shipDATE`), + KEY `i_l_suppkey_partkey` (`l_partkey`,`l_suppkey`), + KEY `i_l_partkey` (`l_partkey`), + KEY `i_l_suppkey` (`l_suppkey`), + KEY `i_l_receiptdate` (`l_receiptDATE`), + KEY `i_l_orderkey` (`l_orderkey`), + KEY `i_l_orderkey_quantity` (`l_orderkey`,`l_quantity`), + KEY `i_l_commitdate` (`l_commitDATE`), + KEY `i_l_quantity` (`l_quantity`) +) ENGINE=Aria DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci PAGE_CHECKSUM=1 +show create table orders; +Table Create Table +orders CREATE TABLE `orders` ( + `o_orderkey` int(11) NOT NULL, + `o_custkey` int(11) DEFAULT NULL, + `o_orderstatus` char(1) DEFAULT NULL, + `o_totalprice` double DEFAULT NULL, + `o_orderDATE` date DEFAULT NULL, + `o_orderpriority` char(15) DEFAULT NULL, + `o_clerk` char(15) DEFAULT NULL, + `o_shippriority` int(11) DEFAULT NULL, + `o_comment` varchar(79) DEFAULT NULL, + PRIMARY KEY (`o_orderkey`), + KEY `i_o_orderdate` (`o_orderDATE`), + KEY `i_o_custkey` (`o_custkey`), + KEY `i_o_totalprice` (`o_totalprice`) +) ENGINE=Aria DEFAULT CHARSET=latin1 COLLATE=latin1_swedish_ci PAGE_CHECKSUM=1 +set optimizer_use_condition_selectivity=2; +select +100 * +(select count(*) from lineitem +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-06-30' AND l_quantity > 45 +) +/ +(select count(*) from lineitem +where l_shipdate BETWEEN '1997-01-01' AND '1997-06-30') +as correct_r_filtered_when_using_l_shipdate; +correct_r_filtered_when_using_l_shipdate +11.7647 +set statement optimizer_switch='rowid_filter=on' for EXPLAIN SELECT l_orderkey, l_linenumber, l_shipdate, l_quantity FROM lineitem +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-06-30' AND +l_quantity > 45; +id select_type table type possible_keys key key_len ref rows Extra +1 SIMPLE lineitem range|filter i_l_shipdate,i_l_quantity i_l_shipdate|i_l_quantity 4|9 NULL 482 (16%) Using index condition; Using where; Using rowid filter +set statement optimizer_switch='rowid_filter=on' for EXPLAIN FORMAT=JSON SELECT l_orderkey, l_linenumber, l_shipdate, l_quantity FROM lineitem +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-06-30' AND +l_quantity > 45; +EXPLAIN +{ + "query_block": { + "select_id": 1, + "nested_loop": [ + { + "table": { + "table_name": "lineitem", + "access_type": "range", + "possible_keys": ["i_l_shipdate", "i_l_quantity"], + "key": "i_l_shipdate", + "key_length": "4", + "used_key_parts": ["l_shipDATE"], + "rowid_filter": { + "range": { + "key": "i_l_quantity", + "used_key_parts": ["l_quantity"] + }, + "rows": 949, + "selectivity_pct": 15.80349709 + }, + "rows": 482, + "filtered": 15.80349731, + "index_condition": "lineitem.l_shipDATE between '1997-01-01' and '1997-06-30'", + "attached_condition": "lineitem.l_quantity > 45" + } + } + ] + } +} +set statement optimizer_switch='rowid_filter=on' for ANALYZE SELECT l_orderkey, l_linenumber, l_shipdate, l_quantity FROM lineitem +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-06-30' AND +l_quantity > 45; +id select_type table type possible_keys key key_len ref rows r_rows filtered r_filtered Extra +1 SIMPLE lineitem range|filter i_l_shipdate,i_l_quantity i_l_shipdate|i_l_quantity 4|9 NULL 482 (16%) 60.00 (11%) 15.80 100.00 Using index condition; Using where; Using rowid filter +set statement optimizer_switch='rowid_filter=on' for ANALYZE FORMAT=JSON SELECT l_orderkey, l_linenumber, l_shipdate, l_quantity FROM lineitem +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-06-30' AND +l_quantity > 45; +ANALYZE +{ + "query_optimization": { + "r_total_time_ms": "REPLACED" + }, + "query_block": { + "select_id": 1, + "r_loops": 1, + "r_total_time_ms": "REPLACED", + "nested_loop": [ + { + "table": { + "table_name": "lineitem", + "access_type": "range", + "possible_keys": ["i_l_shipdate", "i_l_quantity"], + "key": "i_l_shipdate", + "key_length": "4", + "used_key_parts": ["l_shipDATE"], + "rowid_filter": { + "range": { + "key": "i_l_quantity", + "used_key_parts": ["l_quantity"] + }, + "rows": 949, + "selectivity_pct": 15.80349709, + "r_rows": 605, + "r_lookups": 510, + "r_selectivity_pct": 11.76470588, + "r_buffer_size": "REPLACED", + "r_filling_time_ms": "REPLACED" + }, + "r_loops": 1, + "rows": 482, + "r_rows": 60, + "r_table_time_ms": "REPLACED", + "r_other_time_ms": "REPLACED", + "filtered": 15.80349731, + "r_filtered": 100, + "index_condition": "lineitem.l_shipDATE between '1997-01-01' and '1997-06-30'", + "attached_condition": "lineitem.l_quantity > 45" + } + } + ] + } +} +set statement optimizer_switch='rowid_filter=on' for SELECT l_orderkey, l_linenumber, l_shipdate, l_quantity FROM lineitem +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-06-30' AND +l_quantity > 45; +l_orderkey l_linenumber l_shipdate l_quantity +1121 5 1997-04-27 47 +1121 6 1997-04-21 50 +1441 7 1997-06-07 50 +1443 1 1997-02-05 47 +1473 1 1997-05-05 50 +1568 2 1997-04-06 46 +1632 1 1997-01-25 47 +1632 3 1997-01-29 47 +1954 7 1997-06-04 49 +1959 1 1997-05-05 46 +2151 3 1997-01-20 49 +2177 5 1997-05-10 46 +2369 2 1997-01-02 47 +2469 3 1997-01-11 48 +2469 6 1997-03-03 49 +2470 2 1997-06-02 50 +260 1 1997-03-24 50 +288 2 1997-04-19 49 +289 4 1997-03-14 48 +3009 1 1997-03-19 48 +3105 3 1997-02-28 48 +3106 2 1997-02-27 49 +3429 1 1997-04-08 48 +3490 2 1997-06-27 50 +3619 1 1997-01-22 49 +3619 3 1997-01-31 46 +3969 3 1997-05-29 46 +4005 4 1997-01-31 49 +4036 1 1997-06-21 46 +4066 4 1997-02-17 49 +4098 1 1997-01-26 46 +422 3 1997-06-21 46 +4258 3 1997-01-02 46 +4421 2 1997-04-21 46 +4421 3 1997-05-25 46 +4453 3 1997-05-29 48 +4484 7 1997-03-17 50 +4609 3 1997-02-11 46 +484 1 1997-03-06 49 +484 3 1997-01-24 50 +484 5 1997-03-05 48 +485 1 1997-03-28 50 +4868 1 1997-04-29 47 +4868 3 1997-04-23 49 +4934 1 1997-05-20 48 +4967 1 1997-05-27 50 +5090 2 1997-04-05 46 +5152 2 1997-03-10 50 +5158 4 1997-04-10 49 +5606 3 1997-03-11 46 +5606 7 1997-02-01 46 +5762 4 1997-03-02 47 +581 3 1997-02-27 49 +5829 5 1997-01-31 49 +5831 4 1997-02-24 46 +5895 2 1997-04-27 47 +5895 3 1997-03-15 49 +5952 1 1997-06-30 49 +705 1 1997-04-18 46 +836 3 1997-03-21 46 +set statement optimizer_switch='rowid_filter=off' for EXPLAIN SELECT l_orderkey, l_linenumber, l_shipdate, l_quantity FROM lineitem +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-06-30' AND +l_quantity > 45; +id select_type table type possible_keys key key_len ref rows Extra +1 SIMPLE lineitem range i_l_shipdate,i_l_quantity i_l_shipdate 4 NULL 482 Using index condition; Using where +set statement optimizer_switch='rowid_filter=off' for EXPLAIN FORMAT=JSON SELECT l_orderkey, l_linenumber, l_shipdate, l_quantity FROM lineitem +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-06-30' AND +l_quantity > 45; +EXPLAIN +{ + "query_block": { + "select_id": 1, + "nested_loop": [ + { + "table": { + "table_name": "lineitem", + "access_type": "range", + "possible_keys": ["i_l_shipdate", "i_l_quantity"], + "key": "i_l_shipdate", + "key_length": "4", + "used_key_parts": ["l_shipDATE"], + "rows": 482, + "filtered": 15.80349731, + "index_condition": "lineitem.l_shipDATE between '1997-01-01' and '1997-06-30'", + "attached_condition": "lineitem.l_quantity > 45" + } + } + ] + } +} +set statement optimizer_switch='rowid_filter=off' for ANALYZE SELECT l_orderkey, l_linenumber, l_shipdate, l_quantity FROM lineitem +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-06-30' AND +l_quantity > 45; +id select_type table type possible_keys key key_len ref rows r_rows filtered r_filtered Extra +1 SIMPLE lineitem range i_l_shipdate,i_l_quantity i_l_shipdate 4 NULL 482 510.00 15.80 11.76 Using index condition; Using where +set statement optimizer_switch='rowid_filter=off' for ANALYZE FORMAT=JSON SELECT l_orderkey, l_linenumber, l_shipdate, l_quantity FROM lineitem +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-06-30' AND +l_quantity > 45; +ANALYZE +{ + "query_optimization": { + "r_total_time_ms": "REPLACED" + }, + "query_block": { + "select_id": 1, + "r_loops": 1, + "r_total_time_ms": "REPLACED", + "nested_loop": [ + { + "table": { + "table_name": "lineitem", + "access_type": "range", + "possible_keys": ["i_l_shipdate", "i_l_quantity"], + "key": "i_l_shipdate", + "key_length": "4", + "used_key_parts": ["l_shipDATE"], + "r_loops": 1, + "rows": 482, + "r_rows": 510, + "r_table_time_ms": "REPLACED", + "r_other_time_ms": "REPLACED", + "filtered": 15.80349731, + "r_filtered": 11.76470588, + "index_condition": "lineitem.l_shipDATE between '1997-01-01' and '1997-06-30'", + "attached_condition": "lineitem.l_quantity > 45" + } + } + ] + } +} +set statement optimizer_switch='rowid_filter=off' for SELECT l_orderkey, l_linenumber, l_shipdate, l_quantity FROM lineitem +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-06-30' AND +l_quantity > 45; +l_orderkey l_linenumber l_shipdate l_quantity +1121 5 1997-04-27 47 +1121 6 1997-04-21 50 +1441 7 1997-06-07 50 +1443 1 1997-02-05 47 +1473 1 1997-05-05 50 +1568 2 1997-04-06 46 +1632 1 1997-01-25 47 +1632 3 1997-01-29 47 +1954 7 1997-06-04 49 +1959 1 1997-05-05 46 +2151 3 1997-01-20 49 +2177 5 1997-05-10 46 +2369 2 1997-01-02 47 +2469 3 1997-01-11 48 +2469 6 1997-03-03 49 +2470 2 1997-06-02 50 +260 1 1997-03-24 50 +288 2 1997-04-19 49 +289 4 1997-03-14 48 +3009 1 1997-03-19 48 +3105 3 1997-02-28 48 +3106 2 1997-02-27 49 +3429 1 1997-04-08 48 +3490 2 1997-06-27 50 +3619 1 1997-01-22 49 +3619 3 1997-01-31 46 +3969 3 1997-05-29 46 +4005 4 1997-01-31 49 +4036 1 1997-06-21 46 +4066 4 1997-02-17 49 +4098 1 1997-01-26 46 +422 3 1997-06-21 46 +4258 3 1997-01-02 46 +4421 2 1997-04-21 46 +4421 3 1997-05-25 46 +4453 3 1997-05-29 48 +4484 7 1997-03-17 50 +4609 3 1997-02-11 46 +484 1 1997-03-06 49 +484 3 1997-01-24 50 +484 5 1997-03-05 48 +485 1 1997-03-28 50 +4868 1 1997-04-29 47 +4868 3 1997-04-23 49 +4934 1 1997-05-20 48 +4967 1 1997-05-27 50 +5090 2 1997-04-05 46 +5152 2 1997-03-10 50 +5158 4 1997-04-10 49 +5606 3 1997-03-11 46 +5606 7 1997-02-01 46 +5762 4 1997-03-02 47 +581 3 1997-02-27 49 +5829 5 1997-01-31 49 +5831 4 1997-02-24 46 +5895 2 1997-04-27 47 +5895 3 1997-03-15 49 +5952 1 1997-06-30 49 +705 1 1997-04-18 46 +836 3 1997-03-21 46 +set statement optimizer_switch='rowid_filter=on' for EXPLAIN SELECT o_orderkey, l_linenumber, l_shipdate, o_totalprice +FROM orders JOIN lineitem ON o_orderkey=l_orderkey +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-01-31' AND +o_totalprice between 200000 and 230000; +id select_type table type possible_keys key key_len ref rows Extra +1 SIMPLE lineitem range PRIMARY,i_l_shipdate,i_l_orderkey,i_l_orderkey_quantity i_l_shipdate 4 NULL 92 Using index condition +1 SIMPLE orders eq_ref|filter PRIMARY,i_o_totalprice PRIMARY|i_o_totalprice 4|9 dbt3_s001.lineitem.l_orderkey 1 (7%) Using where; Using rowid filter +set statement optimizer_switch='rowid_filter=on' for EXPLAIN FORMAT=JSON SELECT o_orderkey, l_linenumber, l_shipdate, o_totalprice +FROM orders JOIN lineitem ON o_orderkey=l_orderkey +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-01-31' AND +o_totalprice between 200000 and 230000; +EXPLAIN +{ + "query_block": { + "select_id": 1, + "nested_loop": [ + { + "table": { + "table_name": "lineitem", + "access_type": "range", + "possible_keys": [ + "PRIMARY", + "i_l_shipdate", + "i_l_orderkey", + "i_l_orderkey_quantity" + ], + "key": "i_l_shipdate", + "key_length": "4", + "used_key_parts": ["l_shipDATE"], + "rows": 92, + "filtered": 100, + "index_condition": "lineitem.l_shipDATE between '1997-01-01' and '1997-01-31'" + } + }, + { + "table": { + "table_name": "orders", + "access_type": "eq_ref", + "possible_keys": ["PRIMARY", "i_o_totalprice"], + "key": "PRIMARY", + "key_length": "4", + "used_key_parts": ["o_orderkey"], + "ref": ["dbt3_s001.lineitem.l_orderkey"], + "rowid_filter": { + "range": { + "key": "i_o_totalprice", + "used_key_parts": ["o_totalprice"] + }, + "rows": 106, + "selectivity_pct": 7.066666667 + }, + "rows": 1, + "filtered": 7.066666603, + "attached_condition": "orders.o_totalprice between 200000 and 230000" + } + } + ] + } +} +set statement optimizer_switch='rowid_filter=on' for ANALYZE SELECT o_orderkey, l_linenumber, l_shipdate, o_totalprice +FROM orders JOIN lineitem ON o_orderkey=l_orderkey +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-01-31' AND +o_totalprice between 200000 and 230000; +id select_type table type possible_keys key key_len ref rows r_rows filtered r_filtered Extra +1 SIMPLE lineitem range PRIMARY,i_l_shipdate,i_l_orderkey,i_l_orderkey_quantity i_l_shipdate 4 NULL 92 98.00 100.00 100.00 Using index condition +1 SIMPLE orders eq_ref|filter PRIMARY,i_o_totalprice PRIMARY|i_o_totalprice 4|9 dbt3_s001.lineitem.l_orderkey 1 (7%) 0.11 (10%) 7.07 100.00 Using where; Using rowid filter +set statement optimizer_switch='rowid_filter=on' for ANALYZE FORMAT=JSON SELECT o_orderkey, l_linenumber, l_shipdate, o_totalprice +FROM orders JOIN lineitem ON o_orderkey=l_orderkey +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-01-31' AND +o_totalprice between 200000 and 230000; +ANALYZE +{ + "query_optimization": { + "r_total_time_ms": "REPLACED" + }, + "query_block": { + "select_id": 1, + "r_loops": 1, + "r_total_time_ms": "REPLACED", + "nested_loop": [ + { + "table": { + "table_name": "lineitem", + "access_type": "range", + "possible_keys": [ + "PRIMARY", + "i_l_shipdate", + "i_l_orderkey", + "i_l_orderkey_quantity" + ], + "key": "i_l_shipdate", + "key_length": "4", + "used_key_parts": ["l_shipDATE"], + "r_loops": 1, + "rows": 92, + "r_rows": 98, + "r_table_time_ms": "REPLACED", + "r_other_time_ms": "REPLACED", + "filtered": 100, + "r_filtered": 100, + "index_condition": "lineitem.l_shipDATE between '1997-01-01' and '1997-01-31'" + } + }, + { + "table": { + "table_name": "orders", + "access_type": "eq_ref", + "possible_keys": ["PRIMARY", "i_o_totalprice"], + "key": "PRIMARY", + "key_length": "4", + "used_key_parts": ["o_orderkey"], + "ref": ["dbt3_s001.lineitem.l_orderkey"], + "rowid_filter": { + "range": { + "key": "i_o_totalprice", + "used_key_parts": ["o_totalprice"] + }, + "rows": 106, + "selectivity_pct": 7.066666667, + "r_rows": 71, + "r_lookups": 96, + "r_selectivity_pct": 10.41666667, + "r_buffer_size": "REPLACED", + "r_filling_time_ms": "REPLACED" + }, + "r_loops": 98, + "rows": 1, + "r_rows": 0.112244898, + "r_table_time_ms": "REPLACED", + "r_other_time_ms": "REPLACED", + "filtered": 7.066666603, + "r_filtered": 100, + "attached_condition": "orders.o_totalprice between 200000 and 230000" + } + } + ] + } +} +set statement optimizer_switch='rowid_filter=on' for SELECT o_orderkey, l_linenumber, l_shipdate, o_totalprice +FROM orders JOIN lineitem ON o_orderkey=l_orderkey +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-01-31' AND +o_totalprice between 200000 and 230000; +o_orderkey l_linenumber l_shipdate o_totalprice +1156 3 1997-01-24 217682.81 +1156 4 1997-01-18 217682.81 +1156 6 1997-01-27 217682.81 +1156 7 1997-01-01 217682.81 +2180 2 1997-01-03 208481.57 +2180 3 1997-01-03 208481.57 +3619 1 1997-01-22 222274.54 +3619 3 1997-01-31 222274.54 +3619 6 1997-01-25 222274.54 +484 3 1997-01-24 219920.62 +5606 6 1997-01-11 219959.08 +set statement optimizer_switch='rowid_filter=off' for EXPLAIN SELECT o_orderkey, l_linenumber, l_shipdate, o_totalprice +FROM orders JOIN lineitem ON o_orderkey=l_orderkey +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-01-31' AND +o_totalprice between 200000 and 230000; +id select_type table type possible_keys key key_len ref rows Extra +1 SIMPLE lineitem range PRIMARY,i_l_shipdate,i_l_orderkey,i_l_orderkey_quantity i_l_shipdate 4 NULL 92 Using index condition +1 SIMPLE orders eq_ref PRIMARY,i_o_totalprice PRIMARY 4 dbt3_s001.lineitem.l_orderkey 1 Using where +set statement optimizer_switch='rowid_filter=off' for EXPLAIN FORMAT=JSON SELECT o_orderkey, l_linenumber, l_shipdate, o_totalprice +FROM orders JOIN lineitem ON o_orderkey=l_orderkey +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-01-31' AND +o_totalprice between 200000 and 230000; +EXPLAIN +{ + "query_block": { + "select_id": 1, + "nested_loop": [ + { + "table": { + "table_name": "lineitem", + "access_type": "range", + "possible_keys": [ + "PRIMARY", + "i_l_shipdate", + "i_l_orderkey", + "i_l_orderkey_quantity" + ], + "key": "i_l_shipdate", + "key_length": "4", + "used_key_parts": ["l_shipDATE"], + "rows": 92, + "filtered": 100, + "index_condition": "lineitem.l_shipDATE between '1997-01-01' and '1997-01-31'" + } + }, + { + "table": { + "table_name": "orders", + "access_type": "eq_ref", + "possible_keys": ["PRIMARY", "i_o_totalprice"], + "key": "PRIMARY", + "key_length": "4", + "used_key_parts": ["o_orderkey"], + "ref": ["dbt3_s001.lineitem.l_orderkey"], + "rows": 1, + "filtered": 7.066666603, + "attached_condition": "orders.o_totalprice between 200000 and 230000" + } + } + ] + } +} +set statement optimizer_switch='rowid_filter=off' for ANALYZE SELECT o_orderkey, l_linenumber, l_shipdate, o_totalprice +FROM orders JOIN lineitem ON o_orderkey=l_orderkey +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-01-31' AND +o_totalprice between 200000 and 230000; +id select_type table type possible_keys key key_len ref rows r_rows filtered r_filtered Extra +1 SIMPLE lineitem range PRIMARY,i_l_shipdate,i_l_orderkey,i_l_orderkey_quantity i_l_shipdate 4 NULL 92 98.00 100.00 100.00 Using index condition +1 SIMPLE orders eq_ref PRIMARY,i_o_totalprice PRIMARY 4 dbt3_s001.lineitem.l_orderkey 1 1.00 7.07 11.22 Using where +set statement optimizer_switch='rowid_filter=off' for ANALYZE FORMAT=JSON SELECT o_orderkey, l_linenumber, l_shipdate, o_totalprice +FROM orders JOIN lineitem ON o_orderkey=l_orderkey +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-01-31' AND +o_totalprice between 200000 and 230000; +ANALYZE +{ + "query_optimization": { + "r_total_time_ms": "REPLACED" + }, + "query_block": { + "select_id": 1, + "r_loops": 1, + "r_total_time_ms": "REPLACED", + "nested_loop": [ + { + "table": { + "table_name": "lineitem", + "access_type": "range", + "possible_keys": [ + "PRIMARY", + "i_l_shipdate", + "i_l_orderkey", + "i_l_orderkey_quantity" + ], + "key": "i_l_shipdate", + "key_length": "4", + "used_key_parts": ["l_shipDATE"], + "r_loops": 1, + "rows": 92, + "r_rows": 98, + "r_table_time_ms": "REPLACED", + "r_other_time_ms": "REPLACED", + "filtered": 100, + "r_filtered": 100, + "index_condition": "lineitem.l_shipDATE between '1997-01-01' and '1997-01-31'" + } + }, + { + "table": { + "table_name": "orders", + "access_type": "eq_ref", + "possible_keys": ["PRIMARY", "i_o_totalprice"], + "key": "PRIMARY", + "key_length": "4", + "used_key_parts": ["o_orderkey"], + "ref": ["dbt3_s001.lineitem.l_orderkey"], + "r_loops": 98, + "rows": 1, + "r_rows": 1, + "r_table_time_ms": "REPLACED", + "r_other_time_ms": "REPLACED", + "filtered": 7.066666603, + "r_filtered": 11.2244898, + "attached_condition": "orders.o_totalprice between 200000 and 230000" + } + } + ] + } +} +set statement optimizer_switch='rowid_filter=off' for SELECT o_orderkey, l_linenumber, l_shipdate, o_totalprice +FROM orders JOIN lineitem ON o_orderkey=l_orderkey +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-01-31' AND +o_totalprice between 200000 and 230000; +o_orderkey l_linenumber l_shipdate o_totalprice +1156 3 1997-01-24 217682.81 +1156 4 1997-01-18 217682.81 +1156 6 1997-01-27 217682.81 +1156 7 1997-01-01 217682.81 +2180 2 1997-01-03 208481.57 +2180 3 1997-01-03 208481.57 +3619 1 1997-01-22 222274.54 +3619 3 1997-01-31 222274.54 +3619 6 1997-01-25 222274.54 +484 3 1997-01-24 219920.62 +5606 6 1997-01-11 219959.08 +set statement optimizer_switch='rowid_filter=on' for EXPLAIN SELECT o_orderkey, l_linenumber, l_shipdate, l_quantity, o_totalprice +FROM orders JOIN lineitem ON o_orderkey=l_orderkey +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-06-30' AND +l_quantity > 45 AND +o_totalprice between 180000 and 230000; +id select_type table type possible_keys key key_len ref rows Extra +1 SIMPLE lineitem range|filter PRIMARY,i_l_shipdate,i_l_orderkey,i_l_orderkey_quantity,i_l_quantity i_l_shipdate|i_l_quantity 4|9 NULL 482 (16%) Using index condition; Using where; Using rowid filter +1 SIMPLE orders eq_ref|filter PRIMARY,i_o_totalprice PRIMARY|i_o_totalprice 4|9 dbt3_s001.lineitem.l_orderkey 1 (14%) Using where; Using rowid filter +set statement optimizer_switch='rowid_filter=on' for EXPLAIN FORMAT=JSON SELECT o_orderkey, l_linenumber, l_shipdate, l_quantity, o_totalprice +FROM orders JOIN lineitem ON o_orderkey=l_orderkey +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-06-30' AND +l_quantity > 45 AND +o_totalprice between 180000 and 230000; +EXPLAIN +{ + "query_block": { + "select_id": 1, + "nested_loop": [ + { + "table": { + "table_name": "lineitem", + "access_type": "range", + "possible_keys": [ + "PRIMARY", + "i_l_shipdate", + "i_l_orderkey", + "i_l_orderkey_quantity", + "i_l_quantity" + ], + "key": "i_l_shipdate", + "key_length": "4", + "used_key_parts": ["l_shipDATE"], + "rowid_filter": { + "range": { + "key": "i_l_quantity", + "used_key_parts": ["l_quantity"] + }, + "rows": 949, + "selectivity_pct": 15.80349709 + }, + "rows": 482, + "filtered": 15.80349731, + "index_condition": "lineitem.l_shipDATE between '1997-01-01' and '1997-06-30'", + "attached_condition": "lineitem.l_quantity > 45" + } + }, + { + "table": { + "table_name": "orders", + "access_type": "eq_ref", + "possible_keys": ["PRIMARY", "i_o_totalprice"], + "key": "PRIMARY", + "key_length": "4", + "used_key_parts": ["o_orderkey"], + "ref": ["dbt3_s001.lineitem.l_orderkey"], + "rowid_filter": { + "range": { + "key": "i_o_totalprice", + "used_key_parts": ["o_totalprice"] + }, + "rows": 216, + "selectivity_pct": 14.4 + }, + "rows": 1, + "filtered": 14.39999962, + "attached_condition": "orders.o_totalprice between 180000 and 230000" + } + } + ] + } +} +set statement optimizer_switch='rowid_filter=on' for ANALYZE SELECT o_orderkey, l_linenumber, l_shipdate, l_quantity, o_totalprice +FROM orders JOIN lineitem ON o_orderkey=l_orderkey +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-06-30' AND +l_quantity > 45 AND +o_totalprice between 180000 and 230000; +id select_type table type possible_keys key key_len ref rows r_rows filtered r_filtered Extra +1 SIMPLE lineitem range|filter PRIMARY,i_l_shipdate,i_l_orderkey,i_l_orderkey_quantity,i_l_quantity i_l_shipdate|i_l_quantity 4|9 NULL 482 (16%) 60.00 (11%) 15.80 100.00 Using index condition; Using where; Using rowid filter +1 SIMPLE orders eq_ref|filter PRIMARY,i_o_totalprice PRIMARY|i_o_totalprice 4|9 dbt3_s001.lineitem.l_orderkey 1 (14%) 0.27 (25%) 14.40 100.00 Using where; Using rowid filter +set statement optimizer_switch='rowid_filter=on' for ANALYZE FORMAT=JSON SELECT o_orderkey, l_linenumber, l_shipdate, l_quantity, o_totalprice +FROM orders JOIN lineitem ON o_orderkey=l_orderkey +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-06-30' AND +l_quantity > 45 AND +o_totalprice between 180000 and 230000; +ANALYZE +{ + "query_optimization": { + "r_total_time_ms": "REPLACED" + }, + "query_block": { + "select_id": 1, + "r_loops": 1, + "r_total_time_ms": "REPLACED", + "nested_loop": [ + { + "table": { + "table_name": "lineitem", + "access_type": "range", + "possible_keys": [ + "PRIMARY", + "i_l_shipdate", + "i_l_orderkey", + "i_l_orderkey_quantity", + "i_l_quantity" + ], + "key": "i_l_shipdate", + "key_length": "4", + "used_key_parts": ["l_shipDATE"], + "rowid_filter": { + "range": { + "key": "i_l_quantity", + "used_key_parts": ["l_quantity"] + }, + "rows": 949, + "selectivity_pct": 15.80349709, + "r_rows": 605, + "r_lookups": 510, + "r_selectivity_pct": 11.76470588, + "r_buffer_size": "REPLACED", + "r_filling_time_ms": "REPLACED" + }, + "r_loops": 1, + "rows": 482, + "r_rows": 60, + "r_table_time_ms": "REPLACED", + "r_other_time_ms": "REPLACED", + "filtered": 15.80349731, + "r_filtered": 100, + "index_condition": "lineitem.l_shipDATE between '1997-01-01' and '1997-06-30'", + "attached_condition": "lineitem.l_quantity > 45" + } + }, + { + "table": { + "table_name": "orders", + "access_type": "eq_ref", + "possible_keys": ["PRIMARY", "i_o_totalprice"], + "key": "PRIMARY", + "key_length": "4", + "used_key_parts": ["o_orderkey"], + "ref": ["dbt3_s001.lineitem.l_orderkey"], + "rowid_filter": { + "range": { + "key": "i_o_totalprice", + "used_key_parts": ["o_totalprice"] + }, + "rows": 216, + "selectivity_pct": 14.4, + "r_rows": 144, + "r_lookups": 59, + "r_selectivity_pct": 25.42372881, + "r_buffer_size": "REPLACED", + "r_filling_time_ms": "REPLACED" + }, + "r_loops": 60, + "rows": 1, + "r_rows": 0.266666667, + "r_table_time_ms": "REPLACED", + "r_other_time_ms": "REPLACED", + "filtered": 14.39999962, + "r_filtered": 100, + "attached_condition": "orders.o_totalprice between 180000 and 230000" + } + } + ] + } +} +set statement optimizer_switch='rowid_filter=on' for SELECT o_orderkey, l_linenumber, l_shipdate, l_quantity, o_totalprice +FROM orders JOIN lineitem ON o_orderkey=l_orderkey +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-06-30' AND +l_quantity > 45 AND +o_totalprice between 180000 and 230000; +o_orderkey l_linenumber l_shipdate l_quantity o_totalprice +1632 1 1997-01-25 47 183286.33 +1632 3 1997-01-29 47 183286.33 +2177 5 1997-05-10 46 183493.42 +2469 3 1997-01-11 48 192074.23 +2469 6 1997-03-03 49 192074.23 +3619 1 1997-01-22 49 222274.54 +3619 3 1997-01-31 46 222274.54 +484 1 1997-03-06 49 219920.62 +484 3 1997-01-24 50 219920.62 +484 5 1997-03-05 48 219920.62 +4934 1 1997-05-20 48 180478.16 +5606 3 1997-03-11 46 219959.08 +5606 7 1997-02-01 46 219959.08 +5829 5 1997-01-31 49 183734.56 +5895 2 1997-04-27 47 201419.83 +5895 3 1997-03-15 49 201419.83 +set statement optimizer_switch='rowid_filter=off' for EXPLAIN SELECT o_orderkey, l_linenumber, l_shipdate, l_quantity, o_totalprice +FROM orders JOIN lineitem ON o_orderkey=l_orderkey +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-06-30' AND +l_quantity > 45 AND +o_totalprice between 180000 and 230000; +id select_type table type possible_keys key key_len ref rows Extra +1 SIMPLE lineitem range PRIMARY,i_l_shipdate,i_l_orderkey,i_l_orderkey_quantity,i_l_quantity i_l_shipdate 4 NULL 482 Using index condition; Using where +1 SIMPLE orders eq_ref PRIMARY,i_o_totalprice PRIMARY 4 dbt3_s001.lineitem.l_orderkey 1 Using where +set statement optimizer_switch='rowid_filter=off' for EXPLAIN FORMAT=JSON SELECT o_orderkey, l_linenumber, l_shipdate, l_quantity, o_totalprice +FROM orders JOIN lineitem ON o_orderkey=l_orderkey +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-06-30' AND +l_quantity > 45 AND +o_totalprice between 180000 and 230000; +EXPLAIN +{ + "query_block": { + "select_id": 1, + "nested_loop": [ + { + "table": { + "table_name": "lineitem", + "access_type": "range", + "possible_keys": [ + "PRIMARY", + "i_l_shipdate", + "i_l_orderkey", + "i_l_orderkey_quantity", + "i_l_quantity" + ], + "key": "i_l_shipdate", + "key_length": "4", + "used_key_parts": ["l_shipDATE"], + "rows": 482, + "filtered": 15.80349731, + "index_condition": "lineitem.l_shipDATE between '1997-01-01' and '1997-06-30'", + "attached_condition": "lineitem.l_quantity > 45" + } + }, + { + "table": { + "table_name": "orders", + "access_type": "eq_ref", + "possible_keys": ["PRIMARY", "i_o_totalprice"], + "key": "PRIMARY", + "key_length": "4", + "used_key_parts": ["o_orderkey"], + "ref": ["dbt3_s001.lineitem.l_orderkey"], + "rows": 1, + "filtered": 14.39999962, + "attached_condition": "orders.o_totalprice between 180000 and 230000" + } + } + ] + } +} +set statement optimizer_switch='rowid_filter=off' for ANALYZE SELECT o_orderkey, l_linenumber, l_shipdate, l_quantity, o_totalprice +FROM orders JOIN lineitem ON o_orderkey=l_orderkey +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-06-30' AND +l_quantity > 45 AND +o_totalprice between 180000 and 230000; +id select_type table type possible_keys key key_len ref rows r_rows filtered r_filtered Extra +1 SIMPLE lineitem range PRIMARY,i_l_shipdate,i_l_orderkey,i_l_orderkey_quantity,i_l_quantity i_l_shipdate 4 NULL 482 510.00 15.80 11.76 Using index condition; Using where +1 SIMPLE orders eq_ref PRIMARY,i_o_totalprice PRIMARY 4 dbt3_s001.lineitem.l_orderkey 1 1.00 14.40 26.67 Using where +set statement optimizer_switch='rowid_filter=off' for ANALYZE FORMAT=JSON SELECT o_orderkey, l_linenumber, l_shipdate, l_quantity, o_totalprice +FROM orders JOIN lineitem ON o_orderkey=l_orderkey +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-06-30' AND +l_quantity > 45 AND +o_totalprice between 180000 and 230000; +ANALYZE +{ + "query_optimization": { + "r_total_time_ms": "REPLACED" + }, + "query_block": { + "select_id": 1, + "r_loops": 1, + "r_total_time_ms": "REPLACED", + "nested_loop": [ + { + "table": { + "table_name": "lineitem", + "access_type": "range", + "possible_keys": [ + "PRIMARY", + "i_l_shipdate", + "i_l_orderkey", + "i_l_orderkey_quantity", + "i_l_quantity" + ], + "key": "i_l_shipdate", + "key_length": "4", + "used_key_parts": ["l_shipDATE"], + "r_loops": 1, + "rows": 482, + "r_rows": 510, + "r_table_time_ms": "REPLACED", + "r_other_time_ms": "REPLACED", + "filtered": 15.80349731, + "r_filtered": 11.76470588, + "index_condition": "lineitem.l_shipDATE between '1997-01-01' and '1997-06-30'", + "attached_condition": "lineitem.l_quantity > 45" + } + }, + { + "table": { + "table_name": "orders", + "access_type": "eq_ref", + "possible_keys": ["PRIMARY", "i_o_totalprice"], + "key": "PRIMARY", + "key_length": "4", + "used_key_parts": ["o_orderkey"], + "ref": ["dbt3_s001.lineitem.l_orderkey"], + "r_loops": 60, + "rows": 1, + "r_rows": 1, + "r_table_time_ms": "REPLACED", + "r_other_time_ms": "REPLACED", + "filtered": 14.39999962, + "r_filtered": 26.66666667, + "attached_condition": "orders.o_totalprice between 180000 and 230000" + } + } + ] + } +} +set statement optimizer_switch='rowid_filter=off' for SELECT o_orderkey, l_linenumber, l_shipdate, l_quantity, o_totalprice +FROM orders JOIN lineitem ON o_orderkey=l_orderkey +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-06-30' AND +l_quantity > 45 AND +o_totalprice between 180000 and 230000; +o_orderkey l_linenumber l_shipdate l_quantity o_totalprice +1632 1 1997-01-25 47 183286.33 +1632 3 1997-01-29 47 183286.33 +2177 5 1997-05-10 46 183493.42 +2469 3 1997-01-11 48 192074.23 +2469 6 1997-03-03 49 192074.23 +3619 1 1997-01-22 49 222274.54 +3619 3 1997-01-31 46 222274.54 +484 1 1997-03-06 49 219920.62 +484 3 1997-01-24 50 219920.62 +484 5 1997-03-05 48 219920.62 +4934 1 1997-05-20 48 180478.16 +5606 3 1997-03-11 46 219959.08 +5606 7 1997-02-01 46 219959.08 +5829 5 1997-01-31 49 183734.56 +5895 2 1997-04-27 47 201419.83 +5895 3 1997-03-15 49 201419.83 +set statement optimizer_switch='rowid_filter=on' for EXPLAIN SELECT STRAIGHT_JOIN o_orderkey, l_linenumber, l_shipdate, l_quantity, o_totalprice +FROM lineitem JOIN orders ON o_orderkey=l_orderkey +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-06-30' AND +l_quantity > 45 AND +o_totalprice between 180000 and 230000; +id select_type table type possible_keys key key_len ref rows Extra +1 SIMPLE lineitem range|filter PRIMARY,i_l_shipdate,i_l_orderkey,i_l_orderkey_quantity,i_l_quantity i_l_shipdate|i_l_quantity 4|9 NULL 482 (16%) Using index condition; Using where; Using rowid filter +1 SIMPLE orders eq_ref|filter PRIMARY,i_o_totalprice PRIMARY|i_o_totalprice 4|9 dbt3_s001.lineitem.l_orderkey 1 (14%) Using where; Using rowid filter +set statement optimizer_switch='rowid_filter=on' for EXPLAIN SELECT o_orderkey, l_linenumber, l_shipdate, o_totalprice +FROM orders JOIN lineitem ON o_orderkey=l_orderkey +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-06-30' AND +o_totalprice between 200000 and 230000; +id select_type table type possible_keys key key_len ref rows Extra +1 SIMPLE orders range PRIMARY,i_o_totalprice i_o_totalprice 9 NULL 106 Using index condition +1 SIMPLE lineitem ref|filter PRIMARY,i_l_shipdate,i_l_orderkey,i_l_orderkey_quantity i_l_orderkey|i_l_shipdate 4|4 dbt3_s001.orders.o_orderkey 4 (8%) Using where; Using rowid filter +set statement optimizer_switch='rowid_filter=on' for EXPLAIN FORMAT=JSON SELECT o_orderkey, l_linenumber, l_shipdate, o_totalprice +FROM orders JOIN lineitem ON o_orderkey=l_orderkey +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-06-30' AND +o_totalprice between 200000 and 230000; +EXPLAIN +{ + "query_block": { + "select_id": 1, + "nested_loop": [ + { + "table": { + "table_name": "orders", + "access_type": "range", + "possible_keys": ["PRIMARY", "i_o_totalprice"], + "key": "i_o_totalprice", + "key_length": "9", + "used_key_parts": ["o_totalprice"], + "rows": 106, + "filtered": 100, + "index_condition": "orders.o_totalprice between 200000 and 230000" + } + }, + { + "table": { + "table_name": "lineitem", + "access_type": "ref", + "possible_keys": [ + "PRIMARY", + "i_l_shipdate", + "i_l_orderkey", + "i_l_orderkey_quantity" + ], + "key": "i_l_orderkey", + "key_length": "4", + "used_key_parts": ["l_orderkey"], + "ref": ["dbt3_s001.orders.o_orderkey"], + "rowid_filter": { + "range": { + "key": "i_l_shipdate", + "used_key_parts": ["l_shipDATE"] + }, + "rows": 482, + "selectivity_pct": 8.026644463 + }, + "rows": 4, + "filtered": 8.026644707, + "attached_condition": "lineitem.l_shipDATE between '1997-01-01' and '1997-06-30'" + } + } + ] + } +} +set statement optimizer_switch='rowid_filter=on' for ANALYZE SELECT o_orderkey, l_linenumber, l_shipdate, o_totalprice +FROM orders JOIN lineitem ON o_orderkey=l_orderkey +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-06-30' AND +o_totalprice between 200000 and 230000; +id select_type table type possible_keys key key_len ref rows r_rows filtered r_filtered Extra +1 SIMPLE orders range PRIMARY,i_o_totalprice i_o_totalprice 9 NULL 106 71.00 100.00 100.00 Using index condition +1 SIMPLE lineitem ref|filter PRIMARY,i_l_shipdate,i_l_orderkey,i_l_orderkey_quantity i_l_orderkey|i_l_shipdate 4|4 dbt3_s001.orders.o_orderkey 4 (8%) 0.52 (7%) 8.03 100.00 Using where; Using rowid filter +set statement optimizer_switch='rowid_filter=on' for ANALYZE FORMAT=JSON SELECT o_orderkey, l_linenumber, l_shipdate, o_totalprice +FROM orders JOIN lineitem ON o_orderkey=l_orderkey +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-06-30' AND +o_totalprice between 200000 and 230000; +ANALYZE +{ + "query_optimization": { + "r_total_time_ms": "REPLACED" + }, + "query_block": { + "select_id": 1, + "r_loops": 1, + "r_total_time_ms": "REPLACED", + "nested_loop": [ + { + "table": { + "table_name": "orders", + "access_type": "range", + "possible_keys": ["PRIMARY", "i_o_totalprice"], + "key": "i_o_totalprice", + "key_length": "9", + "used_key_parts": ["o_totalprice"], + "r_loops": 1, + "rows": 106, + "r_rows": 71, + "r_table_time_ms": "REPLACED", + "r_other_time_ms": "REPLACED", + "filtered": 100, + "r_filtered": 100, + "index_condition": "orders.o_totalprice between 200000 and 230000" + } + }, + { + "table": { + "table_name": "lineitem", + "access_type": "ref", + "possible_keys": [ + "PRIMARY", + "i_l_shipdate", + "i_l_orderkey", + "i_l_orderkey_quantity" + ], + "key": "i_l_orderkey", + "key_length": "4", + "used_key_parts": ["l_orderkey"], + "ref": ["dbt3_s001.orders.o_orderkey"], + "rowid_filter": { + "range": { + "key": "i_l_shipdate", + "used_key_parts": ["l_shipDATE"] + }, + "rows": 482, + "selectivity_pct": 8.026644463, + "r_rows": 510, + "r_lookups": 476, + "r_selectivity_pct": 7.773109244, + "r_buffer_size": "REPLACED", + "r_filling_time_ms": "REPLACED" + }, + "r_loops": 71, + "rows": 4, + "r_rows": 0.521126761, + "r_table_time_ms": "REPLACED", + "r_other_time_ms": "REPLACED", + "filtered": 8.026644707, + "r_filtered": 100, + "attached_condition": "lineitem.l_shipDATE between '1997-01-01' and '1997-06-30'" + } + } + ] + } +} +set statement optimizer_switch='rowid_filter=on' for SELECT o_orderkey, l_linenumber, l_shipdate, o_totalprice +FROM orders JOIN lineitem ON o_orderkey=l_orderkey +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-06-30' AND +o_totalprice between 200000 and 230000; +o_orderkey l_linenumber l_shipdate o_totalprice +1156 3 1997-01-24 217682.81 +1156 4 1997-01-18 217682.81 +1156 6 1997-01-27 217682.81 +1156 7 1997-01-01 217682.81 +1890 1 1997-04-02 202364.58 +1890 3 1997-02-09 202364.58 +1890 4 1997-04-08 202364.58 +1890 5 1997-04-15 202364.58 +1890 6 1997-02-13 202364.58 +2180 2 1997-01-03 208481.57 +2180 3 1997-01-03 208481.57 +3619 1 1997-01-22 222274.54 +3619 3 1997-01-31 222274.54 +3619 4 1997-03-18 222274.54 +3619 6 1997-01-25 222274.54 +453 1 1997-06-30 216826.73 +453 2 1997-06-30 216826.73 +484 1 1997-03-06 219920.62 +484 2 1997-04-09 219920.62 +484 3 1997-01-24 219920.62 +484 4 1997-04-29 219920.62 +484 5 1997-03-05 219920.62 +484 6 1997-04-06 219920.62 +5606 2 1997-02-23 219959.08 +5606 3 1997-03-11 219959.08 +5606 4 1997-02-06 219959.08 +5606 6 1997-01-11 219959.08 +5606 7 1997-02-01 219959.08 +5859 2 1997-05-15 210643.96 +5859 5 1997-05-28 210643.96 +5859 6 1997-06-15 210643.96 +5895 1 1997-04-05 201419.83 +5895 2 1997-04-27 201419.83 +5895 3 1997-03-15 201419.83 +5895 4 1997-03-03 201419.83 +5895 5 1997-04-30 201419.83 +5895 6 1997-04-19 201419.83 +set statement optimizer_switch='rowid_filter=off' for EXPLAIN SELECT o_orderkey, l_linenumber, l_shipdate, o_totalprice +FROM orders JOIN lineitem ON o_orderkey=l_orderkey +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-06-30' AND +o_totalprice between 200000 and 230000; +id select_type table type possible_keys key key_len ref rows Extra +1 SIMPLE orders range PRIMARY,i_o_totalprice i_o_totalprice 9 NULL 106 Using index condition +1 SIMPLE lineitem ref PRIMARY,i_l_shipdate,i_l_orderkey,i_l_orderkey_quantity i_l_orderkey 4 dbt3_s001.orders.o_orderkey 4 Using where +set statement optimizer_switch='rowid_filter=off' for EXPLAIN FORMAT=JSON SELECT o_orderkey, l_linenumber, l_shipdate, o_totalprice +FROM orders JOIN lineitem ON o_orderkey=l_orderkey +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-06-30' AND +o_totalprice between 200000 and 230000; +EXPLAIN +{ + "query_block": { + "select_id": 1, + "nested_loop": [ + { + "table": { + "table_name": "orders", + "access_type": "range", + "possible_keys": ["PRIMARY", "i_o_totalprice"], + "key": "i_o_totalprice", + "key_length": "9", + "used_key_parts": ["o_totalprice"], + "rows": 106, + "filtered": 100, + "index_condition": "orders.o_totalprice between 200000 and 230000" + } + }, + { + "table": { + "table_name": "lineitem", + "access_type": "ref", + "possible_keys": [ + "PRIMARY", + "i_l_shipdate", + "i_l_orderkey", + "i_l_orderkey_quantity" + ], + "key": "i_l_orderkey", + "key_length": "4", + "used_key_parts": ["l_orderkey"], + "ref": ["dbt3_s001.orders.o_orderkey"], + "rows": 4, + "filtered": 8.026644707, + "attached_condition": "lineitem.l_shipDATE between '1997-01-01' and '1997-06-30'" + } + } + ] + } +} +set statement optimizer_switch='rowid_filter=off' for ANALYZE SELECT o_orderkey, l_linenumber, l_shipdate, o_totalprice +FROM orders JOIN lineitem ON o_orderkey=l_orderkey +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-06-30' AND +o_totalprice between 200000 and 230000; +id select_type table type possible_keys key key_len ref rows r_rows filtered r_filtered Extra +1 SIMPLE orders range PRIMARY,i_o_totalprice i_o_totalprice 9 NULL 106 71.00 100.00 100.00 Using index condition +1 SIMPLE lineitem ref PRIMARY,i_l_shipdate,i_l_orderkey,i_l_orderkey_quantity i_l_orderkey 4 dbt3_s001.orders.o_orderkey 4 6.70 8.03 7.77 Using where +set statement optimizer_switch='rowid_filter=off' for ANALYZE FORMAT=JSON SELECT o_orderkey, l_linenumber, l_shipdate, o_totalprice +FROM orders JOIN lineitem ON o_orderkey=l_orderkey +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-06-30' AND +o_totalprice between 200000 and 230000; +ANALYZE +{ + "query_optimization": { + "r_total_time_ms": "REPLACED" + }, + "query_block": { + "select_id": 1, + "r_loops": 1, + "r_total_time_ms": "REPLACED", + "nested_loop": [ + { + "table": { + "table_name": "orders", + "access_type": "range", + "possible_keys": ["PRIMARY", "i_o_totalprice"], + "key": "i_o_totalprice", + "key_length": "9", + "used_key_parts": ["o_totalprice"], + "r_loops": 1, + "rows": 106, + "r_rows": 71, + "r_table_time_ms": "REPLACED", + "r_other_time_ms": "REPLACED", + "filtered": 100, + "r_filtered": 100, + "index_condition": "orders.o_totalprice between 200000 and 230000" + } + }, + { + "table": { + "table_name": "lineitem", + "access_type": "ref", + "possible_keys": [ + "PRIMARY", + "i_l_shipdate", + "i_l_orderkey", + "i_l_orderkey_quantity" + ], + "key": "i_l_orderkey", + "key_length": "4", + "used_key_parts": ["l_orderkey"], + "ref": ["dbt3_s001.orders.o_orderkey"], + "r_loops": 71, + "rows": 4, + "r_rows": 6.704225352, + "r_table_time_ms": "REPLACED", + "r_other_time_ms": "REPLACED", + "filtered": 8.026644707, + "r_filtered": 7.773109244, + "attached_condition": "lineitem.l_shipDATE between '1997-01-01' and '1997-06-30'" + } + } + ] + } +} +set statement optimizer_switch='rowid_filter=off' for SELECT o_orderkey, l_linenumber, l_shipdate, o_totalprice +FROM orders JOIN lineitem ON o_orderkey=l_orderkey +WHERE l_shipdate BETWEEN '1997-01-01' AND '1997-06-30' AND +o_totalprice between 200000 and 230000; +o_orderkey l_linenumber l_shipdate o_totalprice +1156 3 1997-01-24 217682.81 +1156 4 1997-01-18 217682.81 +1156 6 1997-01-27 217682.81 +1156 7 1997-01-01 217682.81 +1890 1 1997-04-02 202364.58 +1890 3 1997-02-09 202364.58 +1890 4 1997-04-08 202364.58 +1890 5 1997-04-15 202364.58 +1890 6 1997-02-13 202364.58 +2180 2 1997-01-03 208481.57 +2180 3 1997-01-03 208481.57 +3619 1 1997-01-22 222274.54 +3619 3 1997-01-31 222274.54 +3619 4 1997-03-18 222274.54 +3619 6 1997-01-25 222274.54 +453 1 1997-06-30 216826.73 +453 2 1997-06-30 216826.73 +484 1 1997-03-06 219920.62 +484 2 1997-04-09 219920.62 +484 3 1997-01-24 219920.62 +484 4 1997-04-29 219920.62 +484 5 1997-03-05 219920.62 +484 6 1997-04-06 219920.62 +5606 2 1997-02-23 219959.08 +5606 3 1997-03-11 219959.08 +5606 4 1997-02-06 219959.08 +5606 6 1997-01-11 219959.08 +5606 7 1997-02-01 219959.08 +5859 2 1997-05-15 210643.96 +5859 5 1997-05-28 210643.96 +5859 6 1997-06-15 210643.96 +5895 1 1997-04-05 201419.83 +5895 2 1997-04-27 201419.83 +5895 3 1997-03-15 201419.83 +5895 4 1997-03-03 201419.83 +5895 5 1997-04-30 201419.83 +5895 6 1997-04-19 201419.83 +# +# MDEV-18413: find constraint correlated indexes +# +ALTER TABLE lineitem ADD CONSTRAINT l_date CHECK(l_shipdate < l_receiptdate); +# Filter on l_shipdate is not used because it participates in +# the same constraint as l_receiptdate. +# Access is made on l_receiptdate. +set statement optimizer_switch='rowid_filter=on' for EXPLAIN SELECT l_shipdate, l_receiptdate, o_totalprice +FROM orders, lineitem +WHERE o_orderkey=l_orderkey AND +l_shipdate BETWEEN '1996-10-01' AND '1996-10-10' AND +l_receiptdate BETWEEN '1996-10-05' AND '1996-10-10' AND +o_totalprice BETWEEN 200000 AND 250000; +id select_type table type possible_keys key key_len ref rows Extra +1 SIMPLE lineitem range PRIMARY,i_l_shipdate,i_l_receiptdate,i_l_orderkey,i_l_orderkey_quantity i_l_receiptdate 4 NULL 17 Using index condition; Using where +1 SIMPLE orders eq_ref PRIMARY,i_o_totalprice PRIMARY 4 dbt3_s001.lineitem.l_orderkey 1 Using where +set statement optimizer_switch='rowid_filter=on' for EXPLAIN FORMAT=JSON SELECT l_shipdate, l_receiptdate, o_totalprice +FROM orders, lineitem +WHERE o_orderkey=l_orderkey AND +l_shipdate BETWEEN '1996-10-01' AND '1996-10-10' AND +l_receiptdate BETWEEN '1996-10-05' AND '1996-10-10' AND +o_totalprice BETWEEN 200000 AND 250000; +EXPLAIN +{ + "query_block": { + "select_id": 1, + "nested_loop": [ + { + "table": { + "table_name": "lineitem", + "access_type": "range", + "possible_keys": [ + "PRIMARY", + "i_l_shipdate", + "i_l_receiptdate", + "i_l_orderkey", + "i_l_orderkey_quantity" + ], + "key": "i_l_receiptdate", + "key_length": "4", + "used_key_parts": ["l_receiptDATE"], + "rows": 17, + "filtered": 0.532889247, + "index_condition": "lineitem.l_receiptDATE between '1996-10-05' and '1996-10-10'", + "attached_condition": "lineitem.l_shipDATE between '1996-10-01' and '1996-10-10'" + } + }, + { + "table": { + "table_name": "orders", + "access_type": "eq_ref", + "possible_keys": ["PRIMARY", "i_o_totalprice"], + "key": "PRIMARY", + "key_length": "4", + "used_key_parts": ["o_orderkey"], + "ref": ["dbt3_s001.lineitem.l_orderkey"], + "rows": 1, + "filtered": 8.466666222, + "attached_condition": "orders.o_totalprice between 200000 and 250000" + } + } + ] + } +} +set statement optimizer_switch='rowid_filter=on' for ANALYZE SELECT l_shipdate, l_receiptdate, o_totalprice +FROM orders, lineitem +WHERE o_orderkey=l_orderkey AND +l_shipdate BETWEEN '1996-10-01' AND '1996-10-10' AND +l_receiptdate BETWEEN '1996-10-05' AND '1996-10-10' AND +o_totalprice BETWEEN 200000 AND 250000; +id select_type table type possible_keys key key_len ref rows r_rows filtered r_filtered Extra +1 SIMPLE lineitem range PRIMARY,i_l_shipdate,i_l_receiptdate,i_l_orderkey,i_l_orderkey_quantity i_l_receiptdate 4 NULL 17 18.00 0.53 38.89 Using index condition; Using where +1 SIMPLE orders eq_ref PRIMARY,i_o_totalprice PRIMARY 4 dbt3_s001.lineitem.l_orderkey 1 1.00 8.47 14.29 Using where +set statement optimizer_switch='rowid_filter=on' for ANALYZE FORMAT=JSON SELECT l_shipdate, l_receiptdate, o_totalprice +FROM orders, lineitem +WHERE o_orderkey=l_orderkey AND +l_shipdate BETWEEN '1996-10-01' AND '1996-10-10' AND +l_receiptdate BETWEEN '1996-10-05' AND '1996-10-10' AND +o_totalprice BETWEEN 200000 AND 250000; +ANALYZE +{ + "query_optimization": { + "r_total_time_ms": "REPLACED" + }, + "query_block": { + "select_id": 1, + "r_loops": 1, + "r_total_time_ms": "REPLACED", + "nested_loop": [ + { + "table": { + "table_name": "lineitem", + "access_type": "range", + "possible_keys": [ + "PRIMARY", + "i_l_shipdate", + "i_l_receiptdate", + "i_l_orderkey", + "i_l_orderkey_quantity" + ], + "key": "i_l_receiptdate", + "key_length": "4", + "used_key_parts": ["l_receiptDATE"], + "r_loops": 1, + "rows": 17, + "r_rows": 18, + "r_table_time_ms": "REPLACED", + "r_other_time_ms": "REPLACED", + "filtered": 0.532889247, + "r_filtered": 38.88888889, + "index_condition": "lineitem.l_receiptDATE between '1996-10-05' and '1996-10-10'", + "attached_condition": "lineitem.l_shipDATE between '1996-10-01' and '1996-10-10'" + } + }, + { + "table": { + "table_name": "orders", + "access_type": "eq_ref", + "possible_keys": ["PRIMARY", "i_o_totalprice"], + "key": "PRIMARY", + "key_length": "4", + "used_key_parts": ["o_orderkey"], + "ref": ["dbt3_s001.lineitem.l_orderkey"], + "r_loops": 7, + "rows": 1, + "r_rows": 1, + "r_table_time_ms": "REPLACED", + "r_other_time_ms": "REPLACED", + "filtered": 8.466666222, + "r_filtered": 14.28571429, + "attached_condition": "orders.o_totalprice between 200000 and 250000" + } + } + ] + } +} +set statement optimizer_switch='rowid_filter=on' for SELECT l_shipdate, l_receiptdate, o_totalprice +FROM orders, lineitem +WHERE o_orderkey=l_orderkey AND +l_shipdate BETWEEN '1996-10-01' AND '1996-10-10' AND +l_receiptdate BETWEEN '1996-10-05' AND '1996-10-10' AND +o_totalprice BETWEEN 200000 AND 250000; +l_shipdate l_receiptdate o_totalprice +1996-10-07 1996-10-08 202623.92 +set statement optimizer_switch='rowid_filter=off' for EXPLAIN SELECT l_shipdate, l_receiptdate, o_totalprice +FROM orders, lineitem +WHERE o_orderkey=l_orderkey AND +l_shipdate BETWEEN '1996-10-01' AND '1996-10-10' AND +l_receiptdate BETWEEN '1996-10-05' AND '1996-10-10' AND +o_totalprice BETWEEN 200000 AND 250000; +id select_type table type possible_keys key key_len ref rows Extra +1 SIMPLE lineitem range PRIMARY,i_l_shipdate,i_l_receiptdate,i_l_orderkey,i_l_orderkey_quantity i_l_receiptdate 4 NULL 17 Using index condition; Using where +1 SIMPLE orders eq_ref PRIMARY,i_o_totalprice PRIMARY 4 dbt3_s001.lineitem.l_orderkey 1 Using where +set statement optimizer_switch='rowid_filter=off' for EXPLAIN FORMAT=JSON SELECT l_shipdate, l_receiptdate, o_totalprice +FROM orders, lineitem +WHERE o_orderkey=l_orderkey AND +l_shipdate BETWEEN '1996-10-01' AND '1996-10-10' AND +l_receiptdate BETWEEN '1996-10-05' AND '1996-10-10' AND +o_totalprice BETWEEN 200000 AND 250000; +EXPLAIN +{ + "query_block": { + "select_id": 1, + "nested_loop": [ + { + "table": { + "table_name": "lineitem", + "access_type": "range", + "possible_keys": [ + "PRIMARY", + "i_l_shipdate", + "i_l_receiptdate", + "i_l_orderkey", + "i_l_orderkey_quantity" + ], + "key": "i_l_receiptdate", + "key_length": "4", + "used_key_parts": ["l_receiptDATE"], + "rows": 17, + "filtered": 0.532889247, + "index_condition": "lineitem.l_receiptDATE between '1996-10-05' and '1996-10-10'", + "attached_condition": "lineitem.l_shipDATE between '1996-10-01' and '1996-10-10'" + } + }, + { + "table": { + "table_name": "orders", + "access_type": "eq_ref", + "possible_keys": ["PRIMARY", "i_o_totalprice"], + "key": "PRIMARY", + "key_length": "4", + "used_key_parts": ["o_orderkey"], + "ref": ["dbt3_s001.lineitem.l_orderkey"], + "rows": 1, + "filtered": 8.466666222, + "attached_condition": "orders.o_totalprice between 200000 and 250000" + } + } + ] + } +} +set statement optimizer_switch='rowid_filter=off' for ANALYZE SELECT l_shipdate, l_receiptdate, o_totalprice +FROM orders, lineitem +WHERE o_orderkey=l_orderkey AND +l_shipdate BETWEEN '1996-10-01' AND '1996-10-10' AND +l_receiptdate BETWEEN '1996-10-05' AND '1996-10-10' AND +o_totalprice BETWEEN 200000 AND 250000; +id select_type table type possible_keys key key_len ref rows r_rows filtered r_filtered Extra +1 SIMPLE lineitem range PRIMARY,i_l_shipdate,i_l_receiptdate,i_l_orderkey,i_l_orderkey_quantity i_l_receiptdate 4 NULL 17 18.00 0.53 38.89 Using index condition; Using where +1 SIMPLE orders eq_ref PRIMARY,i_o_totalprice PRIMARY 4 dbt3_s001.lineitem.l_orderkey 1 1.00 8.47 14.29 Using where +set statement optimizer_switch='rowid_filter=off' for ANALYZE FORMAT=JSON SELECT l_shipdate, l_receiptdate, o_totalprice +FROM orders, lineitem +WHERE o_orderkey=l_orderkey AND +l_shipdate BETWEEN '1996-10-01' AND '1996-10-10' AND +l_receiptdate BETWEEN '1996-10-05' AND '1996-10-10' AND +o_totalprice BETWEEN 200000 AND 250000; +ANALYZE +{ + "query_optimization": { + "r_total_time_ms": "REPLACED" + }, + "query_block": { + "select_id": 1, + "r_loops": 1, + "r_total_time_ms": "REPLACED", + "nested_loop": [ + { + "table": { + "table_name": "lineitem", + "access_type": "range", + "possible_keys": [ + "PRIMARY", + "i_l_shipdate", + "i_l_receiptdate", + "i_l_orderkey", + "i_l_orderkey_quantity" + ], + "key": "i_l_receiptdate", + "key_length": "4", + "used_key_parts": ["l_receiptDATE"], + "r_loops": 1, + "rows": 17, + "r_rows": 18, + "r_table_time_ms": "REPLACED", + "r_other_time_ms": "REPLACED", + "filtered": 0.532889247, + "r_filtered": 38.88888889, + "index_condition": "lineitem.l_receiptDATE between '1996-10-05' and '1996-10-10'", + "attached_condition": "lineitem.l_shipDATE between '1996-10-01' and '1996-10-10'" + } + }, + { + "table": { + "table_name": "orders", + "access_type": "eq_ref", + "possible_keys": ["PRIMARY", "i_o_totalprice"], + "key": "PRIMARY", + "key_length": "4", + "used_key_parts": ["o_orderkey"], + "ref": ["dbt3_s001.lineitem.l_orderkey"], + "r_loops": 7, + "rows": 1, + "r_rows": 1, + "r_table_time_ms": "REPLACED", + "r_other_time_ms": "REPLACED", + "filtered": 8.466666222, + "r_filtered": 14.28571429, + "attached_condition": "orders.o_totalprice between 200000 and 250000" + } + } + ] + } +} +set statement optimizer_switch='rowid_filter=off' for SELECT l_shipdate, l_receiptdate, o_totalprice +FROM orders, lineitem +WHERE o_orderkey=l_orderkey AND +l_shipdate BETWEEN '1996-10-01' AND '1996-10-10' AND +l_receiptdate BETWEEN '1996-10-05' AND '1996-10-10' AND +o_totalprice BETWEEN 200000 AND 250000; +l_shipdate l_receiptdate o_totalprice +1996-10-07 1996-10-08 202623.92 +ALTER TABLE orders ADD COLUMN o_totaldiscount double; +UPDATE orders SET o_totaldiscount = o_totalprice*(o_custkey/1000); +CREATE INDEX i_o_totaldiscount on orders(o_totaldiscount); +ALTER TABLE orders ADD CONSTRAINT o_price CHECK(o_totalprice > o_totaldiscount); +# Filter on o_totalprice is not used because it participates in +# the same constraint as o_discount. +# Access is made on o_discount. +set statement optimizer_switch='rowid_filter=on' for EXPLAIN SELECT o_totaldiscount, o_totalprice, l_shipdate +FROM orders, lineitem +WHERE o_orderkey=l_orderkey AND +o_totaldiscount BETWEEN 18000 AND 20000 AND +o_totalprice BETWEEN 200000 AND 220000 AND +l_shipdate BETWEEN '1996-10-01' AND '1996-12-01'; +id select_type table type possible_keys key key_len ref rows Extra +1 SIMPLE orders range PRIMARY,i_o_totalprice,i_o_totaldiscount i_o_totaldiscount 9 NULL 61 Using index condition; Using where +1 SIMPLE lineitem ref|filter PRIMARY,i_l_shipdate,i_l_orderkey,i_l_orderkey_quantity PRIMARY|i_l_shipdate 4|4 dbt3_s001.orders.o_orderkey 4 (3%) Using where; Using rowid filter +set statement optimizer_switch='rowid_filter=on' for EXPLAIN FORMAT=JSON SELECT o_totaldiscount, o_totalprice, l_shipdate +FROM orders, lineitem +WHERE o_orderkey=l_orderkey AND +o_totaldiscount BETWEEN 18000 AND 20000 AND +o_totalprice BETWEEN 200000 AND 220000 AND +l_shipdate BETWEEN '1996-10-01' AND '1996-12-01'; +EXPLAIN +{ + "query_block": { + "select_id": 1, + "nested_loop": [ + { + "table": { + "table_name": "orders", + "access_type": "range", + "possible_keys": ["PRIMARY", "i_o_totalprice", "i_o_totaldiscount"], + "key": "i_o_totaldiscount", + "key_length": "9", + "used_key_parts": ["o_totaldiscount"], + "rows": 61, + "filtered": 5, + "index_condition": "orders.o_totaldiscount between 18000 and 20000", + "attached_condition": "orders.o_totalprice between 200000 and 220000" + } + }, + { + "table": { + "table_name": "lineitem", + "access_type": "ref", + "possible_keys": [ + "PRIMARY", + "i_l_shipdate", + "i_l_orderkey", + "i_l_orderkey_quantity" + ], + "key": "PRIMARY", + "key_length": "4", + "used_key_parts": ["l_orderkey"], + "ref": ["dbt3_s001.orders.o_orderkey"], + "rowid_filter": { + "range": { + "key": "i_l_shipdate", + "used_key_parts": ["l_shipDATE"] + }, + "rows": 174, + "selectivity_pct": 2.897585346 + }, + "rows": 4, + "filtered": 2.897585392, + "attached_condition": "lineitem.l_shipDATE between '1996-10-01' and '1996-12-01'" + } + } + ] + } +} +set statement optimizer_switch='rowid_filter=on' for ANALYZE SELECT o_totaldiscount, o_totalprice, l_shipdate +FROM orders, lineitem +WHERE o_orderkey=l_orderkey AND +o_totaldiscount BETWEEN 18000 AND 20000 AND +o_totalprice BETWEEN 200000 AND 220000 AND +l_shipdate BETWEEN '1996-10-01' AND '1996-12-01'; +id select_type table type possible_keys key key_len ref rows r_rows filtered r_filtered Extra +1 SIMPLE orders range PRIMARY,i_o_totalprice,i_o_totaldiscount i_o_totaldiscount 9 NULL 61 41.00 5.00 2.44 Using index condition; Using where +1 SIMPLE lineitem ref|filter PRIMARY,i_l_shipdate,i_l_orderkey,i_l_orderkey_quantity PRIMARY|i_l_shipdate 4|4 dbt3_s001.orders.o_orderkey 4 (3%) 4.00 (66%) 2.90 100.00 Using where; Using rowid filter +set statement optimizer_switch='rowid_filter=on' for ANALYZE FORMAT=JSON SELECT o_totaldiscount, o_totalprice, l_shipdate +FROM orders, lineitem +WHERE o_orderkey=l_orderkey AND +o_totaldiscount BETWEEN 18000 AND 20000 AND +o_totalprice BETWEEN 200000 AND 220000 AND +l_shipdate BETWEEN '1996-10-01' AND '1996-12-01'; +ANALYZE +{ + "query_optimization": { + "r_total_time_ms": "REPLACED" + }, + "query_block": { + "select_id": 1, + "r_loops": 1, + "r_total_time_ms": "REPLACED", + "nested_loop": [ + { + "table": { + "table_name": "orders", + "access_type": "range", + "possible_keys": ["PRIMARY", "i_o_totalprice", "i_o_totaldiscount"], + "key": "i_o_totaldiscount", + "key_length": "9", + "used_key_parts": ["o_totaldiscount"], + "r_loops": 1, + "rows": 61, + "r_rows": 41, + "r_table_time_ms": "REPLACED", + "r_other_time_ms": "REPLACED", + "filtered": 5, + "r_filtered": 2.43902439, + "index_condition": "orders.o_totaldiscount between 18000 and 20000", + "attached_condition": "orders.o_totalprice between 200000 and 220000" + } + }, + { + "table": { + "table_name": "lineitem", + "access_type": "ref", + "possible_keys": [ + "PRIMARY", + "i_l_shipdate", + "i_l_orderkey", + "i_l_orderkey_quantity" + ], + "key": "PRIMARY", + "key_length": "4", + "used_key_parts": ["l_orderkey"], + "ref": ["dbt3_s001.orders.o_orderkey"], + "rowid_filter": { + "range": { + "key": "i_l_shipdate", + "used_key_parts": ["l_shipDATE"] + }, + "rows": 174, + "selectivity_pct": 2.897585346, + "r_rows": 183, + "r_lookups": 6, + "r_selectivity_pct": 66.66666667, + "r_buffer_size": "REPLACED", + "r_filling_time_ms": "REPLACED" + }, + "r_loops": 1, + "rows": 4, + "r_rows": 4, + "r_table_time_ms": "REPLACED", + "r_other_time_ms": "REPLACED", + "filtered": 2.897585392, + "r_filtered": 100, + "attached_condition": "lineitem.l_shipDATE between '1996-10-01' and '1996-12-01'" + } + } + ] + } +} +set statement optimizer_switch='rowid_filter=on' for SELECT o_totaldiscount, o_totalprice, l_shipdate +FROM orders, lineitem +WHERE o_orderkey=l_orderkey AND +o_totaldiscount BETWEEN 18000 AND 20000 AND +o_totalprice BETWEEN 200000 AND 220000 AND +l_shipdate BETWEEN '1996-10-01' AND '1996-12-01'; +o_totaldiscount o_totalprice l_shipdate +18016.04288 219707.84 1996-10-02 +18016.04288 219707.84 1996-10-17 +18016.04288 219707.84 1996-11-04 +18016.04288 219707.84 1996-11-14 +set statement optimizer_switch='rowid_filter=off' for EXPLAIN SELECT o_totaldiscount, o_totalprice, l_shipdate +FROM orders, lineitem +WHERE o_orderkey=l_orderkey AND +o_totaldiscount BETWEEN 18000 AND 20000 AND +o_totalprice BETWEEN 200000 AND 220000 AND +l_shipdate BETWEEN '1996-10-01' AND '1996-12-01'; +id select_type table type possible_keys key key_len ref rows Extra +1 SIMPLE orders range PRIMARY,i_o_totalprice,i_o_totaldiscount i_o_totaldiscount 9 NULL 61 Using index condition; Using where +1 SIMPLE lineitem ref PRIMARY,i_l_shipdate,i_l_orderkey,i_l_orderkey_quantity PRIMARY 4 dbt3_s001.orders.o_orderkey 4 Using where +set statement optimizer_switch='rowid_filter=off' for EXPLAIN FORMAT=JSON SELECT o_totaldiscount, o_totalprice, l_shipdate +FROM orders, lineitem +WHERE o_orderkey=l_orderkey AND +o_totaldiscount BETWEEN 18000 AND 20000 AND +o_totalprice BETWEEN 200000 AND 220000 AND +l_shipdate BETWEEN '1996-10-01' AND '1996-12-01'; +EXPLAIN +{ + "query_block": { + "select_id": 1, + "nested_loop": [ + { + "table": { + "table_name": "orders", + "access_type": "range", + "possible_keys": ["PRIMARY", "i_o_totalprice", "i_o_totaldiscount"], + "key": "i_o_totaldiscount", + "key_length": "9", + "used_key_parts": ["o_totaldiscount"], + "rows": 61, + "filtered": 5, + "index_condition": "orders.o_totaldiscount between 18000 and 20000", + "attached_condition": "orders.o_totalprice between 200000 and 220000" + } + }, + { + "table": { + "table_name": "lineitem", + "access_type": "ref", + "possible_keys": [ + "PRIMARY", + "i_l_shipdate", + "i_l_orderkey", + "i_l_orderkey_quantity" + ], + "key": "PRIMARY", + "key_length": "4", + "used_key_parts": ["l_orderkey"], + "ref": ["dbt3_s001.orders.o_orderkey"], + "rows": 4, + "filtered": 2.897585392, + "attached_condition": "lineitem.l_shipDATE between '1996-10-01' and '1996-12-01'" + } + } + ] + } +} +set statement optimizer_switch='rowid_filter=off' for ANALYZE SELECT o_totaldiscount, o_totalprice, l_shipdate +FROM orders, lineitem +WHERE o_orderkey=l_orderkey AND +o_totaldiscount BETWEEN 18000 AND 20000 AND +o_totalprice BETWEEN 200000 AND 220000 AND +l_shipdate BETWEEN '1996-10-01' AND '1996-12-01'; +id select_type table type possible_keys key key_len ref rows r_rows filtered r_filtered Extra +1 SIMPLE orders range PRIMARY,i_o_totalprice,i_o_totaldiscount i_o_totaldiscount 9 NULL 61 41.00 5.00 2.44 Using index condition; Using where +1 SIMPLE lineitem ref PRIMARY,i_l_shipdate,i_l_orderkey,i_l_orderkey_quantity PRIMARY 4 dbt3_s001.orders.o_orderkey 4 6.00 2.90 66.67 Using where +set statement optimizer_switch='rowid_filter=off' for ANALYZE FORMAT=JSON SELECT o_totaldiscount, o_totalprice, l_shipdate +FROM orders, lineitem +WHERE o_orderkey=l_orderkey AND +o_totaldiscount BETWEEN 18000 AND 20000 AND +o_totalprice BETWEEN 200000 AND 220000 AND +l_shipdate BETWEEN '1996-10-01' AND '1996-12-01'; +ANALYZE +{ + "query_optimization": { + "r_total_time_ms": "REPLACED" + }, + "query_block": { + "select_id": 1, + "r_loops": 1, + "r_total_time_ms": "REPLACED", + "nested_loop": [ + { + "table": { + "table_name": "orders", + "access_type": "range", + "possible_keys": ["PRIMARY", "i_o_totalprice", "i_o_totaldiscount"], + "key": "i_o_totaldiscount", + "key_length": "9", + "used_key_parts": ["o_totaldiscount"], + "r_loops": 1, + "rows": 61, + "r_rows": 41, + "r_table_time_ms": "REPLACED", + "r_other_time_ms": "REPLACED", + "filtered": 5, + "r_filtered": 2.43902439, + "index_condition": "orders.o_totaldiscount between 18000 and 20000", + "attached_condition": "orders.o_totalprice between 200000 and 220000" + } + }, + { + "table": { + "table_name": "lineitem", + "access_type": "ref", + "possible_keys": [ + "PRIMARY", + "i_l_shipdate", + "i_l_orderkey", + "i_l_orderkey_quantity" + ], + "key": "PRIMARY", + "key_length": "4", + "used_key_parts": ["l_orderkey"], + "ref": ["dbt3_s001.orders.o_orderkey"], + "r_loops": 1, + "rows": 4, + "r_rows": 6, + "r_table_time_ms": "REPLACED", + "r_other_time_ms": "REPLACED", + "filtered": 2.897585392, + "r_filtered": 66.66666667, + "attached_condition": "lineitem.l_shipDATE between '1996-10-01' and '1996-12-01'" + } + } + ] + } +} +set statement optimizer_switch='rowid_filter=off' for SELECT o_totaldiscount, o_totalprice, l_shipdate +FROM orders, lineitem +WHERE o_orderkey=l_orderkey AND +o_totaldiscount BETWEEN 18000 AND 20000 AND +o_totalprice BETWEEN 200000 AND 220000 AND +l_shipdate BETWEEN '1996-10-01' AND '1996-12-01'; +o_totaldiscount o_totalprice l_shipdate +18016.04288 219707.84 1996-10-02 +18016.04288 219707.84 1996-10-17 +18016.04288 219707.84 1996-11-04 +18016.04288 219707.84 1996-11-14 +CREATE VIEW v1 AS +SELECT * FROM orders +WHERE o_orderdate BETWEEN '1992-12-01' AND '1997-01-01'; +set statement optimizer_switch='rowid_filter=on' for EXPLAIN SELECT o_totaldiscount, o_totalprice, l_shipdate +FROM v1, lineitem +WHERE o_orderkey=l_orderkey AND +o_totaldiscount BETWEEN 18000 AND 20000 AND +o_totalprice BETWEEN 200000 AND 220000 AND +l_shipdate BETWEEN '1996-10-01' AND '1996-12-01'; +id select_type table type possible_keys key key_len ref rows Extra +1 SIMPLE orders range PRIMARY,i_o_orderdate,i_o_totalprice,i_o_totaldiscount i_o_totaldiscount 9 NULL 61 Using index condition; Using where +1 SIMPLE lineitem ref PRIMARY,i_l_shipdate,i_l_orderkey,i_l_orderkey_quantity PRIMARY 4 dbt3_s001.orders.o_orderkey 4 Using where +set statement optimizer_switch='rowid_filter=on' for EXPLAIN FORMAT=JSON SELECT o_totaldiscount, o_totalprice, l_shipdate +FROM v1, lineitem +WHERE o_orderkey=l_orderkey AND +o_totaldiscount BETWEEN 18000 AND 20000 AND +o_totalprice BETWEEN 200000 AND 220000 AND +l_shipdate BETWEEN '1996-10-01' AND '1996-12-01'; +EXPLAIN +{ + "query_block": { + "select_id": 1, + "nested_loop": [ + { + "table": { + "table_name": "orders", + "access_type": "range", + "possible_keys": [ + "PRIMARY", + "i_o_orderdate", + "i_o_totalprice", + "i_o_totaldiscount" + ], + "key": "i_o_totaldiscount", + "key_length": "9", + "used_key_parts": ["o_totaldiscount"], + "rows": 61, + "filtered": "REPLACED", + "index_condition": "orders.o_totaldiscount between 18000 and 20000", + "attached_condition": "orders.o_totalprice between 200000 and 220000 and orders.o_orderDATE between '1992-12-01' and '1997-01-01'" + } + }, + { + "table": { + "table_name": "lineitem", + "access_type": "ref", + "possible_keys": [ + "PRIMARY", + "i_l_shipdate", + "i_l_orderkey", + "i_l_orderkey_quantity" + ], + "key": "PRIMARY", + "key_length": "4", + "used_key_parts": ["l_orderkey"], + "ref": ["dbt3_s001.orders.o_orderkey"], + "rows": 4, + "filtered": "REPLACED", + "attached_condition": "lineitem.l_shipDATE between '1996-10-01' and '1996-12-01'" + } + } + ] + } +} +set statement optimizer_switch='rowid_filter=on' for ANALYZE SELECT o_totaldiscount, o_totalprice, l_shipdate +FROM v1, lineitem +WHERE o_orderkey=l_orderkey AND +o_totaldiscount BETWEEN 18000 AND 20000 AND +o_totalprice BETWEEN 200000 AND 220000 AND +l_shipdate BETWEEN '1996-10-01' AND '1996-12-01'; +id select_type table type possible_keys key key_len ref rows r_rows filtered r_filtered Extra +1 SIMPLE orders range PRIMARY,i_o_orderdate,i_o_totalprice,i_o_totaldiscount i_o_totaldiscount 9 NULL 61 41.00 # 2.44 Using index condition; Using where +1 SIMPLE lineitem ref PRIMARY,i_l_shipdate,i_l_orderkey,i_l_orderkey_quantity PRIMARY 4 dbt3_s001.orders.o_orderkey 4 6.00 # 66.67 Using where +set statement optimizer_switch='rowid_filter=on' for ANALYZE FORMAT=JSON SELECT o_totaldiscount, o_totalprice, l_shipdate +FROM v1, lineitem +WHERE o_orderkey=l_orderkey AND +o_totaldiscount BETWEEN 18000 AND 20000 AND +o_totalprice BETWEEN 200000 AND 220000 AND +l_shipdate BETWEEN '1996-10-01' AND '1996-12-01'; +ANALYZE +{ + "query_optimization": { + "r_total_time_ms": "REPLACED" + }, + "query_block": { + "select_id": 1, + "r_loops": 1, + "r_total_time_ms": "REPLACED", + "nested_loop": [ + { + "table": { + "table_name": "orders", + "access_type": "range", + "possible_keys": [ + "PRIMARY", + "i_o_orderdate", + "i_o_totalprice", + "i_o_totaldiscount" + ], + "key": "i_o_totaldiscount", + "key_length": "9", + "used_key_parts": ["o_totaldiscount"], + "r_loops": 1, + "rows": 61, + "r_rows": 41, + "r_table_time_ms": "REPLACED", + "r_other_time_ms": "REPLACED", + "filtered": "REPLACED", + "r_filtered": 2.43902439, + "index_condition": "orders.o_totaldiscount between 18000 and 20000", + "attached_condition": "orders.o_totalprice between 200000 and 220000 and orders.o_orderDATE between '1992-12-01' and '1997-01-01'" + } + }, + { + "table": { + "table_name": "lineitem", + "access_type": "ref", + "possible_keys": [ + "PRIMARY", + "i_l_shipdate", + "i_l_orderkey", + "i_l_orderkey_quantity" + ], + "key": "PRIMARY", + "key_length": "4", + "used_key_parts": ["l_orderkey"], + "ref": ["dbt3_s001.orders.o_orderkey"], + "r_loops": 1, + "rows": 4, + "r_rows": 6, + "r_table_time_ms": "REPLACED", + "r_other_time_ms": "REPLACED", + "filtered": "REPLACED", + "r_filtered": 66.66666667, + "attached_condition": "lineitem.l_shipDATE between '1996-10-01' and '1996-12-01'" + } + } + ] + } +} +set statement optimizer_switch='rowid_filter=on' for SELECT o_totaldiscount, o_totalprice, l_shipdate +FROM v1, lineitem +WHERE o_orderkey=l_orderkey AND +o_totaldiscount BETWEEN 18000 AND 20000 AND +o_totalprice BETWEEN 200000 AND 220000 AND +l_shipdate BETWEEN '1996-10-01' AND '1996-12-01'; +o_totaldiscount o_totalprice l_shipdate +18016.04288 219707.84 1996-10-02 +18016.04288 219707.84 1996-10-17 +18016.04288 219707.84 1996-11-04 +18016.04288 219707.84 1996-11-14 +set statement optimizer_switch='rowid_filter=off' for EXPLAIN SELECT o_totaldiscount, o_totalprice, l_shipdate +FROM v1, lineitem +WHERE o_orderkey=l_orderkey AND +o_totaldiscount BETWEEN 18000 AND 20000 AND +o_totalprice BETWEEN 200000 AND 220000 AND +l_shipdate BETWEEN '1996-10-01' AND '1996-12-01'; +id select_type table type possible_keys key key_len ref rows Extra +1 SIMPLE orders range PRIMARY,i_o_orderdate,i_o_totalprice,i_o_totaldiscount i_o_totaldiscount 9 NULL 61 Using index condition; Using where +1 SIMPLE lineitem ref PRIMARY,i_l_shipdate,i_l_orderkey,i_l_orderkey_quantity PRIMARY 4 dbt3_s001.orders.o_orderkey 4 Using where +set statement optimizer_switch='rowid_filter=off' for EXPLAIN FORMAT=JSON SELECT o_totaldiscount, o_totalprice, l_shipdate +FROM v1, lineitem +WHERE o_orderkey=l_orderkey AND +o_totaldiscount BETWEEN 18000 AND 20000 AND +o_totalprice BETWEEN 200000 AND 220000 AND +l_shipdate BETWEEN '1996-10-01' AND '1996-12-01'; +EXPLAIN +{ + "query_block": { + "select_id": 1, + "nested_loop": [ + { + "table": { + "table_name": "orders", + "access_type": "range", + "possible_keys": [ + "PRIMARY", + "i_o_orderdate", + "i_o_totalprice", + "i_o_totaldiscount" + ], + "key": "i_o_totaldiscount", + "key_length": "9", + "used_key_parts": ["o_totaldiscount"], + "rows": 61, + "filtered": "REPLACED", + "index_condition": "orders.o_totaldiscount between 18000 and 20000", + "attached_condition": "orders.o_totalprice between 200000 and 220000 and orders.o_orderDATE between '1992-12-01' and '1997-01-01'" + } + }, + { + "table": { + "table_name": "lineitem", + "access_type": "ref", + "possible_keys": [ + "PRIMARY", + "i_l_shipdate", + "i_l_orderkey", + "i_l_orderkey_quantity" + ], + "key": "PRIMARY", + "key_length": "4", + "used_key_parts": ["l_orderkey"], + "ref": ["dbt3_s001.orders.o_orderkey"], + "rows": 4, + "filtered": "REPLACED", + "attached_condition": "lineitem.l_shipDATE between '1996-10-01' and '1996-12-01'" + } + } + ] + } +} +set statement optimizer_switch='rowid_filter=off' for ANALYZE SELECT o_totaldiscount, o_totalprice, l_shipdate +FROM v1, lineitem +WHERE o_orderkey=l_orderkey AND +o_totaldiscount BETWEEN 18000 AND 20000 AND +o_totalprice BETWEEN 200000 AND 220000 AND +l_shipdate BETWEEN '1996-10-01' AND '1996-12-01'; +id select_type table type possible_keys key key_len ref rows r_rows filtered r_filtered Extra +1 SIMPLE orders range PRIMARY,i_o_orderdate,i_o_totalprice,i_o_totaldiscount i_o_totaldiscount 9 NULL 61 41.00 # 2.44 Using index condition; Using where +1 SIMPLE lineitem ref PRIMARY,i_l_shipdate,i_l_orderkey,i_l_orderkey_quantity PRIMARY 4 dbt3_s001.orders.o_orderkey 4 6.00 # 66.67 Using where +set statement optimizer_switch='rowid_filter=off' for ANALYZE FORMAT=JSON SELECT o_totaldiscount, o_totalprice, l_shipdate +FROM v1, lineitem +WHERE o_orderkey=l_orderkey AND +o_totaldiscount BETWEEN 18000 AND 20000 AND +o_totalprice BETWEEN 200000 AND 220000 AND +l_shipdate BETWEEN '1996-10-01' AND '1996-12-01'; +ANALYZE +{ + "query_optimization": { + "r_total_time_ms": "REPLACED" + }, + "query_block": { + "select_id": 1, + "r_loops": 1, + "r_total_time_ms": "REPLACED", + "nested_loop": [ + { + "table": { + "table_name": "orders", + "access_type": "range", + "possible_keys": [ + "PRIMARY", + "i_o_orderdate", + "i_o_totalprice", + "i_o_totaldiscount" + ], + "key": "i_o_totaldiscount", + "key_length": "9", + "used_key_parts": ["o_totaldiscount"], + "r_loops": 1, + "rows": 61, + "r_rows": 41, + "r_table_time_ms": "REPLACED", + "r_other_time_ms": "REPLACED", + "filtered": "REPLACED", + "r_filtered": 2.43902439, + "index_condition": "orders.o_totaldiscount between 18000 and 20000", + "attached_condition": "orders.o_totalprice between 200000 and 220000 and orders.o_orderDATE between '1992-12-01' and '1997-01-01'" + } + }, + { + "table": { + "table_name": "lineitem", + "access_type": "ref", + "possible_keys": [ + "PRIMARY", + "i_l_shipdate", + "i_l_orderkey", + "i_l_orderkey_quantity" + ], + "key": "PRIMARY", + "key_length": "4", + "used_key_parts": ["l_orderkey"], + "ref": ["dbt3_s001.orders.o_orderkey"], + "r_loops": 1, + "rows": 4, + "r_rows": 6, + "r_table_time_ms": "REPLACED", + "r_other_time_ms": "REPLACED", + "filtered": "REPLACED", + "r_filtered": 66.66666667, + "attached_condition": "lineitem.l_shipDATE between '1996-10-01' and '1996-12-01'" + } + } + ] + } +} +set statement optimizer_switch='rowid_filter=off' for SELECT o_totaldiscount, o_totalprice, l_shipdate +FROM v1, lineitem +WHERE o_orderkey=l_orderkey AND +o_totaldiscount BETWEEN 18000 AND 20000 AND +o_totalprice BETWEEN 200000 AND 220000 AND +l_shipdate BETWEEN '1996-10-01' AND '1996-12-01'; +o_totaldiscount o_totalprice l_shipdate +18016.04288 219707.84 1996-10-02 +18016.04288 219707.84 1996-10-17 +18016.04288 219707.84 1996-11-04 +18016.04288 219707.84 1996-11-14 +ALTER TABLE lineitem DROP CONSTRAINT l_date; +ALTER TABLE orders DROP CONSTRAINT o_price; +ALTER TABLE orders DROP COLUMN o_totaldiscount; +DROP VIEW v1; +DROP DATABASE dbt3_s001; +use test; diff --git a/mysql-test/main/rowid_filter_aria.test b/mysql-test/main/rowid_filter_aria.test new file mode 100644 index 00000000000..869d398f791 --- /dev/null +++ b/mysql-test/main/rowid_filter_aria.test @@ -0,0 +1,9 @@ +# +# Test rowid filters with Aria +# + +SET SESSION DEFAULT_STORAGE_ENGINE='Aria'; + +#set global aria.optimizer_rowid_compare_cost=0.00001; +#set global aria.optimizer_rowid_copy_cost=0.00001; +--source rowid_filter.test diff --git a/mysql-test/main/rowid_filter_innodb.result b/mysql-test/main/rowid_filter_innodb.result index 56a7061ddf7..db2e4052a21 100644 --- a/mysql-test/main/rowid_filter_innodb.result +++ b/mysql-test/main/rowid_filter_innodb.result @@ -2141,698 +2141,6 @@ ALTER TABLE orders DROP COLUMN o_totaldiscount; DROP VIEW v1; DROP DATABASE dbt3_s001; use test; -# -# MDEV-18816: potential range filter for one join table with -# impossible WHERE for another -# -create table t1 ( -pk int not null primary key, c2 varchar(10) , i1 int,key (c2) -) engine=myisam; -insert into t1 values (1,'a',-5),(2,'a',null); -create table t2 ( -pk int, i1 int, c1 varchar(30) , key c1 (c1(30)), key i1 (i1) -) engine=myisam; -insert into t2 values -(1,-5,'a'),(2,null,'a'),(3,null,'a'),(4,null,'a'),(5,5,'a'),(6,null,'a'), -(7,4,'a'),(8,55,'a'),(9,null,'a'),(10,null,'a'),(11,null,'a'),(12,-5,'a'), -(13,-5,'a'),(14,null,'a'),(15,null,'a'),(16,-5,'a'),(17,-5,'a'); -select 1 -from t1 -left join -t2 join t1 as t1_a on t2.i1 = t1_a.pk -on t1.c2 = t2.c1 -where t1_a.pk is null and t1_a.i1 != 3; -1 -explain extended select 1 -from t1 -left join -t2 join t1 as t1_a on t2.i1 = t1_a.pk -on t1.c2 = t2.c1 -where t1_a.pk is null and t1_a.i1 != 3; -id select_type table type possible_keys key key_len ref rows filtered Extra -1 SIMPLE NULL NULL NULL NULL NULL NULL NULL NULL Impossible WHERE noticed after reading const tables -Warnings: -Note 1003 select 1 AS `1` from `test`.`t1` join `test`.`t2` join `test`.`t1` `t1_a` where 0 -drop table t1,t2; -# -# MDEV-18640: TABLE::prune_range_rowid_filters: Conditional jump or -# move depends on uninitialized value -# -CREATE TABLE t1 ( -pk INT, i INT, PRIMARY KEY (pk), KEY (pk,i) -) ENGINE=MyISAM; -INSERT INTO t1 VALUES (1,10), (7,70), (2,20); -SELECT * FROM t1 WHERE pk < 5; -pk i -1 10 -2 20 -DROP TABLE t1; -# -# MDEV-18956: Possible rowid filter for subquery for which -# in_to_exists strategy has been chosen -# -CREATE TABLE t1 (pk int) engine=myisam ; -INSERT INTO t1 VALUES (1),(2); -CREATE TABLE t2 ( -pk int auto_increment PRIMARY KEY, -i1 int, i2 int, c2 varchar(1), -KEY (i1), KEY (i2) -) engine=myisam; -INSERT INTO t2 VALUES -(1,8,6,'t'),(2,5,7,'i'),(3,4,4,'h'),(4,207,38,'d'),(5,183,206,'b'), -(6,7,null,'o'),(7,1,2,'j'),(8,17,36,'s'),(9,4,5,'q'),(10,0,6,'l'), -(11,1,9,'j'),(12,5,6,'y'),(13,null,0,'i'),(14,7,7,'x'),(15,5,2,'u'); -SELECT * FROM t1 HAVING (7, 9) IN (SELECT t2.i1, t2.i2 FROM t2 WHERE t2.i1 = 3); -pk -EXPLAIN EXTENDED -SELECT * FROM t1 HAVING (7, 9) IN (SELECT t2.i1, t2.i2 FROM t2 WHERE t2.i1 = 3); -id select_type table type possible_keys key key_len ref rows filtered Extra -1 PRIMARY NULL NULL NULL NULL NULL NULL NULL NULL Impossible HAVING -2 SUBQUERY NULL NULL NULL NULL NULL NULL NULL NULL no matching row in const table -Warnings: -Note 1003 /* select#1 */ select `test`.`t1`.`pk` AS `pk` from `test`.`t1` having 0 -DROP TABLE t1,t2; -# -# MDEV-19255: rowid range filter built for range condition -# that uses in expensive subquery -# -CREATE TABLE t1 ( -pk1 INT PRIMARY KEY, a1 INT, b1 VARCHAR(1), KEY(a1), KEY(b1) -) ENGINE=MyISAM; -INSERT INTO t1 VALUES -(10,0,'z'),(11,3,'j'),(12,8,'f'),(13,8,'p'),(14,6,'w'),(15,0,'c'),(16,1,'j'), -(17,1,'f'),(18,5,'v'),(19,3,'f'),(20,2,'q'),(21,8,'y'),(22,0,'a'),(23,9,'w'), -(24,3,'e'),(25,1,'b'),(26,9,'r'),(27,2,'k'),(28,5,'c'),(29,3,'k'),(30,9,'b'), -(31,8,'j'),(32,1,'t'),(33,8,'n'),(34,3,'z'),(35,0,'u'),(36,3,'a'),(37,3,'g'), -(38,1,'f'),(39,6,'p'),(40,6,'m'),(41,6,'t'),(42,7,'i'),(43,4,'h'),(44,3,'d'), -(45,2,'b'),(46,1,'o'),(47,2,'j'),(48,6,'s'),(49,5,'q'),(50,6,'l'),(51,9,'j'), -(52,6,'y'),(53,0,'i'),(54,7,'x'),(55,2,'u'),(56,6,'t'),(57,4,'b'),(58,5,'m'), -(59,4,'x'),(60,8,'x'),(61,6,'v'),(62,8,'m'),(63,4,'j'),(64,8,'z'),(65,2,'a'), -(66,9,'i'),(67,4,'g'),(68,8,'h'),(69,1,'p'),(70,8,'a'),(71,0,'x'),(72,2,'s'), -(73,6,'k'),(74,0,'m'),(75,6,'e'),(76,9,'y'),(77,7,'d'),(78,7,'w'),(79,6,'y'), -(80,9,'s'),(81,9,'x'),(82,6,'l'),(83,9,'f'),(84,8,'x'),(85,1,'p'),(86,7,'y'), -(87,6,'p'),(88,1,'g'),(89,3,'c'),(90,5,'h'),(91,3,'p'),(92,2,'b'),(93,1,NULL), -(94,3,NULL),(95,2,'y'),(96,7,'s'),(97,7,'x'),(98,6,'i'),(99,9,'t'),(100,5,'j'), -(101,0,'u'),(102,7,'r'),(103,2,'x'),(104,8,'e'),(105,8,'i'),(106,5,'q'), -(107,8,'z'),(108,3,'k'),(109,65,NULL); -CREATE TABLE t2 (pk2 INT PRIMARY KEY, a2 INT, b2 VARCHAR(1)) ENGINE=MyISAM; -INSERT INTO t2 VALUES (1,1,'i'); -INSERT INTO t2 SELECT * FROM t1; -INSERT INTO t1 SELECT pk1+200, a1, b1 FROM t1; -INSERT INTO t1 SELECT pk1+400, a1, b1 FROM t1; -ANALYZE TABLE t1,t2 PERSISTENT FOR ALL; -Table Op Msg_type Msg_text -test.t1 analyze status Engine-independent statistics collected -test.t1 analyze status OK -test.t2 analyze status Engine-independent statistics collected -test.t2 analyze status OK -SELECT * FROM t1 INNER JOIN t2 ON ( pk1+1 = pk2+2 AND a1 = a2 ) -WHERE b1 <= ( SELECT MAX(b2) FROM t2 WHERE pk2 <= 1 ); -pk1 a1 b1 pk2 a2 b2 -17 1 f 16 1 j -37 3 g 36 3 a -105 8 i 104 8 e -EXPLAIN EXTENDED SELECT * FROM t1 INNER JOIN t2 ON ( pk1+1 = pk2+2 AND a1 = a2 ) -WHERE b1 <= ( SELECT MAX(b2) FROM t2 WHERE pk2 <= 1 ); -id select_type table type possible_keys key key_len ref rows filtered Extra -1 PRIMARY t2 ALL NULL NULL NULL NULL 101 100.00 -1 PRIMARY t1 ALL a1,b1 NULL NULL NULL 400 2.61 Using where; Using join buffer (flat, BNL join) -2 SUBQUERY t2 range PRIMARY PRIMARY 4 NULL 1 100.00 Using index condition -Warnings: -Note 1003 /* select#1 */ select `test`.`t1`.`pk1` AS `pk1`,`test`.`t1`.`a1` AS `a1`,`test`.`t1`.`b1` AS `b1`,`test`.`t2`.`pk2` AS `pk2`,`test`.`t2`.`a2` AS `a2`,`test`.`t2`.`b2` AS `b2` from `test`.`t1` join `test`.`t2` where `test`.`t1`.`a1` = `test`.`t2`.`a2` and `test`.`t1`.`b1` <= (/* select#2 */ select max(`test`.`t2`.`b2`) from `test`.`t2` where `test`.`t2`.`pk2` <= 1) and `test`.`t1`.`pk1` + 1 = `test`.`t2`.`pk2` + 2 -set @@optimizer_where_cost=0.0356*4; -EXPLAIN EXTENDED SELECT * FROM t1 INNER JOIN t2 ON ( pk1+1 = pk2+2 AND a1 = a2 ) -WHERE b1 <= ( SELECT MAX(b2) FROM t2 WHERE pk2 <= 1 ); -id select_type table type possible_keys key key_len ref rows filtered Extra -1 PRIMARY t2 ALL NULL NULL NULL NULL 101 100.00 Using where -1 PRIMARY t1 ref|filter a1,b1 a1|b1 5|4 test.t2.a2 36 (29%) 28.75 Using where; Using rowid filter -2 SUBQUERY t2 range PRIMARY PRIMARY 4 NULL 1 100.00 Using index condition -Warnings: -Note 1003 /* select#1 */ select `test`.`t1`.`pk1` AS `pk1`,`test`.`t1`.`a1` AS `a1`,`test`.`t1`.`b1` AS `b1`,`test`.`t2`.`pk2` AS `pk2`,`test`.`t2`.`a2` AS `a2`,`test`.`t2`.`b2` AS `b2` from `test`.`t1` join `test`.`t2` where `test`.`t1`.`a1` = `test`.`t2`.`a2` and `test`.`t1`.`b1` <= (/* select#2 */ select max(`test`.`t2`.`b2`) from `test`.`t2` where `test`.`t2`.`pk2` <= 1) and `test`.`t1`.`pk1` + 1 = `test`.`t2`.`pk2` + 2 -EXPLAIN FORMAT=JSON SELECT * FROM t1 INNER JOIN t2 ON ( pk1+1 = pk2+2 AND a1 = a2 ) -WHERE b1 <= ( SELECT MAX(b2) FROM t2 WHERE pk2 <= 1 ); -EXPLAIN -{ - "query_block": { - "select_id": 1, - "nested_loop": [ - { - "table": { - "table_name": "t2", - "access_type": "ALL", - "rows": 101, - "filtered": 100, - "attached_condition": "t2.a2 is not null" - } - }, - { - "table": { - "table_name": "t1", - "access_type": "ref", - "possible_keys": ["a1", "b1"], - "key": "a1", - "key_length": "5", - "used_key_parts": ["a1"], - "ref": ["test.t2.a2"], - "rowid_filter": { - "range": { - "key": "b1", - "used_key_parts": ["b1"] - }, - "rows": 115, - "selectivity_pct": 28.75 - }, - "rows": 36, - "filtered": 28.75, - "attached_condition": "t1.b1 <= (subquery#2) and t1.pk1 + 1 = t2.pk2 + 2" - } - } - ], - "subqueries": [ - { - "query_block": { - "select_id": 2, - "nested_loop": [ - { - "table": { - "table_name": "t2", - "access_type": "range", - "possible_keys": ["PRIMARY"], - "key": "PRIMARY", - "key_length": "4", - "used_key_parts": ["pk2"], - "rows": 1, - "filtered": 100, - "index_condition": "t2.pk2 <= 1" - } - } - ] - } - } - ] - } -} -set @@optimizer_where_cost=default; -DROP TABLE t1,t2; -# -# MDEV-21794: Optimizer flag rowid_filter leads to long query -# -create table t10(a int); -insert into t10 values (0),(1),(2),(3),(4),(5),(6),(7),(8),(9); -create table t11(a int); -insert into t11 select A.a + B.a* 10 + C.a * 100 from t10 A, t10 B, t10 C; -CREATE TABLE t1 ( -el_id int(10) unsigned NOT NULL , -el_index blob NOT NULL, -el_index_60 varbinary(60) NOT NULL, -filler blob, -PRIMARY KEY (el_id), -KEY el_index (el_index(60)), -KEY el_index_60 (el_index_60,el_id) -); -insert into t1 -select -A.a+1000*B.a, -A.a+1000*B.a + 10000, -A.a+1000*B.a + 10000, -'filler-data-filler-data' -from -t11 A, t10 B; -analyze table t1 persistent for all; -Table Op Msg_type Msg_text -test.t1 analyze status Engine-independent statistics collected -test.t1 analyze Warning Engine-independent statistics are not collected for column 'el_index' -test.t1 analyze Warning Engine-independent statistics are not collected for column 'filler' -test.t1 analyze status OK -# This must not use rowid_filter with key=el_index|el_index_60: -explain -select * from t1 -where el_index like '10%' and (el_index_60 like '10%' or el_index_60 like '20%'); -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 range el_index,el_index_60 el_index 62 NULL 1000 Using where -drop table t10, t11, t1; -# -# MDEV-22160: SIGSEGV in st_join_table::save_explain_data on SELECT -# -set @save_optimizer_switch= @@optimizer_switch; -SET @@optimizer_switch="index_merge_sort_union=OFF"; -CREATE TABLE t1 (a INT, b INT, INDEX(a), INDEX(b)); -INSERT INTO t1 VALUES (0,0),(0,0),(1,0),(-1,1), (-2,1), (-2,3), (-3,4), (-2,4),(3,3),(3,4),(3,5),(8,8),(8,9),(1,0),(2,0),(0,0),(0,0); -explain -SELECT * FROM t1 WHERE a > 0 AND b=0; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ref|filter a,b b|a 5|5 const 7 (47%) Using where; Using rowid filter -SELECT * FROM t1 WHERE a > 0 AND b=0; -a b -1 0 -1 0 -2 0 -drop table t1; -SET @@optimizer_switch=@save_optimizer_switch; -# -# MDEV-28846: Poor performance when rowid filter contains no elements -# -create table t1 ( -pk int primary key auto_increment, -nm varchar(32), -fl1 tinyint default 0, -fl2 tinyint default 0, -index idx1(nm, fl1), -index idx2(fl2) -) engine=myisam; -create table name ( -pk int primary key auto_increment, -nm bigint -) engine=myisam; -create table flag2 ( -pk int primary key auto_increment, -fl2 tinyint -) engine=myisam; -insert into name(nm) select seq from seq_1_to_1000 order by rand(17); -insert into flag2(fl2) select seq mod 2 from seq_1_to_1000 order by rand(19); -insert into t1(nm,fl2) -select nm, fl2 from name, flag2 where name.pk = flag2.pk; -analyze table t1 persistent for all; -Table Op Msg_type Msg_text -test.t1 analyze status Engine-independent statistics collected -test.t1 analyze status Table is already up to date -select '500%' as a; -a -500% -set optimizer_switch='rowid_filter=on'; -explain -select * from t1 where nm like '500%' AND fl2 = 0; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 range idx1,idx2 idx1 35 NULL 1 Using index condition; Using where -analyze format=json -select * from t1 where nm like '500%' AND fl2 = 0; -ANALYZE -{ - "query_optimization": { - "r_total_time_ms": "REPLACED" - }, - "query_block": { - "select_id": 1, - "r_loops": 1, - "r_total_time_ms": "REPLACED", - "nested_loop": [ - { - "table": { - "table_name": "t1", - "access_type": "range", - "possible_keys": ["idx1", "idx2"], - "key": "idx1", - "key_length": "35", - "used_key_parts": ["nm"], - "r_loops": 1, - "rows": 1, - "r_rows": 1, - "r_table_time_ms": "REPLACED", - "r_other_time_ms": "REPLACED", - "filtered": 49.20000076, - "r_filtered": 100, - "index_condition": "t1.nm like '500%'", - "attached_condition": "t1.fl2 = 0" - } - } - ] - } -} -select * from t1 where nm like '500%' AND fl2 = 0; -pk nm fl1 fl2 -517 500 0 0 -truncate table name; -truncate table flag2; -truncate table t1; -insert into name(nm) select seq from seq_1_to_1000 order by rand(17); -insert into flag2(fl2) select seq mod 2 from seq_1_to_1000 order by rand(19); -insert into t1(nm,fl2) -select nm, fl2 from name, flag2 where name.pk = flag2.pk; -analyze table t1 persistent for all; -Table Op Msg_type Msg_text -test.t1 analyze status Engine-independent statistics collected -test.t1 analyze status Table is already up to date -set optimizer_switch='rowid_filter=off'; -explain -select * from t1 where nm like '500%' AND fl2 = 0; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 range idx1,idx2 idx1 35 NULL 1 Using index condition; Using where -analyze format=json -select * from t1 where nm like '500%' AND fl2 = 0; -ANALYZE -{ - "query_optimization": { - "r_total_time_ms": "REPLACED" - }, - "query_block": { - "select_id": 1, - "r_loops": 1, - "r_total_time_ms": "REPLACED", - "nested_loop": [ - { - "table": { - "table_name": "t1", - "access_type": "range", - "possible_keys": ["idx1", "idx2"], - "key": "idx1", - "key_length": "35", - "used_key_parts": ["nm"], - "r_loops": 1, - "rows": 1, - "r_rows": 1, - "r_table_time_ms": "REPLACED", - "r_other_time_ms": "REPLACED", - "filtered": 49.20000076, - "r_filtered": 100, - "index_condition": "t1.nm like '500%'", - "attached_condition": "t1.fl2 = 0" - } - } - ] - } -} -select * from t1 where nm like '500%' AND fl2 = 0; -pk nm fl1 fl2 -517 500 0 0 -truncate table name; -truncate table flag2; -truncate table t1; -insert into name(nm) select seq from seq_1_to_1000 order by rand(17); -insert into flag2(fl2) select seq mod 10 from seq_1_to_1000 order by rand(19); -insert into t1(nm,fl2) -select nm, fl2 from name, flag2 where name.pk = flag2.pk; -analyze table t1 persistent for all; -Table Op Msg_type Msg_text -test.t1 analyze status Engine-independent statistics collected -test.t1 analyze status Table is already up to date -select '607%' as a; -a -607% -set optimizer_switch='rowid_filter=on'; -explain -select * from t1 where nm like '607%' AND fl2 = 0; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 range idx1,idx2 idx1 35 NULL 1 Using index condition; Using where -select * from t1 where nm like '607%' AND fl2 = 0; -pk nm fl1 fl2 -721 607 0 0 -truncate table name; -truncate table flag2; -truncate table t1; -insert into name(nm) select seq from seq_1_to_10000 order by rand(17); -insert into flag2(fl2) select seq mod 100 from seq_1_to_10000 order by rand(19); -insert into t1(nm,fl2) -select nm, fl2 from name, flag2 where name.pk = flag2.pk; -analyze table t1 persistent for all; -Table Op Msg_type Msg_text -test.t1 analyze status Engine-independent statistics collected -test.t1 analyze status Table is already up to date -select '75%' as a; -a -75% -set optimizer_switch='rowid_filter=on'; -explain -select * from t1 where nm like '75%' AND fl2 = 0; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 ref|filter idx1,idx2 idx2|idx1 2|35 const 55 (1%) Using where; Using rowid filter -analyze format=json -select * from t1 where nm like '75%' AND fl2 = 0; -ANALYZE -{ - "query_optimization": { - "r_total_time_ms": "REPLACED" - }, - "query_block": { - "select_id": 1, - "r_loops": 1, - "r_total_time_ms": "REPLACED", - "nested_loop": [ - { - "table": { - "table_name": "t1", - "access_type": "ref", - "possible_keys": ["idx1", "idx2"], - "key": "idx2", - "key_length": "2", - "used_key_parts": ["fl2"], - "ref": ["const"], - "rowid_filter": { - "range": { - "key": "idx1", - "used_key_parts": ["nm"] - }, - "rows": 115, - "selectivity_pct": 1.15, - "r_rows": 111, - "r_lookups": 100, - "r_selectivity_pct": 2, - "r_buffer_size": "REPLACED", - "r_filling_time_ms": "REPLACED" - }, - "r_loops": 1, - "rows": 55, - "r_rows": 2, - "r_table_time_ms": "REPLACED", - "r_other_time_ms": "REPLACED", - "filtered": 1.149999976, - "r_filtered": 100, - "attached_condition": "t1.nm like '75%'" - } - } - ] - } -} -select * from t1 where nm like '75%' AND fl2 = 0; -pk nm fl1 fl2 -4543 7503 0 0 -7373 7518 0 0 -drop table name, flag2; -drop table t1; -create table t1 ( -pk int primary key auto_increment, -nm char(255), -fl1 tinyint default 0, -fl2 int default 0, -index idx1(nm, fl1), -index idx2(fl2) -) engine=myisam; -create table name ( -pk int primary key auto_increment, -nm bigint -) engine=myisam; -create table flag2 ( -pk int primary key auto_increment, -fl2 int -) engine=myisam; -insert into name(nm) select seq from seq_1_to_10000 order by rand(17); -insert into flag2(fl2) select seq mod 10 from seq_1_to_10000 order by rand(19); -insert into t1(nm,fl2) -select nm, fl2 from name, flag2 where name.pk = flag2.pk; -analyze table t1 persistent for all; -Table Op Msg_type Msg_text -test.t1 analyze status Engine-independent statistics collected -test.t1 analyze status Table is already up to date -select * from t1 -where -( -nm like '3400%' or nm like '3402%' or nm like '3403%' or -nm like '3404%' or nm like '3405%' or nm like '3406%' or nm like '3407%' or -nm like '3409%' or -nm like '3411%' or nm like '3412%' or nm like '3413%' or -nm like '3414%' or nm like '3415%' or nm like '3416%' or nm like '3417%' or -nm like '3418%' or nm like '3419%' or -nm like '3421%' or nm like '3422%' or nm like '3423%' or -nm like '3424%' or nm like '3425%' or nm like '3426%' or nm like '3427%' or -nm like '3428%' or nm like '3429%' or -nm like '3430%' or nm like '3431%' or nm like '3432%' or nm like '3433%' or -nm like '3434%' or nm like '3435%' or nm like '3436%' or nm like '3437%' or -nm like '3439%' or -nm like '3440%' or nm like '3441%' or nm like '3442%' or nm like '3443%' or -nm like '3444%' or nm like '3445%' or nm like '3446%' or nm like '3447%' or -nm like '3448%' -) and fl2 = 0; -pk nm fl1 fl2 -analyze format=json select * from t1 -where -( -nm like '3400%' or nm like '3402%' or nm like '3403%' or -nm like '3404%' or nm like '3405%' or nm like '3406%' or nm like '3407%' or -nm like '3409%' or -nm like '3411%' or nm like '3412%' or nm like '3413%' or -nm like '3414%' or nm like '3415%' or nm like '3416%' or nm like '3417%' or -nm like '3418%' or nm like '3419%' or -nm like '3421%' or nm like '3422%' or nm like '3423%' or -nm like '3424%' or nm like '3425%' or nm like '3426%' or nm like '3427%' or -nm like '3428%' or nm like '3429%' or -nm like '3430%' or nm like '3431%' or nm like '3432%' or nm like '3433%' or -nm like '3434%' or nm like '3435%' or nm like '3436%' or nm like '3437%' or -nm like '3439%' or -nm like '3440%' or nm like '3441%' or nm like '3442%' or nm like '3443%' or -nm like '3444%' or nm like '3445%' or nm like '3446%' or nm like '3447%' or -nm like '3448%' -) and fl2 = 0; -ANALYZE -{ - "query_optimization": { - "r_total_time_ms": "REPLACED" - }, - "query_block": { - "select_id": 1, - "r_loops": 1, - "r_total_time_ms": "REPLACED", - "nested_loop": [ - { - "table": { - "table_name": "t1", - "access_type": "range", - "possible_keys": ["idx1", "idx2"], - "key": "idx1", - "key_length": "256", - "used_key_parts": ["nm"], - "rowid_filter": { - "range": { - "key": "idx2", - "used_key_parts": ["fl2"] - }, - "rows": 863, - "selectivity_pct": 8.63, - "r_rows": 1000, - "r_lookups": 44, - "r_selectivity_pct": 0, - "r_buffer_size": "REPLACED", - "r_filling_time_ms": "REPLACED" - }, - "r_loops": 1, - "rows": 44, - "r_rows": 0, - "r_table_time_ms": "REPLACED", - "r_other_time_ms": "REPLACED", - "filtered": 8.630000114, - "r_filtered": 100, - "index_condition": "t1.nm like '3400%' or t1.nm like '3402%' or t1.nm like '3403%' or t1.nm like '3404%' or t1.nm like '3405%' or t1.nm like '3406%' or t1.nm like '3407%' or t1.nm like '3409%' or t1.nm like '3411%' or t1.nm like '3412%' or t1.nm like '3413%' or t1.nm like '3414%' or t1.nm like '3415%' or t1.nm like '3416%' or t1.nm like '3417%' or t1.nm like '3418%' or t1.nm like '3419%' or t1.nm like '3421%' or t1.nm like '3422%' or t1.nm like '3423%' or t1.nm like '3424%' or t1.nm like '3425%' or t1.nm like '3426%' or t1.nm like '3427%' or t1.nm like '3428%' or t1.nm like '3429%' or t1.nm like '3430%' or t1.nm like '3431%' or t1.nm like '3432%' or t1.nm like '3433%' or t1.nm like '3434%' or t1.nm like '3435%' or t1.nm like '3436%' or t1.nm like '3437%' or t1.nm like '3439%' or t1.nm like '3440%' or t1.nm like '3441%' or t1.nm like '3442%' or t1.nm like '3443%' or t1.nm like '3444%' or t1.nm like '3445%' or t1.nm like '3446%' or t1.nm like '3447%' or t1.nm like '3448%'", - "attached_condition": "t1.fl2 = 0" - } - } - ] - } -} -create table t0 select * from t1 where nm like '34%'; -delete from t1 using t1,t0 where t1.nm=t0.nm; -analyze format=json select * from t1 -where -( -nm like '3400%' or nm like '3402%' or nm like '3403%' or -nm like '3404%' or nm like '3405%' or nm like '3406%' or nm like '3407%' or -nm like '3409%' or -nm like '3411%' or nm like '3412%' or nm like '3413%' or -nm like '3414%' or nm like '3415%' or nm like '3416%' or nm like '3417%' or -nm like '3418%' or nm like '3419%' or -nm like '3421%' or nm like '3422%' or nm like '3423%' or -nm like '3424%' or nm like '3425%' or nm like '3426%' or nm like '3427%' or -nm like '3428%' or nm like '3429%' or -nm like '3430%' or nm like '3431%' or nm like '3432%' or nm like '3433%' or -nm like '3434%' or nm like '3435%' or nm like '3436%' or nm like '3437%' or -nm like '3439%' or -nm like '3440%' or nm like '3441%' or nm like '3442%' or nm like '3443%' or -nm like '3444%' or nm like '3445%' or nm like '3446%' or nm like '3447%' or -nm like '3448%' -) and fl2 = 0; -ANALYZE -{ - "query_optimization": { - "r_total_time_ms": "REPLACED" - }, - "query_block": { - "select_id": 1, - "r_loops": 1, - "r_total_time_ms": "REPLACED", - "nested_loop": [ - { - "table": { - "table_name": "t1", - "access_type": "range", - "possible_keys": ["idx1", "idx2"], - "key": "idx1", - "key_length": "256", - "used_key_parts": ["nm"], - "rowid_filter": { - "range": { - "key": "idx2", - "used_key_parts": ["fl2"] - }, - "rows": 853, - "selectivity_pct": 8.53, - "r_rows": 987, - "r_lookups": 0, - "r_selectivity_pct": 0, - "r_buffer_size": "REPLACED", - "r_filling_time_ms": "REPLACED" - }, - "r_loops": 1, - "rows": 44, - "r_rows": 0, - "r_table_time_ms": "REPLACED", - "r_other_time_ms": "REPLACED", - "filtered": 8.529999733, - "r_filtered": 100, - "index_condition": "t1.nm like '3400%' or t1.nm like '3402%' or t1.nm like '3403%' or t1.nm like '3404%' or t1.nm like '3405%' or t1.nm like '3406%' or t1.nm like '3407%' or t1.nm like '3409%' or t1.nm like '3411%' or t1.nm like '3412%' or t1.nm like '3413%' or t1.nm like '3414%' or t1.nm like '3415%' or t1.nm like '3416%' or t1.nm like '3417%' or t1.nm like '3418%' or t1.nm like '3419%' or t1.nm like '3421%' or t1.nm like '3422%' or t1.nm like '3423%' or t1.nm like '3424%' or t1.nm like '3425%' or t1.nm like '3426%' or t1.nm like '3427%' or t1.nm like '3428%' or t1.nm like '3429%' or t1.nm like '3430%' or t1.nm like '3431%' or t1.nm like '3432%' or t1.nm like '3433%' or t1.nm like '3434%' or t1.nm like '3435%' or t1.nm like '3436%' or t1.nm like '3437%' or t1.nm like '3439%' or t1.nm like '3440%' or t1.nm like '3441%' or t1.nm like '3442%' or t1.nm like '3443%' or t1.nm like '3444%' or t1.nm like '3445%' or t1.nm like '3446%' or t1.nm like '3447%' or t1.nm like '3448%'", - "attached_condition": "t1.fl2 = 0" - } - } - ] - } -} -drop table t0; -set optimizer_switch='rowid_filter=default'; -drop table name, flag2; -drop table t1; -set @@use_stat_tables=@save_use_stat_tables; -# -# MDEV-21633 -# Assertion `tmp >= 0' failed in best_access_path with rowid_filter=ON -# -set @save_optimizer_switch= @@optimizer_switch; -SET optimizer_switch='rowid_filter=on'; -CREATE TABLE t1 ( -pk INT AUTO_INCREMENT, -a INT, -b VARCHAR(8), -KEY(a), -PRIMARY KEY(pk), -KEY (a,pk) -) ENGINE=MyISAM; -INSERT INTO t1 (a,b) VALUES -(NULL,'d'),(9,'b'),(2,'x'),(5,'k'),(NULL,'d'),(3,'s'),(5,'k'),(1,'r'), -(8,'l'),(3,'z'),(1,'c'),(1,'q'),(NULL,'x'),(NULL,'p'),(NULL,'z'),(7,'a'), -(0,'i'),(3,'s'),(NULL,'h'),(4,'p'),(1,'i'),(4,'f'),(1,'c'),(NULL,'a'), -(NULL,'x'),(1,'b'),(NULL,'n'),(NULL,'h'),(5,'i'),(6,'e'),(NULL,'i'), -(7,'e'),(1,'r'),(NULL,'z'),(1,'i'),(14,'c'),(6,'u'),(3,'b'),(4,'z'), -(2,'c'),(70,'d'),(NULL,'p'),(21,'j'),(6,'e'),(5,'c'),(13,'i'),(42,'d'), -(80,'s'),(14,'t'),(9,'a'),(0,'2'),(0,NULL),(0,NULL),(0,NULL),(0,''), -(0,''),(0,'1'),(0,''),(0,''),(0,''),(0,''),(0,NULL),(0,''),(0,''),(0,''), -(0,NULL),(0,''),(0,''),(0,''),(0,''),(0,''),(0,''),(0,NULL),(0,NULL), -(0,NULL),(0,''),(0,''),(0,''),(0,''),(0,NULL),(0,''),(0,NULL),(0,NULL), -(0,''),(0,''),(0,''),(0,NULL),(0,''),(0,NULL),(0,''),(0,''),(0,''),(0,''), -(0,''),(0,''),(0,''),(0,NULL),(0,''),(0,NULL),(0,''); -CREATE TABLE t2 (c INT) ENGINE=MyISAM; -INSERT INTO t2 VALUES (1),(2),(3),(4),(5),(6); -SELECT * FROM t1 JOIN t2 WHERE a = c AND pk BETWEEN 4 AND 7 AND a BETWEEN 2 AND 12 AND b != 'foo'; -pk a b c -6 3 s 3 -4 5 k 5 -7 5 k 5 -explain SELECT * FROM t1 JOIN t2 WHERE a = c AND pk BETWEEN 4 AND 7 AND a BETWEEN 2 AND 12 AND b != 'foo'; -id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 range|filter PRIMARY,a,a_2 PRIMARY|a 4|5 NULL 4 (11%) Using index condition; Using where; Using rowid filter -1 SIMPLE t2 ALL NULL NULL NULL NULL 6 Using where; Using join buffer (flat, BNL join) -SET optimizer_switch='rowid_filter=off'; -SELECT * FROM t1 JOIN t2 WHERE a = c AND pk BETWEEN 4 AND 7 AND a BETWEEN 2 AND 12 AND b != 'foo'; -pk a b c -6 3 s 3 -4 5 k 5 -7 5 k 5 -SET @@optimizer_switch=@save_optimizer_switch; -DROP TABLE t1, t2; SET GLOBAL innodb_stats_persistent=@save_stats_persistent; # # MDEV-18755: possible RORI-plan and possible plan with range filter diff --git a/mysql-test/main/rowid_filter_myisam.result b/mysql-test/main/rowid_filter_myisam.result index 927257d2cc7..a09f3b75d3d 100644 --- a/mysql-test/main/rowid_filter_myisam.result +++ b/mysql-test/main/rowid_filter_myisam.result @@ -1,3 +1,4 @@ +SET optimizer_switch='rowid_filter=on'; # # MDEV-22553: Assertion `info->lastpos == (~ (my_off_t) 0)' failed in mi_rkey with rowid_filer=on # @@ -19,3 +20,675 @@ ALTER TABLE t1 ENABLE KEYS; SELECT * FROM t1 WHERE ( a BETWEEN 255 AND 270 OR f = 200 ) AND f IN ( 1, 4, 112, 143 ) AND d IN ('Montana', 'South Dakota'); a b c d e f DROP TABLE t1; +use test; +# +# MDEV-18816: potential range filter for one join table with +# impossible WHERE for another +# +create table t1 ( +pk int not null primary key, c2 varchar(10) , i1 int,key (c2) +) engine=myisam; +insert into t1 values (1,'a',-5),(2,'a',null); +create table t2 ( +pk int, i1 int, c1 varchar(30) , key c1 (c1(30)), key i1 (i1) +) engine=myisam; +insert into t2 values +(1,-5,'a'),(2,null,'a'),(3,null,'a'),(4,null,'a'),(5,5,'a'),(6,null,'a'), +(7,4,'a'),(8,55,'a'),(9,null,'a'),(10,null,'a'),(11,null,'a'),(12,-5,'a'), +(13,-5,'a'),(14,null,'a'),(15,null,'a'),(16,-5,'a'),(17,-5,'a'); +select 1 +from t1 +left join +t2 join t1 as t1_a on t2.i1 = t1_a.pk +on t1.c2 = t2.c1 +where t1_a.pk is null and t1_a.i1 != 3; +1 +explain extended select 1 +from t1 +left join +t2 join t1 as t1_a on t2.i1 = t1_a.pk +on t1.c2 = t2.c1 +where t1_a.pk is null and t1_a.i1 != 3; +id select_type table type possible_keys key key_len ref rows filtered Extra +1 SIMPLE NULL NULL NULL NULL NULL NULL NULL NULL Impossible WHERE noticed after reading const tables +Warnings: +Note 1003 select 1 AS `1` from `test`.`t1` join `test`.`t2` join `test`.`t1` `t1_a` where 0 +drop table t1,t2; +# +# MDEV-18640: TABLE::prune_range_rowid_filters: Conditional jump or +# move depends on uninitialized value +# +CREATE TABLE t1 ( +pk INT, i INT, PRIMARY KEY (pk), KEY (pk,i) +) ENGINE=MyISAM; +INSERT INTO t1 VALUES (1,10), (7,70), (2,20); +SELECT * FROM t1 WHERE pk < 5; +pk i +1 10 +2 20 +DROP TABLE t1; +# +# MDEV-18956: Possible rowid filter for subquery for which +# in_to_exists strategy has been chosen +# +CREATE TABLE t1 (pk int) engine=myisam ; +INSERT INTO t1 VALUES (1),(2); +CREATE TABLE t2 ( +pk int auto_increment PRIMARY KEY, +i1 int, i2 int, c2 varchar(1), +KEY (i1), KEY (i2) +) engine=myisam; +INSERT INTO t2 VALUES +(1,8,6,'t'),(2,5,7,'i'),(3,4,4,'h'),(4,207,38,'d'),(5,183,206,'b'), +(6,7,null,'o'),(7,1,2,'j'),(8,17,36,'s'),(9,4,5,'q'),(10,0,6,'l'), +(11,1,9,'j'),(12,5,6,'y'),(13,null,0,'i'),(14,7,7,'x'),(15,5,2,'u'); +SELECT * FROM t1 HAVING (7, 9) IN (SELECT t2.i1, t2.i2 FROM t2 WHERE t2.i1 = 3); +pk +EXPLAIN EXTENDED +SELECT * FROM t1 HAVING (7, 9) IN (SELECT t2.i1, t2.i2 FROM t2 WHERE t2.i1 = 3); +id select_type table type possible_keys key key_len ref rows filtered Extra +1 PRIMARY NULL NULL NULL NULL NULL NULL NULL NULL Impossible HAVING +2 SUBQUERY NULL NULL NULL NULL NULL NULL NULL NULL no matching row in const table +Warnings: +Note 1003 /* select#1 */ select `test`.`t1`.`pk` AS `pk` from `test`.`t1` having 0 +DROP TABLE t1,t2; +# +# MDEV-19255: rowid range filter built for range condition +# that uses in expensive subquery +# +CREATE TABLE t1 ( +pk1 INT PRIMARY KEY, a1 INT, b1 VARCHAR(1), KEY(b1) +) ENGINE=MyISAM; +INSERT INTO t1 VALUES +(10,0,'z'),(11,3,'j'),(12,8,'f'),(13,8,'p'),(14,6,'w'),(15,0,'c'),(16,1,'j'), +(17,1,'f'),(18,5,'v'),(19,3,'f'),(20,2,'q'),(21,8,'y'),(22,0,'a'),(23,9,'w'), +(24,3,'e'),(25,1,'b'),(26,9,'r'),(27,2,'k'),(28,5,'c'),(29,3,'k'),(30,9,'b'), +(31,8,'j'),(32,1,'t'),(33,8,'n'),(34,3,'z'),(35,0,'u'),(36,3,'a'),(37,3,'g'), +(38,1,'f'),(39,6,'p'),(40,6,'m'),(41,6,'t'),(42,7,'i'),(43,4,'h'),(44,3,'d'), +(45,2,'b'),(46,1,'o'),(47,2,'j'),(48,6,'s'),(49,5,'q'),(50,6,'l'),(51,9,'j'), +(52,6,'y'),(53,0,'i'),(54,7,'x'),(55,2,'u'),(56,6,'t'),(57,4,'b'),(58,5,'m'), +(59,4,'x'),(60,8,'x'),(61,6,'v'),(62,8,'m'),(63,4,'j'),(64,8,'z'),(65,2,'a'), +(66,9,'i'),(67,4,'g'),(68,8,'h'),(69,1,'p'),(70,8,'a'),(71,0,'x'),(72,2,'s'), +(73,6,'k'),(74,0,'m'),(75,6,'e'),(76,9,'y'),(77,7,'d'),(78,7,'w'),(79,6,'y'), +(80,9,'s'),(81,9,'x'),(82,6,'l'),(83,9,'f'),(84,8,'x'),(85,1,'p'),(86,7,'y'), +(87,6,'p'),(88,1,'g'),(89,3,'c'),(90,5,'h'),(91,3,'p'),(92,2,'b'),(93,1,NULL), +(94,3,NULL),(95,2,'y'),(96,7,'s'),(97,7,'x'),(98,6,'i'),(99,9,'t'),(100,5,'j'), +(101,0,'u'),(102,7,'r'),(103,2,'x'),(104,8,'e'),(105,8,'i'),(106,5,'q'), +(107,8,'z'),(108,3,'k'),(109,65,NULL); +CREATE TABLE t2 (pk2 INT PRIMARY KEY, a2 INT, b2 VARCHAR(1)) ENGINE=MyISAM; +INSERT INTO t2 VALUES (1,1,'x'); +INSERT INTO t2 SELECT * FROM t1; +SELECT * FROM t1 INNER JOIN t2 ON ( pk1 <> pk2 AND pk1 = a2 ) +WHERE b1 <= ( SELECT MAX(b2) FROM t2 WHERE pk2 <= 1 ); +pk1 a1 b1 pk2 a2 b2 +65 2 a 109 65 NULL +EXPLAIN EXTENDED SELECT * FROM t1 INNER JOIN t2 ON ( pk1 <> pk2 AND pk1 = a2 ) +WHERE b1 <= ( SELECT MAX(b2) FROM t2 WHERE pk2 <= 1 ); +id select_type table type possible_keys key key_len ref rows filtered Extra +1 PRIMARY t2 ALL NULL NULL NULL NULL 101 100.00 Using where +1 PRIMARY t1 eq_ref|filter PRIMARY,b1 PRIMARY|b1 4|4 test.t2.a2 1 (87%) 87.00 Using where; Using rowid filter +2 SUBQUERY t2 range PRIMARY PRIMARY 4 NULL 1 100.00 Using index condition +Warnings: +Note 1003 /* select#1 */ select `test`.`t1`.`pk1` AS `pk1`,`test`.`t1`.`a1` AS `a1`,`test`.`t1`.`b1` AS `b1`,`test`.`t2`.`pk2` AS `pk2`,`test`.`t2`.`a2` AS `a2`,`test`.`t2`.`b2` AS `b2` from `test`.`t1` join `test`.`t2` where `test`.`t1`.`pk1` = `test`.`t2`.`a2` and `test`.`t1`.`b1` <= (/* select#2 */ select max(`test`.`t2`.`b2`) from `test`.`t2` where `test`.`t2`.`pk2` <= 1) and `test`.`t2`.`a2` <> `test`.`t2`.`pk2` +EXPLAIN FORMAT=JSON SELECT * FROM t1 INNER JOIN t2 ON ( pk1 <> pk2 AND pk1 = a2 ) +WHERE b1 <= ( SELECT MAX(b2) FROM t2 WHERE pk2 <= 1 ); +EXPLAIN +{ + "query_block": { + "select_id": 1, + "nested_loop": [ + { + "table": { + "table_name": "t2", + "access_type": "ALL", + "rows": 101, + "filtered": 100, + "attached_condition": "t2.a2 <> t2.pk2 and t2.a2 is not null" + } + }, + { + "table": { + "table_name": "t1", + "access_type": "eq_ref", + "possible_keys": ["PRIMARY", "b1"], + "key": "PRIMARY", + "key_length": "4", + "used_key_parts": ["pk1"], + "ref": ["test.t2.a2"], + "rowid_filter": { + "range": { + "key": "b1", + "used_key_parts": ["b1"] + }, + "rows": 87, + "selectivity_pct": 87 + }, + "rows": 1, + "filtered": 87, + "attached_condition": "t1.b1 <= (subquery#2)" + } + } + ], + "subqueries": [ + { + "query_block": { + "select_id": 2, + "nested_loop": [ + { + "table": { + "table_name": "t2", + "access_type": "range", + "possible_keys": ["PRIMARY"], + "key": "PRIMARY", + "key_length": "4", + "used_key_parts": ["pk2"], + "rows": 1, + "filtered": 100, + "index_condition": "t2.pk2 <= 1" + } + } + ] + } + } + ] + } +} +DROP TABLE t1,t2; +# +# MDEV-21794: Optimizer flag rowid_filter leads to long query +# +create table t10(a int); +insert into t10 values (0),(1),(2),(3),(4),(5),(6),(7),(8),(9); +create table t11(a int); +insert into t11 select A.a + B.a* 10 + C.a * 100 from t10 A, t10 B, t10 C; +CREATE TABLE t1 ( +el_id int(10) unsigned NOT NULL , +el_index blob NOT NULL, +el_index_60 varbinary(60) NOT NULL, +filler blob, +PRIMARY KEY (el_id), +KEY el_index (el_index(60)), +KEY el_index_60 (el_index_60,el_id) +); +insert into t1 +select +A.a+1000*B.a, +A.a+1000*B.a + 10000, +A.a+1000*B.a + 10000, +'filler-data-filler-data' +from +t11 A, t10 B; +analyze table t1 persistent for all; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze Warning Engine-independent statistics are not collected for column 'el_index' +test.t1 analyze Warning Engine-independent statistics are not collected for column 'filler' +test.t1 analyze status Table is already up to date +# This must not use rowid_filter with key=el_index|el_index_60: +explain +select * from t1 +where el_index like '10%' and (el_index_60 like '10%' or el_index_60 like '20%'); +id select_type table type possible_keys key key_len ref rows Extra +1 SIMPLE t1 range el_index,el_index_60 el_index 62 NULL 645 Using where +drop table t10, t11, t1; +# +# MDEV-22160: SIGSEGV in st_join_table::save_explain_data on SELECT +# +set @save_optimizer_switch= @@optimizer_switch; +SET @@optimizer_switch="index_merge_sort_union=OFF"; +CREATE TABLE t1 (a INT, b INT, INDEX(a), INDEX(b)); +INSERT INTO t1 VALUES (0,0),(0,0),(1,0),(-1,1), (-2,1), (-2,3), (-3,4), (-2,4),(3,3),(3,4),(3,5),(8,8),(8,9),(1,0),(2,0),(0,0),(0,0); +explain +SELECT * FROM t1 WHERE a > 0 AND b=0; +id select_type table type possible_keys key key_len ref rows Extra +1 SIMPLE t1 ref|filter a,b b|a 5|5 const 7 (47%) Using where; Using rowid filter +SELECT * FROM t1 WHERE a > 0 AND b=0; +a b +1 0 +1 0 +2 0 +drop table t1; +SET @@optimizer_switch=@save_optimizer_switch; +# +# MDEV-21633 +# Assertion `tmp >= 0' failed in best_access_path with rowid_filter=ON +# +set @save_optimizer_switch= @@optimizer_switch; +SET optimizer_switch='rowid_filter=on'; +CREATE TABLE t1 ( +pk INT AUTO_INCREMENT, +a INT, +b VARCHAR(8), +KEY(a), +PRIMARY KEY(pk), +KEY (a,pk) +) ENGINE=MyISAM; +INSERT INTO t1 (a,b) VALUES +(NULL,'d'),(9,'b'),(2,'x'),(5,'k'),(NULL,'d'),(3,'s'),(5,'k'),(1,'r'), +(8,'l'),(3,'z'),(1,'c'),(1,'q'),(NULL,'x'),(NULL,'p'),(NULL,'z'),(7,'a'), +(0,'i'),(3,'s'),(NULL,'h'),(4,'p'),(1,'i'),(4,'f'),(1,'c'),(NULL,'a'), +(NULL,'x'),(1,'b'),(NULL,'n'),(NULL,'h'),(5,'i'),(6,'e'),(NULL,'i'), +(7,'e'),(1,'r'),(NULL,'z'),(1,'i'),(14,'c'),(6,'u'),(3,'b'),(4,'z'), +(2,'c'),(70,'d'),(NULL,'p'),(21,'j'),(6,'e'),(5,'c'),(13,'i'),(42,'d'), +(80,'s'),(14,'t'),(9,'a'),(0,'2'),(0,NULL),(0,NULL),(0,NULL),(0,''), +(0,''),(0,'1'),(0,''),(0,''),(0,''),(0,''),(0,NULL),(0,''),(0,''),(0,''), +(0,NULL),(0,''),(0,''),(0,''),(0,''),(0,''),(0,''),(0,NULL),(0,NULL), +(0,NULL),(0,''),(0,''),(0,''),(0,''),(0,NULL),(0,''),(0,NULL),(0,NULL), +(0,''),(0,''),(0,''),(0,NULL),(0,''),(0,NULL),(0,''),(0,''),(0,''),(0,''), +(0,''),(0,''),(0,''),(0,NULL),(0,''),(0,NULL),(0,''); +CREATE TABLE t2 (c INT) ENGINE=MyISAM; +INSERT INTO t2 VALUES (1),(2),(3),(4),(5),(6); +SELECT * FROM t1 JOIN t2 WHERE a = c AND pk BETWEEN 4 AND 7 AND a BETWEEN 2 AND 12 AND b != 'foo'; +pk a b c +6 3 s 3 +4 5 k 5 +7 5 k 5 +explain SELECT * FROM t1 JOIN t2 WHERE a = c AND pk BETWEEN 4 AND 7 AND a BETWEEN 2 AND 12 AND b != 'foo'; +id select_type table type possible_keys key key_len ref rows Extra +1 SIMPLE t1 range|filter PRIMARY,a,a_2 PRIMARY|a 4|5 NULL 4 (11%) Using index condition; Using where; Using rowid filter +1 SIMPLE t2 ALL NULL NULL NULL NULL 6 Using where; Using join buffer (flat, BNL join) +SET optimizer_switch='rowid_filter=off'; +SELECT * FROM t1 JOIN t2 WHERE a = c AND pk BETWEEN 4 AND 7 AND a BETWEEN 2 AND 12 AND b != 'foo'; +pk a b c +6 3 s 3 +4 5 k 5 +7 5 k 5 +SET @@optimizer_switch=@save_optimizer_switch; +DROP TABLE t1, t2; +# +# MDEV-28846: Poor performance when rowid filter contains no elements +# +create table t1 ( +pk int primary key auto_increment, +nm varchar(32), +fl1 tinyint default 0, +fl2 tinyint default 0, +index idx1(nm, fl1), +index idx2(fl2) +) engine=myisam; +create table name ( +pk int primary key auto_increment, +nm bigint +) engine=myisam; +create table flag2 ( +pk int primary key auto_increment, +fl2 tinyint +) engine=myisam; +insert into name(nm) select seq from seq_1_to_1000 order by rand(17); +insert into flag2(fl2) select seq mod 2 from seq_1_to_1000 order by rand(19); +insert into t1(nm,fl2) +select nm, fl2 from name, flag2 where name.pk = flag2.pk; +analyze table t1 persistent for all; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status Table is already up to date +select '500%' as a; +a +500% +set optimizer_switch='rowid_filter=on'; +explain +select * from t1 where nm like '500%' AND fl2 = 0; +id select_type table type possible_keys key key_len ref rows Extra +1 SIMPLE t1 range idx1,idx2 idx1 35 NULL 1 Using index condition; Using where +analyze format=json +select * from t1 where nm like '500%' AND fl2 = 0; +ANALYZE +{ + "query_optimization": { + "r_total_time_ms": "REPLACED" + }, + "query_block": { + "select_id": 1, + "r_loops": 1, + "r_total_time_ms": "REPLACED", + "nested_loop": [ + { + "table": { + "table_name": "t1", + "access_type": "range", + "possible_keys": ["idx1", "idx2"], + "key": "idx1", + "key_length": "35", + "used_key_parts": ["nm"], + "r_loops": 1, + "rows": 1, + "r_rows": 1, + "r_table_time_ms": "REPLACED", + "r_other_time_ms": "REPLACED", + "filtered": 49.20000076, + "r_filtered": 100, + "index_condition": "t1.nm like '500%'", + "attached_condition": "t1.fl2 = 0" + } + } + ] + } +} +select * from t1 where nm like '500%' AND fl2 = 0; +pk nm fl1 fl2 +517 500 0 0 +truncate table name; +truncate table flag2; +truncate table t1; +insert into name(nm) select seq from seq_1_to_1000 order by rand(17); +insert into flag2(fl2) select seq mod 2 from seq_1_to_1000 order by rand(19); +insert into t1(nm,fl2) +select nm, fl2 from name, flag2 where name.pk = flag2.pk; +analyze table t1 persistent for all; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status Table is already up to date +set optimizer_switch='rowid_filter=off'; +explain +select * from t1 where nm like '500%' AND fl2 = 0; +id select_type table type possible_keys key key_len ref rows Extra +1 SIMPLE t1 range idx1,idx2 idx1 35 NULL 1 Using index condition; Using where +analyze format=json +select * from t1 where nm like '500%' AND fl2 = 0; +ANALYZE +{ + "query_optimization": { + "r_total_time_ms": "REPLACED" + }, + "query_block": { + "select_id": 1, + "r_loops": 1, + "r_total_time_ms": "REPLACED", + "nested_loop": [ + { + "table": { + "table_name": "t1", + "access_type": "range", + "possible_keys": ["idx1", "idx2"], + "key": "idx1", + "key_length": "35", + "used_key_parts": ["nm"], + "r_loops": 1, + "rows": 1, + "r_rows": 1, + "r_table_time_ms": "REPLACED", + "r_other_time_ms": "REPLACED", + "filtered": 49.20000076, + "r_filtered": 100, + "index_condition": "t1.nm like '500%'", + "attached_condition": "t1.fl2 = 0" + } + } + ] + } +} +select * from t1 where nm like '500%' AND fl2 = 0; +pk nm fl1 fl2 +517 500 0 0 +truncate table name; +truncate table flag2; +truncate table t1; +insert into name(nm) select seq from seq_1_to_1000 order by rand(17); +insert into flag2(fl2) select seq mod 10 from seq_1_to_1000 order by rand(19); +insert into t1(nm,fl2) +select nm, fl2 from name, flag2 where name.pk = flag2.pk; +analyze table t1 persistent for all; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status Table is already up to date +select '607%' as a; +a +607% +set optimizer_switch='rowid_filter=on'; +explain +select * from t1 where nm like '607%' AND fl2 = 0; +id select_type table type possible_keys key key_len ref rows Extra +1 SIMPLE t1 range idx1,idx2 idx1 35 NULL 1 Using index condition; Using where +select * from t1 where nm like '607%' AND fl2 = 0; +pk nm fl1 fl2 +721 607 0 0 +truncate table name; +truncate table flag2; +truncate table t1; +insert into name(nm) select seq from seq_1_to_10000 order by rand(17); +insert into flag2(fl2) select seq mod 100 from seq_1_to_10000 order by rand(19); +insert into t1(nm,fl2) +select nm, fl2 from name, flag2 where name.pk = flag2.pk; +analyze table t1 persistent for all; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status Table is already up to date +select '75%' as a; +a +75% +set optimizer_switch='rowid_filter=on'; +explain +select * from t1 where nm like '75%' AND fl2 = 0; +id select_type table type possible_keys key key_len ref rows Extra +1 SIMPLE t1 ref|filter idx1,idx2 idx2|idx1 2|35 const 55 (1%) Using where; Using rowid filter +analyze format=json +select * from t1 where nm like '75%' AND fl2 = 0; +ANALYZE +{ + "query_optimization": { + "r_total_time_ms": "REPLACED" + }, + "query_block": { + "select_id": 1, + "r_loops": 1, + "r_total_time_ms": "REPLACED", + "nested_loop": [ + { + "table": { + "table_name": "t1", + "access_type": "ref", + "possible_keys": ["idx1", "idx2"], + "key": "idx2", + "key_length": "2", + "used_key_parts": ["fl2"], + "ref": ["const"], + "rowid_filter": { + "range": { + "key": "idx1", + "used_key_parts": ["nm"] + }, + "rows": 115, + "selectivity_pct": 1.15, + "r_rows": 111, + "r_lookups": 100, + "r_selectivity_pct": 2, + "r_buffer_size": "REPLACED", + "r_filling_time_ms": "REPLACED" + }, + "r_loops": 1, + "rows": 55, + "r_rows": 2, + "r_table_time_ms": "REPLACED", + "r_other_time_ms": "REPLACED", + "filtered": 1.149999976, + "r_filtered": 100, + "attached_condition": "t1.nm like '75%'" + } + } + ] + } +} +select * from t1 where nm like '75%' AND fl2 = 0; +pk nm fl1 fl2 +4543 7503 0 0 +7373 7518 0 0 +drop table name, flag2; +drop table t1; +create table t1 ( +pk int primary key auto_increment, +nm char(255), +fl1 tinyint default 0, +fl2 int default 0, +index idx1(nm, fl1), +index idx2(fl2) +) engine=myisam; +create table name ( +pk int primary key auto_increment, +nm bigint +) engine=myisam; +create table flag2 ( +pk int primary key auto_increment, +fl2 int +) engine=myisam; +insert into name(nm) select seq from seq_1_to_10000 order by rand(17); +insert into flag2(fl2) select seq mod 10 from seq_1_to_10000 order by rand(19); +insert into t1(nm,fl2) +select nm, fl2 from name, flag2 where name.pk = flag2.pk; +analyze table t1 persistent for all; +Table Op Msg_type Msg_text +test.t1 analyze status Engine-independent statistics collected +test.t1 analyze status Table is already up to date +select * from t1 +where +( +nm like '3400%' or nm like '3402%' or nm like '3403%' or +nm like '3404%' or nm like '3405%' or nm like '3406%' or nm like '3407%' or +nm like '3409%' or +nm like '3411%' or nm like '3412%' or nm like '3413%' or +nm like '3414%' or nm like '3415%' or nm like '3416%' or nm like '3417%' or +nm like '3418%' or nm like '3419%' or +nm like '3421%' or nm like '3422%' or nm like '3423%' or +nm like '3424%' or nm like '3425%' or nm like '3426%' or nm like '3427%' or +nm like '3428%' or nm like '3429%' or +nm like '3430%' or nm like '3431%' or nm like '3432%' or nm like '3433%' or +nm like '3434%' or nm like '3435%' or nm like '3436%' or nm like '3437%' or +nm like '3439%' or +nm like '3440%' or nm like '3441%' or nm like '3442%' or nm like '3443%' or +nm like '3444%' or nm like '3445%' or nm like '3446%' or nm like '3447%' or +nm like '3448%' +) and fl2 = 0; +pk nm fl1 fl2 +analyze format=json select * from t1 +where +( +nm like '3400%' or nm like '3402%' or nm like '3403%' or +nm like '3404%' or nm like '3405%' or nm like '3406%' or nm like '3407%' or +nm like '3409%' or +nm like '3411%' or nm like '3412%' or nm like '3413%' or +nm like '3414%' or nm like '3415%' or nm like '3416%' or nm like '3417%' or +nm like '3418%' or nm like '3419%' or +nm like '3421%' or nm like '3422%' or nm like '3423%' or +nm like '3424%' or nm like '3425%' or nm like '3426%' or nm like '3427%' or +nm like '3428%' or nm like '3429%' or +nm like '3430%' or nm like '3431%' or nm like '3432%' or nm like '3433%' or +nm like '3434%' or nm like '3435%' or nm like '3436%' or nm like '3437%' or +nm like '3439%' or +nm like '3440%' or nm like '3441%' or nm like '3442%' or nm like '3443%' or +nm like '3444%' or nm like '3445%' or nm like '3446%' or nm like '3447%' or +nm like '3448%' +) and fl2 = 0; +ANALYZE +{ + "query_optimization": { + "r_total_time_ms": "REPLACED" + }, + "query_block": { + "select_id": 1, + "r_loops": 1, + "r_total_time_ms": "REPLACED", + "nested_loop": [ + { + "table": { + "table_name": "t1", + "access_type": "range", + "possible_keys": ["idx1", "idx2"], + "key": "idx1", + "key_length": "256", + "used_key_parts": ["nm"], + "rowid_filter": { + "range": { + "key": "idx2", + "used_key_parts": ["fl2"] + }, + "rows": 863, + "selectivity_pct": 8.63, + "r_rows": 1000, + "r_lookups": 44, + "r_selectivity_pct": 0, + "r_buffer_size": "REPLACED", + "r_filling_time_ms": "REPLACED" + }, + "r_loops": 1, + "rows": 44, + "r_rows": 0, + "r_table_time_ms": "REPLACED", + "r_other_time_ms": "REPLACED", + "filtered": 8.630000114, + "r_filtered": 100, + "index_condition": "t1.nm like '3400%' or t1.nm like '3402%' or t1.nm like '3403%' or t1.nm like '3404%' or t1.nm like '3405%' or t1.nm like '3406%' or t1.nm like '3407%' or t1.nm like '3409%' or t1.nm like '3411%' or t1.nm like '3412%' or t1.nm like '3413%' or t1.nm like '3414%' or t1.nm like '3415%' or t1.nm like '3416%' or t1.nm like '3417%' or t1.nm like '3418%' or t1.nm like '3419%' or t1.nm like '3421%' or t1.nm like '3422%' or t1.nm like '3423%' or t1.nm like '3424%' or t1.nm like '3425%' or t1.nm like '3426%' or t1.nm like '3427%' or t1.nm like '3428%' or t1.nm like '3429%' or t1.nm like '3430%' or t1.nm like '3431%' or t1.nm like '3432%' or t1.nm like '3433%' or t1.nm like '3434%' or t1.nm like '3435%' or t1.nm like '3436%' or t1.nm like '3437%' or t1.nm like '3439%' or t1.nm like '3440%' or t1.nm like '3441%' or t1.nm like '3442%' or t1.nm like '3443%' or t1.nm like '3444%' or t1.nm like '3445%' or t1.nm like '3446%' or t1.nm like '3447%' or t1.nm like '3448%'", + "attached_condition": "t1.fl2 = 0" + } + } + ] + } +} +create table t0 select * from t1 where nm like '34%'; +delete from t1 using t1,t0 where t1.nm=t0.nm; +analyze format=json select * from t1 +where +( +nm like '3400%' or nm like '3402%' or nm like '3403%' or +nm like '3404%' or nm like '3405%' or nm like '3406%' or nm like '3407%' or +nm like '3409%' or +nm like '3411%' or nm like '3412%' or nm like '3413%' or +nm like '3414%' or nm like '3415%' or nm like '3416%' or nm like '3417%' or +nm like '3418%' or nm like '3419%' or +nm like '3421%' or nm like '3422%' or nm like '3423%' or +nm like '3424%' or nm like '3425%' or nm like '3426%' or nm like '3427%' or +nm like '3428%' or nm like '3429%' or +nm like '3430%' or nm like '3431%' or nm like '3432%' or nm like '3433%' or +nm like '3434%' or nm like '3435%' or nm like '3436%' or nm like '3437%' or +nm like '3439%' or +nm like '3440%' or nm like '3441%' or nm like '3442%' or nm like '3443%' or +nm like '3444%' or nm like '3445%' or nm like '3446%' or nm like '3447%' or +nm like '3448%' +) and fl2 = 0; +ANALYZE +{ + "query_optimization": { + "r_total_time_ms": "REPLACED" + }, + "query_block": { + "select_id": 1, + "r_loops": 1, + "r_total_time_ms": "REPLACED", + "nested_loop": [ + { + "table": { + "table_name": "t1", + "access_type": "range", + "possible_keys": ["idx1", "idx2"], + "key": "idx1", + "key_length": "256", + "used_key_parts": ["nm"], + "rowid_filter": { + "range": { + "key": "idx2", + "used_key_parts": ["fl2"] + }, + "rows": 853, + "selectivity_pct": 8.53, + "r_rows": 987, + "r_lookups": 0, + "r_selectivity_pct": 0, + "r_buffer_size": "REPLACED", + "r_filling_time_ms": "REPLACED" + }, + "r_loops": 1, + "rows": 44, + "r_rows": 0, + "r_table_time_ms": "REPLACED", + "r_other_time_ms": "REPLACED", + "filtered": 8.529999733, + "r_filtered": 100, + "index_condition": "t1.nm like '3400%' or t1.nm like '3402%' or t1.nm like '3403%' or t1.nm like '3404%' or t1.nm like '3405%' or t1.nm like '3406%' or t1.nm like '3407%' or t1.nm like '3409%' or t1.nm like '3411%' or t1.nm like '3412%' or t1.nm like '3413%' or t1.nm like '3414%' or t1.nm like '3415%' or t1.nm like '3416%' or t1.nm like '3417%' or t1.nm like '3418%' or t1.nm like '3419%' or t1.nm like '3421%' or t1.nm like '3422%' or t1.nm like '3423%' or t1.nm like '3424%' or t1.nm like '3425%' or t1.nm like '3426%' or t1.nm like '3427%' or t1.nm like '3428%' or t1.nm like '3429%' or t1.nm like '3430%' or t1.nm like '3431%' or t1.nm like '3432%' or t1.nm like '3433%' or t1.nm like '3434%' or t1.nm like '3435%' or t1.nm like '3436%' or t1.nm like '3437%' or t1.nm like '3439%' or t1.nm like '3440%' or t1.nm like '3441%' or t1.nm like '3442%' or t1.nm like '3443%' or t1.nm like '3444%' or t1.nm like '3445%' or t1.nm like '3446%' or t1.nm like '3447%' or t1.nm like '3448%'", + "attached_condition": "t1.fl2 = 0" + } + } + ] + } +} +drop table t0; +set optimizer_switch='rowid_filter=default'; +drop table name, flag2; +drop table t1; diff --git a/mysql-test/main/rowid_filter_myisam.test b/mysql-test/main/rowid_filter_myisam.test index 3ea4dc26ea0..c340b50d9fd 100644 --- a/mysql-test/main/rowid_filter_myisam.test +++ b/mysql-test/main/rowid_filter_myisam.test @@ -1,3 +1,5 @@ +SET optimizer_switch='rowid_filter=on'; + --echo # --echo # MDEV-22553: Assertion `info->lastpos == (~ (my_off_t) 0)' failed in mi_rkey with rowid_filer=on --echo # @@ -1623,3 +1625,405 @@ ALTER TABLE t1 ENABLE KEYS; --echo # Must not crash: SELECT * FROM t1 WHERE ( a BETWEEN 255 AND 270 OR f = 200 ) AND f IN ( 1, 4, 112, 143 ) AND d IN ('Montana', 'South Dakota'); DROP TABLE t1; + + + +use test; + +--echo # +--echo # MDEV-18816: potential range filter for one join table with +--echo # impossible WHERE for another +--echo # + +create table t1 ( + pk int not null primary key, c2 varchar(10) , i1 int,key (c2) +) engine=myisam; +insert into t1 values (1,'a',-5),(2,'a',null); + +create table t2 ( + pk int, i1 int, c1 varchar(30) , key c1 (c1(30)), key i1 (i1) +) engine=myisam; +insert into t2 values + (1,-5,'a'),(2,null,'a'),(3,null,'a'),(4,null,'a'),(5,5,'a'),(6,null,'a'), + (7,4,'a'),(8,55,'a'),(9,null,'a'),(10,null,'a'),(11,null,'a'),(12,-5,'a'), + (13,-5,'a'),(14,null,'a'),(15,null,'a'),(16,-5,'a'),(17,-5,'a'); + +let $q= +select 1 + from t1 + left join + t2 join t1 as t1_a on t2.i1 = t1_a.pk + on t1.c2 = t2.c1 +where t1_a.pk is null and t1_a.i1 != 3; + +eval $q; +eval explain extended $q; + +drop table t1,t2; + +--echo # +--echo # MDEV-18640: TABLE::prune_range_rowid_filters: Conditional jump or +--echo # move depends on uninitialized value +--echo # + +CREATE TABLE t1 ( + pk INT, i INT, PRIMARY KEY (pk), KEY (pk,i) +) ENGINE=MyISAM; +INSERT INTO t1 VALUES (1,10), (7,70), (2,20); + +SELECT * FROM t1 WHERE pk < 5; + +DROP TABLE t1; + +--echo # +--echo # MDEV-18956: Possible rowid filter for subquery for which +--echo # in_to_exists strategy has been chosen +--echo # + +CREATE TABLE t1 (pk int) engine=myisam ; +INSERT INTO t1 VALUES (1),(2); + +CREATE TABLE t2 ( + pk int auto_increment PRIMARY KEY, + i1 int, i2 int, c2 varchar(1), + KEY (i1), KEY (i2) +) engine=myisam; + +INSERT INTO t2 VALUES + (1,8,6,'t'),(2,5,7,'i'),(3,4,4,'h'),(4,207,38,'d'),(5,183,206,'b'), + (6,7,null,'o'),(7,1,2,'j'),(8,17,36,'s'),(9,4,5,'q'),(10,0,6,'l'), + (11,1,9,'j'),(12,5,6,'y'),(13,null,0,'i'),(14,7,7,'x'),(15,5,2,'u'); + +SELECT * FROM t1 HAVING (7, 9) IN (SELECT t2.i1, t2.i2 FROM t2 WHERE t2.i1 = 3); +EXPLAIN EXTENDED +SELECT * FROM t1 HAVING (7, 9) IN (SELECT t2.i1, t2.i2 FROM t2 WHERE t2.i1 = 3); + +DROP TABLE t1,t2; + +--echo # +--echo # MDEV-19255: rowid range filter built for range condition +--echo # that uses in expensive subquery +--echo # + +CREATE TABLE t1 ( + pk1 INT PRIMARY KEY, a1 INT, b1 VARCHAR(1), KEY(b1) +) ENGINE=MyISAM; +INSERT INTO t1 VALUES +(10,0,'z'),(11,3,'j'),(12,8,'f'),(13,8,'p'),(14,6,'w'),(15,0,'c'),(16,1,'j'), +(17,1,'f'),(18,5,'v'),(19,3,'f'),(20,2,'q'),(21,8,'y'),(22,0,'a'),(23,9,'w'), +(24,3,'e'),(25,1,'b'),(26,9,'r'),(27,2,'k'),(28,5,'c'),(29,3,'k'),(30,9,'b'), +(31,8,'j'),(32,1,'t'),(33,8,'n'),(34,3,'z'),(35,0,'u'),(36,3,'a'),(37,3,'g'), +(38,1,'f'),(39,6,'p'),(40,6,'m'),(41,6,'t'),(42,7,'i'),(43,4,'h'),(44,3,'d'), +(45,2,'b'),(46,1,'o'),(47,2,'j'),(48,6,'s'),(49,5,'q'),(50,6,'l'),(51,9,'j'), +(52,6,'y'),(53,0,'i'),(54,7,'x'),(55,2,'u'),(56,6,'t'),(57,4,'b'),(58,5,'m'), +(59,4,'x'),(60,8,'x'),(61,6,'v'),(62,8,'m'),(63,4,'j'),(64,8,'z'),(65,2,'a'), +(66,9,'i'),(67,4,'g'),(68,8,'h'),(69,1,'p'),(70,8,'a'),(71,0,'x'),(72,2,'s'), +(73,6,'k'),(74,0,'m'),(75,6,'e'),(76,9,'y'),(77,7,'d'),(78,7,'w'),(79,6,'y'), +(80,9,'s'),(81,9,'x'),(82,6,'l'),(83,9,'f'),(84,8,'x'),(85,1,'p'),(86,7,'y'), +(87,6,'p'),(88,1,'g'),(89,3,'c'),(90,5,'h'),(91,3,'p'),(92,2,'b'),(93,1,NULL), +(94,3,NULL),(95,2,'y'),(96,7,'s'),(97,7,'x'),(98,6,'i'),(99,9,'t'),(100,5,'j'), +(101,0,'u'),(102,7,'r'),(103,2,'x'),(104,8,'e'),(105,8,'i'),(106,5,'q'), +(107,8,'z'),(108,3,'k'),(109,65,NULL); + +CREATE TABLE t2 (pk2 INT PRIMARY KEY, a2 INT, b2 VARCHAR(1)) ENGINE=MyISAM; +INSERT INTO t2 VALUES (1,1,'x'); +INSERT INTO t2 SELECT * FROM t1; + +let $q= +SELECT * FROM t1 INNER JOIN t2 ON ( pk1 <> pk2 AND pk1 = a2 ) + WHERE b1 <= ( SELECT MAX(b2) FROM t2 WHERE pk2 <= 1 ); + +eval $q; +eval EXPLAIN EXTENDED $q; +eval EXPLAIN FORMAT=JSON $q; + +DROP TABLE t1,t2; + +--echo # +--echo # MDEV-21794: Optimizer flag rowid_filter leads to long query +--echo # +create table t10(a int); +insert into t10 values (0),(1),(2),(3),(4),(5),(6),(7),(8),(9); + +create table t11(a int); +insert into t11 select A.a + B.a* 10 + C.a * 100 from t10 A, t10 B, t10 C; + +CREATE TABLE t1 ( + el_id int(10) unsigned NOT NULL , + el_index blob NOT NULL, + el_index_60 varbinary(60) NOT NULL, + filler blob, + + PRIMARY KEY (el_id), + KEY el_index (el_index(60)), + KEY el_index_60 (el_index_60,el_id) +); + +insert into t1 +select + A.a+1000*B.a, + A.a+1000*B.a + 10000, + A.a+1000*B.a + 10000, + 'filler-data-filler-data' +from + t11 A, t10 B; +analyze table t1 persistent for all; + +--echo # This must not use rowid_filter with key=el_index|el_index_60: +explain +select * from t1 +where el_index like '10%' and (el_index_60 like '10%' or el_index_60 like '20%'); + +drop table t10, t11, t1; + + +--echo # +--echo # MDEV-22160: SIGSEGV in st_join_table::save_explain_data on SELECT +--echo # + +set @save_optimizer_switch= @@optimizer_switch; +SET @@optimizer_switch="index_merge_sort_union=OFF"; +CREATE TABLE t1 (a INT, b INT, INDEX(a), INDEX(b)); +INSERT INTO t1 VALUES (0,0),(0,0),(1,0),(-1,1), (-2,1), (-2,3), (-3,4), (-2,4),(3,3),(3,4),(3,5),(8,8),(8,9),(1,0),(2,0),(0,0),(0,0); +explain +SELECT * FROM t1 WHERE a > 0 AND b=0; +SELECT * FROM t1 WHERE a > 0 AND b=0; +drop table t1; +SET @@optimizer_switch=@save_optimizer_switch; + +--echo # +--echo # MDEV-21633 +--echo # Assertion `tmp >= 0' failed in best_access_path with rowid_filter=ON +--echo # + +set @save_optimizer_switch= @@optimizer_switch; +SET optimizer_switch='rowid_filter=on'; + +CREATE TABLE t1 ( + pk INT AUTO_INCREMENT, + a INT, + b VARCHAR(8), + KEY(a), + PRIMARY KEY(pk), + KEY (a,pk) +) ENGINE=MyISAM; + +INSERT INTO t1 (a,b) VALUES + (NULL,'d'),(9,'b'),(2,'x'),(5,'k'),(NULL,'d'),(3,'s'),(5,'k'),(1,'r'), + (8,'l'),(3,'z'),(1,'c'),(1,'q'),(NULL,'x'),(NULL,'p'),(NULL,'z'),(7,'a'), + (0,'i'),(3,'s'),(NULL,'h'),(4,'p'),(1,'i'),(4,'f'),(1,'c'),(NULL,'a'), + (NULL,'x'),(1,'b'),(NULL,'n'),(NULL,'h'),(5,'i'),(6,'e'),(NULL,'i'), + (7,'e'),(1,'r'),(NULL,'z'),(1,'i'),(14,'c'),(6,'u'),(3,'b'),(4,'z'), + (2,'c'),(70,'d'),(NULL,'p'),(21,'j'),(6,'e'),(5,'c'),(13,'i'),(42,'d'), + (80,'s'),(14,'t'),(9,'a'),(0,'2'),(0,NULL),(0,NULL),(0,NULL),(0,''), + (0,''),(0,'1'),(0,''),(0,''),(0,''),(0,''),(0,NULL),(0,''),(0,''),(0,''), + (0,NULL),(0,''),(0,''),(0,''),(0,''),(0,''),(0,''),(0,NULL),(0,NULL), + (0,NULL),(0,''),(0,''),(0,''),(0,''),(0,NULL),(0,''),(0,NULL),(0,NULL), + (0,''),(0,''),(0,''),(0,NULL),(0,''),(0,NULL),(0,''),(0,''),(0,''),(0,''), + (0,''),(0,''),(0,''),(0,NULL),(0,''),(0,NULL),(0,''); + +CREATE TABLE t2 (c INT) ENGINE=MyISAM; +INSERT INTO t2 VALUES (1),(2),(3),(4),(5),(6); + +SELECT * FROM t1 JOIN t2 WHERE a = c AND pk BETWEEN 4 AND 7 AND a BETWEEN 2 AND 12 AND b != 'foo'; + +explain SELECT * FROM t1 JOIN t2 WHERE a = c AND pk BETWEEN 4 AND 7 AND a BETWEEN 2 AND 12 AND b != 'foo'; + +SET optimizer_switch='rowid_filter=off'; + +SELECT * FROM t1 JOIN t2 WHERE a = c AND pk BETWEEN 4 AND 7 AND a BETWEEN 2 AND 12 AND b != 'foo'; + +SET @@optimizer_switch=@save_optimizer_switch; + +# Cleanup +DROP TABLE t1, t2; + +--echo # +--echo # MDEV-28846: Poor performance when rowid filter contains no elements +--echo # + +--source include/have_sequence.inc + +create table t1 ( + pk int primary key auto_increment, + nm varchar(32), + fl1 tinyint default 0, + fl2 tinyint default 0, + index idx1(nm, fl1), + index idx2(fl2) +) engine=myisam; + +create table name ( + pk int primary key auto_increment, + nm bigint +) engine=myisam; + +create table flag2 ( + pk int primary key auto_increment, + fl2 tinyint +) engine=myisam; + +insert into name(nm) select seq from seq_1_to_1000 order by rand(17); +insert into flag2(fl2) select seq mod 2 from seq_1_to_1000 order by rand(19); + +insert into t1(nm,fl2) + select nm, fl2 from name, flag2 where name.pk = flag2.pk; + +analyze table t1 persistent for all; + +let $a= +`select concat((select nm from t1 where fl2=0 order by RAND(13) limit 1),'%')`; +eval select '$a' as a; + +set optimizer_switch='rowid_filter=on'; +eval +explain +select * from t1 where nm like '$a' AND fl2 = 0; +--source include/analyze-format.inc +eval +analyze format=json +select * from t1 where nm like '$a' AND fl2 = 0; +eval +select * from t1 where nm like '$a' AND fl2 = 0; + +truncate table name; +truncate table flag2; +truncate table t1; + +insert into name(nm) select seq from seq_1_to_1000 order by rand(17); +insert into flag2(fl2) select seq mod 2 from seq_1_to_1000 order by rand(19); + +insert into t1(nm,fl2) + select nm, fl2 from name, flag2 where name.pk = flag2.pk; + +analyze table t1 persistent for all; + +set optimizer_switch='rowid_filter=off'; +eval +explain +select * from t1 where nm like '$a' AND fl2 = 0; +--source include/analyze-format.inc +eval +analyze format=json +select * from t1 where nm like '$a' AND fl2 = 0; +eval +select * from t1 where nm like '$a' AND fl2 = 0; + +truncate table name; +truncate table flag2; +truncate table t1; + +insert into name(nm) select seq from seq_1_to_1000 order by rand(17); +insert into flag2(fl2) select seq mod 10 from seq_1_to_1000 order by rand(19); + +insert into t1(nm,fl2) + select nm, fl2 from name, flag2 where name.pk = flag2.pk; + +analyze table t1 persistent for all; + +let $a= +`select concat((select nm from t1 where fl2=0 order by RAND(13) limit 1),'%')`; +eval select '$a' as a; + +set optimizer_switch='rowid_filter=on'; +eval +explain +select * from t1 where nm like '$a' AND fl2 = 0; +eval +select * from t1 where nm like '$a' AND fl2 = 0; + +truncate table name; +truncate table flag2; +truncate table t1; + +insert into name(nm) select seq from seq_1_to_10000 order by rand(17); +insert into flag2(fl2) select seq mod 100 from seq_1_to_10000 order by rand(19); + +insert into t1(nm,fl2) + select nm, fl2 from name, flag2 where name.pk = flag2.pk; + +analyze table t1 persistent for all; + +let $a= +`select concat(left((select nm from t1 where fl2=0 order by RAND(13) limit 1),2),'%')`; +eval select '$a' as a; + +set optimizer_switch='rowid_filter=on'; +eval +explain +select * from t1 where nm like '$a' AND fl2 = 0; +--source include/analyze-format.inc +eval +analyze format=json +select * from t1 where nm like '$a' AND fl2 = 0; +eval +select * from t1 where nm like '$a' AND fl2 = 0; + +drop table name, flag2; +drop table t1; + +# This test shows that if the container is empty there are no lookups into it + +create table t1 ( + pk int primary key auto_increment, + nm char(255), + fl1 tinyint default 0, + fl2 int default 0, + index idx1(nm, fl1), + index idx2(fl2) +) engine=myisam; + +create table name ( + pk int primary key auto_increment, + nm bigint +) engine=myisam; + +create table flag2 ( + pk int primary key auto_increment, + fl2 int +) engine=myisam; + +insert into name(nm) select seq from seq_1_to_10000 order by rand(17); +insert into flag2(fl2) select seq mod 10 from seq_1_to_10000 order by rand(19); + +insert into t1(nm,fl2) + select nm, fl2 from name, flag2 where name.pk = flag2.pk; + +analyze table t1 persistent for all; + +let $q= +select * from t1 +where +( + nm like '3400%' or nm like '3402%' or nm like '3403%' or + nm like '3404%' or nm like '3405%' or nm like '3406%' or nm like '3407%' or + nm like '3409%' or + nm like '3411%' or nm like '3412%' or nm like '3413%' or + nm like '3414%' or nm like '3415%' or nm like '3416%' or nm like '3417%' or + nm like '3418%' or nm like '3419%' or + nm like '3421%' or nm like '3422%' or nm like '3423%' or + nm like '3424%' or nm like '3425%' or nm like '3426%' or nm like '3427%' or + nm like '3428%' or nm like '3429%' or + nm like '3430%' or nm like '3431%' or nm like '3432%' or nm like '3433%' or + nm like '3434%' or nm like '3435%' or nm like '3436%' or nm like '3437%' or + nm like '3439%' or + nm like '3440%' or nm like '3441%' or nm like '3442%' or nm like '3443%' or + nm like '3444%' or nm like '3445%' or nm like '3446%' or nm like '3447%' or + nm like '3448%' +) and fl2 = 0; + +eval $q; +--source include/analyze-format.inc +eval analyze format=json $q; + +create table t0 select * from t1 where nm like '34%'; +delete from t1 using t1,t0 where t1.nm=t0.nm; +--source include/analyze-format.inc +eval analyze format=json $q; + +drop table t0; + +set optimizer_switch='rowid_filter=default'; + +drop table name, flag2; +drop table t1; diff --git a/mysql-test/suite/maria/icp.result b/mysql-test/suite/maria/icp.result index a421ba6d3ea..d990d8b0855 100644 --- a/mysql-test/suite/maria/icp.result +++ b/mysql-test/suite/maria/icp.result @@ -409,7 +409,7 @@ WHERE (pk BETWEEN 4 AND 5 OR pk < 2) AND c1 < 240 ORDER BY c1 LIMIT 1; id select_type table type possible_keys key key_len ref rows Extra -1 SIMPLE t1 range PRIMARY,k1 k1 5 NULL 4 Using index condition; Using where +1 SIMPLE t1 range|filter PRIMARY,k1 k1|PRIMARY 5|4 NULL 4 (38%) Using index condition; Using where; Using rowid filter DROP TABLE t1; # # diff --git a/mysys/array.c b/mysys/array.c index 6e871ee6343..02a54d44656 100644 --- a/mysys/array.c +++ b/mysys/array.c @@ -92,7 +92,7 @@ my_bool init_dynamic_array2(PSI_memory_key psi_key, DYNAMIC_ARRAY *array, my_bool insert_dynamic(DYNAMIC_ARRAY *array, const void * element) { void *buffer; - if (array->elements == array->max_element) + if (unlikely(array->elements == array->max_element)) { /* Call only when necessary */ if (!(buffer=alloc_dynamic(array))) return TRUE; @@ -102,7 +102,42 @@ my_bool insert_dynamic(DYNAMIC_ARRAY *array, const void * element) buffer=array->buffer+(array->elements * array->size_of_element); array->elements++; } - memcpy(buffer,element,(size_t) array->size_of_element); + memcpy(buffer, element, array->size_of_element); + return FALSE; +} + + +/* Fast version of appending to dynamic array */ + +void init_append_dynamic(DYNAMIC_ARRAY_APPEND *append, + DYNAMIC_ARRAY *array) +{ + append->array= array; + append->pos= array->buffer + array->elements * array->size_of_element; + append->end= array->buffer + array->max_element * array->size_of_element; +} + + +my_bool append_dynamic(DYNAMIC_ARRAY_APPEND *append, + const void *element) +{ + DYNAMIC_ARRAY *array= append->array; + size_t size_of_element= array->size_of_element; + if (unlikely(append->pos == append->end)) + { + void *buffer; + if (!(buffer=alloc_dynamic(array))) + return TRUE; + append->pos= (uchar*)buffer + size_of_element; + append->end= array->buffer + array->max_element * size_of_element; + memcpy(buffer, element, size_of_element); + } + else + { + array->elements++; + memcpy(append->pos, element, size_of_element); + append->pos+= size_of_element; + } return FALSE; } @@ -281,7 +316,7 @@ my_bool allocate_dynamic(DYNAMIC_ARRAY *array, size_t max_elements) void get_dynamic(DYNAMIC_ARRAY *array, void *element, size_t idx) { - if (idx >= array->elements) + if (unlikely(idx >= array->elements)) { DBUG_PRINT("warning",("To big array idx: %d, array size is %d", idx,array->elements)); @@ -306,7 +341,7 @@ void delete_dynamic(DYNAMIC_ARRAY *array) /* Just mark as empty if we are using a static buffer */ - if (!(array->malloc_flags & MY_INIT_BUFFER_USED) && array->buffer) + if (array->buffer && !(array->malloc_flags & MY_INIT_BUFFER_USED)) my_free(array->buffer); array->buffer= 0; diff --git a/sql/handler.cc b/sql/handler.cc index d409de8f298..0d66da589f2 100644 --- a/sql/handler.cc +++ b/sql/handler.cc @@ -6964,8 +6964,7 @@ check_result_t handler_rowid_filter_check(void *h_arg) extern "C" int handler_rowid_filter_is_active(void *h_arg) { - if (!h_arg) - return false; + DBUG_ASSERT(h_arg); handler *h= (handler*) h_arg; return h->rowid_filter_is_active; } diff --git a/sql/handler.h b/sql/handler.h index 8a16f8bbbea..0166c2526e1 100644 --- a/sql/handler.h +++ b/sql/handler.h @@ -4665,10 +4665,14 @@ public: DBUG_ASSERT(pushed_rowid_filter != NULL && save_pushed_rowid_filter == NULL); save_pushed_rowid_filter= pushed_rowid_filter; - if (rowid_filter_is_active) - save_rowid_filter_is_active= rowid_filter_is_active; + save_rowid_filter_is_active= rowid_filter_is_active; pushed_rowid_filter= NULL; - rowid_filter_is_active= false; + + if (rowid_filter_is_active) + { + rowid_filter_is_active= false; + rowid_filter_changed(); + } } virtual void enable_pushed_rowid_filter() @@ -4676,12 +4680,17 @@ public: DBUG_ASSERT(save_pushed_rowid_filter != NULL && pushed_rowid_filter == NULL); pushed_rowid_filter= save_pushed_rowid_filter; - if (save_rowid_filter_is_active) - rowid_filter_is_active= true; save_pushed_rowid_filter= NULL; + if (save_rowid_filter_is_active) + { + rowid_filter_is_active= true; + rowid_filter_changed(); + } } virtual bool rowid_filter_push(Rowid_filter *rowid_filter) { return true; } + /* Signal that rowid filter may have been enabled / disabled */ + virtual void rowid_filter_changed() {} /* Needed for partition / spider */ virtual TABLE_LIST *get_next_global_for_child() { return NULL; } diff --git a/sql/optimizer_defaults.h b/sql/optimizer_defaults.h index 26c54464219..a3c22d898cf 100644 --- a/sql/optimizer_defaults.h +++ b/sql/optimizer_defaults.h @@ -86,6 +86,13 @@ /* Rowid copy is usually just a single memcpy of a short string */ #define DEFAULT_ROWID_COPY_COST 0.000002653 +/* + Cost modifiers rowid_filter. These takes into account the overhead of + using and calling Rowid_filter_sorted_array::check() from the engine +*/ +#define ROWID_FILTER_PER_CHECK_MODIFIER 4 /* times key_copy_cost */ +#define ROWID_FILTER_PER_ELEMENT_MODIFIER 3 /* times rowid_compare_cost */ + /* Average disk seek time on a hard disk is 8-10 ms, which is also about the time to read a IO_SIZE (8192) block. diff --git a/sql/rowid_filter.cc b/sql/rowid_filter.cc index 4d6bf4ea98c..bf768218cff 100644 --- a/sql/rowid_filter.cc +++ b/sql/rowid_filter.cc @@ -19,6 +19,7 @@ #include "sql_class.h" #include "opt_range.h" #include "rowid_filter.h" +#include "optimizer_defaults.h" #include "sql_select.h" #include "opt_trace.h" @@ -127,8 +128,10 @@ void Range_rowid_filter_cost_info::init(Rowid_filter_container_type cont_type, cost_of_building_range_filter= build_cost(container_type); where_cost= tab->in_use->variables.optimizer_where_cost; - base_lookup_cost= tab->file->ROW_NEXT_FIND_COST; - rowid_compare_cost= tab->file->ROWID_COMPARE_COST; + base_lookup_cost= (ROWID_FILTER_PER_CHECK_MODIFIER * + tab->file->KEY_COPY_COST); + rowid_compare_cost= (ROWID_FILTER_PER_ELEMENT_MODIFIER * + tab->file->ROWID_COMPARE_COST); selectivity= est_elements/((double) table->stat_records()); gain= avg_access_and_eval_gain_per_row(container_type, tab->file->ROW_LOOKUP_COST); @@ -589,41 +592,40 @@ bool Range_rowid_filter::fill() file->pushed_idx_cond_keyno= MAX_KEY; file->in_range_check_pushed_down= false; - /* We're going to just read rowids / primary keys */ + /* We're going to just read rowids / clustered primary keys */ table->prepare_for_position(); - table->file->ha_start_keyread(quick->index); + file->ha_start_keyread(quick->index); if (quick->init() || quick->reset()) - rc= 1; + goto end; - while (!rc) + while (!(rc= quick->get_next())) { - rc= quick->get_next(); - if (thd->killed) - rc= 1; - if (!rc) + file->position(quick->record); + if (container->add(NULL, (char*) file->ref) || thd->killed) { - file->position(quick->record); - if (container->add(NULL, (char*) file->ref)) - rc= 1; - else - tracker->increment_container_elements_count(); + rc= 1; + break; } } +end: quick->range_end(); - table->file->ha_end_keyread(); + file->ha_end_keyread(); table->status= table_status_save; file->pushed_idx_cond= pushed_idx_cond_save; file->pushed_idx_cond_keyno= pushed_idx_cond_keyno_save; file->in_range_check_pushed_down= in_range_check_pushed_down_save; - tracker->report_container_buff_size(table->file->ref_length); + + tracker->set_container_elements_count(container->elements()); + tracker->report_container_buff_size(file->ref_length); if (rc != HA_ERR_END_OF_FILE) return 1; - table->file->rowid_filter_is_active= true; + container->sort(refpos_order_cmp, (void *) file); + file->rowid_filter_is_active= container->elements() != 0; return 0; } @@ -647,18 +649,13 @@ bool Range_rowid_filter::fill() bool Rowid_filter_sorted_array::check(void *ctxt, char *elem) { - TABLE *table= (TABLE *) ctxt; - if (!is_checked) - { - refpos_container.sort(refpos_order_cmp, (void *) (table->file)); - is_checked= true; - } + handler *file= ((TABLE *) ctxt)->file; int l= 0; int r= refpos_container.elements()-1; while (l <= r) { int m= (l + r) / 2; - int cmp= refpos_order_cmp((void *) (table->file), + int cmp= refpos_order_cmp((void *) file, refpos_container.get_pos(m), elem); if (cmp == 0) return true; @@ -675,14 +672,6 @@ Range_rowid_filter::~Range_rowid_filter() { delete container; container= 0; - if (select) - { - if (select->quick) - { - delete select->quick; - select->quick= 0; - } - delete select; - select= 0; - } + delete select; + select= 0; } diff --git a/sql/rowid_filter.h b/sql/rowid_filter.h index f761e1220aa..7c5b561107a 100644 --- a/sql/rowid_filter.h +++ b/sql/rowid_filter.h @@ -186,7 +186,10 @@ public: virtual bool check(void *ctxt, char *elem) = 0; /* True if the container does not contain any element */ - virtual bool is_empty() = 0; + bool is_empty() { return elements() == 0; } + virtual uint elements() = 0; + virtual void sort (int (*cmp) (void *ctxt, const void *el1, const void *el2), + void *cmp_arg) = 0; virtual ~Rowid_filter_container() {} }; @@ -264,7 +267,7 @@ public: bool build() { return fill(); } - bool check(char *elem) + bool check(char *elem) override { if (container->is_empty()) return false; @@ -296,52 +299,49 @@ class Refpos_container_sorted_array : public Sql_alloc /* Number of bytes allocated for an element */ uint elem_size; /* The dynamic array over which the wrapper is built */ - Dynamic_array *array; + DYNAMIC_ARRAY array; + DYNAMIC_ARRAY_APPEND append; public: Refpos_container_sorted_array(uint max_elems, uint elem_sz) - : max_elements(max_elems), elem_size(elem_sz), array(0) {} + :max_elements(max_elems), elem_size(elem_sz) + { + bzero(&array, sizeof(array)); + } ~Refpos_container_sorted_array() { - delete array; - array= 0; + delete_dynamic(&array); } bool alloc() { - array= new Dynamic_array (PSI_INSTRUMENT_MEM, - elem_size * max_elements, - elem_size * max_elements/sizeof(char) + 1); - return array == NULL; + /* This can never fail as things will be allocated on demand */ + init_dynamic_array2(PSI_INSTRUMENT_MEM, &array, elem_size, 0, + max_elements, 512, MYF(0)); + init_append_dynamic(&append, &array); + return 0; } - bool add(char *elem) + bool add(const char *elem) { - for (uint i= 0; i < elem_size; i++) - { - if (array->append(elem[i])) - return true; - } - return false; + return append_dynamic(&append, elem); } - char *get_pos(uint n) + inline uchar *get_pos(uint n) const { - return array->get_pos(n * elem_size); + return dynamic_array_ptr(&array, n); } - uint elements() { return (uint) (array->elements() / elem_size); } + inline uint elements() const { return (uint) array.elements; } void sort (int (*cmp) (void *ctxt, const void *el1, const void *el2), void *cmp_arg) { - my_qsort2(array->front(), array->elements()/elem_size, + my_qsort2(array.buffer, array.elements, elem_size, (qsort2_cmp) cmp, cmp_arg); } - - bool is_empty() { return elements() == 0; } }; @@ -356,23 +356,29 @@ class Rowid_filter_sorted_array: public Rowid_filter_container { /* The dynamic array to store rowids / primary keys */ Refpos_container_sorted_array refpos_container; - /* Initially false, becomes true after the first call of (check() */ - bool is_checked; public: Rowid_filter_sorted_array(uint elems, uint elem_size) - : refpos_container(elems, elem_size), is_checked(false) {} + : refpos_container(elems, elem_size) {} - Rowid_filter_container_type get_type() + Rowid_filter_container_type get_type() override { return SORTED_ARRAY_CONTAINER; } - bool alloc() { return refpos_container.alloc(); } + bool alloc() override { return refpos_container.alloc(); } - bool add(void *ctxt, char *elem) { return refpos_container.add(elem); } + bool add(void *ctxt, char *elem) override + { return refpos_container.add(elem); } - bool check(void *ctxt, char *elem); + bool check(void *ctxt, char *elem) override; + + uint elements() override { return refpos_container.elements(); } + + void sort (int (*cmp) (void *ctxt, const void *el1, const void *el2), + void *cmp_arg) + { + return refpos_container.sort(cmp, cmp_arg); + } - bool is_empty() { return refpos_container.is_empty(); } }; /** diff --git a/sql/sql_analyze_stmt.h b/sql/sql_analyze_stmt.h index 4136dff1e0c..8f60d4b523a 100644 --- a/sql/sql_analyze_stmt.h +++ b/sql/sql_analyze_stmt.h @@ -414,7 +414,8 @@ public: n_positive_checks++; } - inline void increment_container_elements_count() { container_elements++; } + inline void set_container_elements_count(uint elements) + { container_elements= elements; } uint get_container_elements() const { return container_elements; } diff --git a/sql/uniques.cc b/sql/uniques.cc index 1886ad278da..36725e80a6b 100644 --- a/sql/uniques.cc +++ b/sql/uniques.cc @@ -170,10 +170,9 @@ static double get_merge_buffers_cost(THD *thd, uint *buff_elems, uint elem_size, size_t n_buffers= last - first + 1; - /* Using log2(n)=log(n)/log(2) formula */ return (2*((double)total_buf_elems*elem_size) / IO_SIZE * default_optimizer_costs.disk_read_cost + - total_buf_elems*log((double) n_buffers) * compare_factor / M_LN2); + total_buf_elems*log2((double) n_buffers) * compare_factor); } diff --git a/storage/innobase/row/row0sel.cc b/storage/innobase/row/row0sel.cc index 13af09361be..fa7e129752a 100644 --- a/storage/innobase/row/row0sel.cc +++ b/storage/innobase/row/row0sel.cc @@ -4040,7 +4040,8 @@ row_search_idx_cond_check( ut_ad(rec_offs_validate(rec, prebuilt->index, offsets)); if (!prebuilt->idx_cond) { - if (!handler_rowid_filter_is_active(prebuilt->pk_filter)) { + if (!prebuilt->pk_filter || + !handler_rowid_filter_is_active(prebuilt->pk_filter)) { return(CHECK_POS); } } else { @@ -4082,7 +4083,8 @@ row_search_idx_cond_check( switch (result) { case CHECK_POS: - if (handler_rowid_filter_is_active(prebuilt->pk_filter)) { + if (prebuilt->pk_filter && + handler_rowid_filter_is_active(prebuilt->pk_filter)) { ut_ad(!prebuilt->index->is_primary()); if (prebuilt->clust_index_was_generated) { ulint len; diff --git a/storage/maria/ha_maria.cc b/storage/maria/ha_maria.cc index f8b72bf85d3..691edba8d55 100644 --- a/storage/maria/ha_maria.cc +++ b/storage/maria/ha_maria.cc @@ -1094,8 +1094,9 @@ ulong ha_maria::index_flags(uint inx, uint part, bool all_parts) const } else { - flags= HA_READ_NEXT | HA_READ_PREV | HA_READ_RANGE | - HA_READ_ORDER | HA_KEYREAD_ONLY | HA_DO_INDEX_COND_PUSHDOWN; + flags= (HA_READ_NEXT | HA_READ_PREV | HA_READ_RANGE | + HA_READ_ORDER | HA_KEYREAD_ONLY | HA_DO_INDEX_COND_PUSHDOWN | + HA_DO_RANGE_FILTER_PUSHDOWN); } return flags; } @@ -2535,10 +2536,12 @@ int ha_maria::index_read_idx_map(uchar * buf, uint index, const uchar * key, end_range= NULL; if (index == pushed_idx_cond_keyno) ma_set_index_cond_func(file, handler_index_cond_check, this); + if (pushed_rowid_filter && handler_rowid_filter_is_active(this)) + ma_set_rowid_filter_func(file, handler_rowid_filter_check, this); error= maria_rkey(file, buf, index, key, keypart_map, find_flag); - ma_set_index_cond_func(file, NULL, 0); + ma_reset_index_filter_functions(file); return error; } @@ -2612,18 +2615,22 @@ int ha_maria::index_next_same(uchar * buf, int ha_maria::index_init(uint idx, bool sorted) { - active_index=idx; + active_index= idx; if (pushed_idx_cond_keyno == idx) ma_set_index_cond_func(file, handler_index_cond_check, this); + if (pushed_rowid_filter && handler_rowid_filter_is_active(this)) + ma_set_rowid_filter_func(file, handler_rowid_filter_check, this); return 0; } - int ha_maria::index_end() { + /* + in_range_check_pushed_down and index_id_cond_keyno are reset in + handler::cancel_pushed_idx_cond() + */ active_index=MAX_KEY; - ma_set_index_cond_func(file, NULL, 0); - in_range_check_pushed_down= FALSE; + ma_reset_index_filter_functions(file); ds_mrr.dsmrr_close(); return 0; } @@ -2811,7 +2818,7 @@ int ha_maria::extra(enum ha_extra_function operation) int ha_maria::reset(void) { - ma_set_index_cond_func(file, NULL, 0); + ma_reset_index_filter_functions(file); ds_mrr.dsmrr_close(); if (file->trn) { @@ -3871,8 +3878,6 @@ bool ha_maria::is_changed() const static void aria_update_optimizer_costs(OPTIMIZER_COSTS *costs) { - costs->rowid_copy_cost= 0.000001; // Just a short memcopy - costs->rowid_cmp_cost= 0.000001; // Just a short memcmp } @@ -4269,6 +4274,26 @@ Item *ha_maria::idx_cond_push(uint keyno_arg, Item* idx_cond_arg) return NULL; } +bool ha_maria::rowid_filter_push(Rowid_filter* rowid_filter) +{ + /* This will be used in index_init() */ + pushed_rowid_filter= rowid_filter; + return false; +} + + +/* Enable / disable rowid filter depending if it's active or not */ + +void ha_maria::rowid_filter_changed() +{ + if (pushed_rowid_filter && handler_rowid_filter_is_active(this)) + ma_set_rowid_filter_func(file, handler_rowid_filter_check, this); + else + ma_set_rowid_filter_func(file, NULL, this); +} + + + /** Find record by unique constrain (used in temporary tables) diff --git a/storage/maria/ha_maria.h b/storage/maria/ha_maria.h index 1486c2d7904..bea913e424f 100644 --- a/storage/maria/ha_maria.h +++ b/storage/maria/ha_maria.h @@ -184,6 +184,8 @@ public: /* Index condition pushdown implementation */ Item *idx_cond_push(uint keyno, Item* idx_cond) override final; + bool rowid_filter_push(Rowid_filter* rowid_filter) override; + void rowid_filter_changed() override; int find_unique_row(uchar *record, uint unique_idx) override final; diff --git a/storage/maria/ma_extra.c b/storage/maria/ma_extra.c index 425cb421e22..087100e3d8c 100644 --- a/storage/maria/ma_extra.c +++ b/storage/maria/ma_extra.c @@ -510,8 +510,17 @@ void ma_set_index_cond_func(MARIA_HA *info, index_cond_func_t func, { info->index_cond_func= func; info->index_cond_func_arg= func_arg; + info->has_cond_pushdown= (info->index_cond_func || info->rowid_filter_func); } +void ma_set_rowid_filter_func(MARIA_HA *info, + rowid_filter_func_t check_func, + void *func_arg) +{ + info->rowid_filter_func= check_func; + info->rowid_filter_func_arg= func_arg; + info->has_cond_pushdown= (info->index_cond_func || info->rowid_filter_func); +} /* Start/Stop Inserting Duplicates Into a Table, WL#1648. diff --git a/storage/maria/ma_info.c b/storage/maria/ma_info.c index ddf92654be0..3de6b8b74c5 100644 --- a/storage/maria/ma_info.c +++ b/storage/maria/ma_info.c @@ -20,14 +20,6 @@ #include #endif - /* Get position to last record */ - -MARIA_RECORD_POS maria_position(MARIA_HA *info) -{ - return info->cur_row.lastpos; -} - - uint maria_max_key_length() { uint tmp= (_ma_max_key_length() - 8 - HA_MAX_KEY_SEG*3); diff --git a/storage/maria/ma_key.c b/storage/maria/ma_key.c index d47e8cf715a..1b58c1c12c8 100644 --- a/storage/maria/ma_key.c +++ b/storage/maria/ma_key.c @@ -678,22 +678,44 @@ int _ma_read_key_record(MARIA_HA *info, uchar *buf, MARIA_RECORD_POS filepos) CHECK_OUT_OF_RANGE to indicate that we don't have any active row. */ -check_result_t ma_check_index_cond(register MARIA_HA *info, uint keynr, - uchar *record) +check_result_t ma_check_index_cond_real(register MARIA_HA *info, uint keynr, + uchar *record) { check_result_t res= CHECK_POS; + DBUG_ASSERT(info->index_cond_func || info->rowid_filter_func); + + if (_ma_put_key_in_record(info, keynr, FALSE, record)) + { + /* Impossible case; Can only happen if bug in code */ + _ma_print_error(info, HA_ERR_CRASHED, 0); + info->cur_row.lastpos= HA_OFFSET_ERROR; /* No active record */ + my_errno= HA_ERR_CRASHED; + return CHECK_ERROR; + } + if (info->index_cond_func) { - if (_ma_put_key_in_record(info, keynr, FALSE, record)) + if ((res= info->index_cond_func(info->index_cond_func_arg)) == + CHECK_OUT_OF_RANGE) { - /* Impossible case; Can only happen if bug in code */ - _ma_print_error(info, HA_ERR_CRASHED, 0); + /* We got beyond the end of scanned range */ info->cur_row.lastpos= HA_OFFSET_ERROR; /* No active record */ - my_errno= HA_ERR_CRASHED; - res= CHECK_ERROR; + my_errno= HA_ERR_END_OF_FILE; + return res; } - else if ((res= info->index_cond_func(info->index_cond_func_arg)) == - CHECK_OUT_OF_RANGE) + /* + If we got an error, out-of-range condition, or ICP condition computed to + FALSE - we don't need to check the Rowid Filter. + */ + if (res != CHECK_POS) + return res; + } + + /* Check the Rowid Filter, if present */ + if (info->rowid_filter_func) + { + if ((res= info->rowid_filter_func(info->rowid_filter_func_arg)) == + CHECK_OUT_OF_RANGE) { /* We got beyond the end of scanned range */ info->cur_row.lastpos= HA_OFFSET_ERROR; /* No active record */ diff --git a/storage/maria/ma_rkey.c b/storage/maria/ma_rkey.c index 8cd82e1c6fc..7e43ed4befa 100644 --- a/storage/maria/ma_rkey.c +++ b/storage/maria/ma_rkey.c @@ -120,6 +120,7 @@ int maria_rkey(MARIA_HA *info, uchar *buf, int inx, const uchar *key_data, /* The key references a concurrently inserted record. */ if (search_flag == HA_READ_KEY_EXACT && + (keyinfo->flag & HA_NOSAME) && last_used_keyseg == keyinfo->seg + keyinfo->keysegs) { /* Simply ignore the key if it matches exactly. (Bug #29838) */ diff --git a/storage/maria/maria_def.h b/storage/maria/maria_def.h index 2ed4a3f502c..f17edfe0657 100644 --- a/storage/maria/maria_def.h +++ b/storage/maria/maria_def.h @@ -213,7 +213,6 @@ extern int maria_rsame_with_pos(MARIA_HA *file, uchar *record, extern int maria_update(MARIA_HA *file, const uchar *old, const uchar *new_record); extern int maria_write(MARIA_HA *file, const uchar *buff); -extern MARIA_RECORD_POS maria_position(MARIA_HA *file); extern int maria_status(MARIA_HA *info, MARIA_INFO *x, uint flag); extern int maria_lock_database(MARIA_HA *file, int lock_type); extern int maria_delete_table(const char *name); @@ -1011,6 +1010,7 @@ struct st_maria_handler my_bool switched_transactional; /* If transaction will autocommit */ my_bool autocommit; + my_bool has_cond_pushdown; #ifdef _WIN32 my_bool owned_by_merge; /* This Maria table is part of a merge union */ #endif @@ -1022,6 +1022,8 @@ struct st_maria_handler my_bool create_unique_index_by_sort; index_cond_func_t index_cond_func; /* Index condition function */ void *index_cond_func_arg; /* parameter for the func */ + rowid_filter_func_t rowid_filter_func; /* rowid filter check function */ + void *rowid_filter_func_arg; /* parameter for the func */ }; /* Table options for the Aria and S3 storage engine */ @@ -1347,7 +1349,11 @@ extern int _ma_read_rnd_no_record(MARIA_HA *info, uchar *buf, MARIA_RECORD_POS filepos, my_bool skip_deleted_blocks); my_off_t _ma_no_keypos_to_recpos(MARIA_SHARE *share, my_off_t pos); - +/* Get position to last record */ +static inline MARIA_RECORD_POS maria_position(MARIA_HA *info) +{ + return info->cur_row.lastpos; +} extern my_bool _ma_ck_write(MARIA_HA *info, MARIA_KEY *key); extern my_bool _ma_enlarge_root(MARIA_HA *info, MARIA_KEY *key, MARIA_RECORD_POS *root); @@ -1734,7 +1740,25 @@ extern my_bool maria_flush_log_for_page_none(PAGECACHE_IO_HOOK_ARGS *args); extern PAGECACHE *maria_log_pagecache; extern void ma_set_index_cond_func(MARIA_HA *info, index_cond_func_t func, void *func_arg); -check_result_t ma_check_index_cond(MARIA_HA *info, uint keynr, uchar *record); +extern void ma_set_rowid_filter_func(MARIA_HA *info, + rowid_filter_func_t check_func, + void *func_arg); +static inline void ma_reset_index_filter_functions(MARIA_HA *info) +{ + info->index_cond_func= NULL; + info->rowid_filter_func= NULL; + info->has_cond_pushdown= 0; +} +check_result_t ma_check_index_cond_real(MARIA_HA *info, uint keynr, + uchar *record); +static inline check_result_t ma_check_index_cond(MARIA_HA *info, uint keynr, + uchar *record) +{ + if (!info->has_cond_pushdown) + return CHECK_POS; + return ma_check_index_cond_real(info, keynr, record); +} + extern my_bool ma_yield_and_check_if_killed(MARIA_HA *info, int inx); extern my_bool ma_killed_standalone(MARIA_HA *); diff --git a/storage/myisam/ha_myisam.cc b/storage/myisam/ha_myisam.cc index df47bda9c86..bd6cfe0c3bc 100644 --- a/storage/myisam/ha_myisam.cc +++ b/storage/myisam/ha_myisam.cc @@ -1971,9 +1971,8 @@ int ha_myisam::index_init(uint idx, bool sorted) active_index=idx; if (pushed_idx_cond_keyno == idx) mi_set_index_cond_func(file, handler_index_cond_check, this); - if (pushed_rowid_filter) - mi_set_rowid_filter_func(file, handler_rowid_filter_check, - handler_rowid_filter_is_active, this); + if (pushed_rowid_filter && handler_rowid_filter_is_active(this)) + mi_set_rowid_filter_func(file, handler_rowid_filter_check, this); return 0; } @@ -1981,11 +1980,10 @@ int ha_myisam::index_init(uint idx, bool sorted) int ha_myisam::index_end() { DBUG_ENTER("ha_myisam::index_end"); - active_index=MAX_KEY; - //pushed_idx_cond_keyno= MAX_KEY; + active_index= MAX_KEY; mi_set_index_cond_func(file, NULL, 0); in_range_check_pushed_down= FALSE; - mi_set_rowid_filter_func(file, NULL, NULL, 0); + mi_set_rowid_filter_func(file, NULL, 0); ds_mrr.dsmrr_close(); #if !defined(DBUG_OFF) && defined(SQL_SELECT_FIXED_FOR_UPDATE) file->update&= ~HA_STATE_AKTIV; // Forget active row @@ -2021,9 +2019,8 @@ int ha_myisam::index_read_idx_map(uchar *buf, uint index, const uchar *key, end_range= NULL; if (index == pushed_idx_cond_keyno) mi_set_index_cond_func(file, handler_index_cond_check, this); - if (pushed_rowid_filter) - mi_set_rowid_filter_func(file, handler_rowid_filter_check, - handler_rowid_filter_is_active, this); + if (pushed_rowid_filter && handler_rowid_filter_is_active(this)) + mi_set_rowid_filter_func(file, handler_rowid_filter_check, this); res= mi_rkey(file, buf, index, key, keypart_map, find_flag); mi_set_index_cond_func(file, NULL, 0); return res; @@ -2728,12 +2725,23 @@ Item *ha_myisam::idx_cond_push(uint keyno_arg, Item* idx_cond_arg) bool ha_myisam::rowid_filter_push(Rowid_filter* rowid_filter) { + /* This will be used in index_init() */ pushed_rowid_filter= rowid_filter; - mi_set_rowid_filter_func(file, handler_rowid_filter_check, - handler_rowid_filter_is_active, this); return false; } + +/* Enable / disable rowid filter depending if it's active or not */ + +void ha_myisam::rowid_filter_changed() +{ + if (pushed_rowid_filter && handler_rowid_filter_is_active(this)) + mi_set_rowid_filter_func(file, handler_rowid_filter_check, this); + else + mi_set_rowid_filter_func(file, NULL, this); +} + + struct st_mysql_storage_engine myisam_storage_engine= { MYSQL_HANDLERTON_INTERFACE_VERSION }; diff --git a/storage/myisam/ha_myisam.h b/storage/myisam/ha_myisam.h index d6ae007a446..0bea4938eb5 100644 --- a/storage/myisam/ha_myisam.h +++ b/storage/myisam/ha_myisam.h @@ -173,8 +173,9 @@ public: int multi_range_read_explain_info(uint mrr_mode, char *str, size_t size); /* Index condition pushdown implementation */ - Item *idx_cond_push(uint keyno, Item* idx_cond); - bool rowid_filter_push(Rowid_filter* rowid_filter); + Item *idx_cond_push(uint keyno, Item* idx_cond) override; + bool rowid_filter_push(Rowid_filter* rowid_filter) override; + void rowid_filter_changed() override; private: DsMrr_impl ds_mrr; diff --git a/storage/myisam/mi_extra.c b/storage/myisam/mi_extra.c index 66238745a04..e7e64edd926 100644 --- a/storage/myisam/mi_extra.c +++ b/storage/myisam/mi_extra.c @@ -376,16 +376,16 @@ void mi_set_index_cond_func(MI_INFO *info, index_cond_func_t func, { info->index_cond_func= func; info->index_cond_func_arg= func_arg; + info->has_cond_pushdown= (info->index_cond_func || info->rowid_filter_func); } void mi_set_rowid_filter_func(MI_INFO *info, rowid_filter_func_t check_func, - rowid_filter_is_active_func_t is_active_func, void *func_arg) { info->rowid_filter_func= check_func; - info->rowid_filter_is_active_func= is_active_func; info->rowid_filter_func_arg= func_arg; + info->has_cond_pushdown= (info->index_cond_func || info->rowid_filter_func); } /* diff --git a/storage/myisam/mi_key.c b/storage/myisam/mi_key.c index 087eb59c7c0..bde3ee19e2c 100644 --- a/storage/myisam/mi_key.c +++ b/storage/myisam/mi_key.c @@ -510,14 +510,6 @@ int mi_unpack_index_tuple(MI_INFO *info, uint keynr, uchar *record) } -static int mi_check_rowid_filter_is_active(MI_INFO *info) -{ - if (info->rowid_filter_is_active_func == NULL) - return 0; - return info->rowid_filter_is_active_func(info->rowid_filter_func_arg); -} - - /* Check the current index tuple: Check ICP condition and/or Rowid Filter @@ -532,21 +524,23 @@ static int mi_check_rowid_filter_is_active(MI_INFO *info) Check result according to check_result_t definition */ -check_result_t mi_check_index_tuple(MI_INFO *info, uint keynr, uchar *record) +check_result_t mi_check_index_tuple_real(MI_INFO *info, uint keynr, uchar *record) { - int need_unpack= TRUE; check_result_t res= CHECK_POS; + DBUG_ASSERT(info->index_cond_func || info->rowid_filter_func); + + if (mi_unpack_index_tuple(info, keynr, record)) + return CHECK_ERROR; if (info->index_cond_func) { - if (mi_unpack_index_tuple(info, keynr, record)) - res= CHECK_ERROR; - else if ((res= info->index_cond_func(info->index_cond_func_arg)) == - CHECK_OUT_OF_RANGE) + if ((res= info->index_cond_func(info->index_cond_func_arg)) == + CHECK_OUT_OF_RANGE) { /* We got beyond the end of scanned range */ info->lastpos= HA_OFFSET_ERROR; /* No active record */ my_errno= HA_ERR_END_OF_FILE; + return res; } /* @@ -555,25 +549,17 @@ check_result_t mi_check_index_tuple(MI_INFO *info, uint keynr, uchar *record) */ if (res != CHECK_POS) return res; - - need_unpack= FALSE; } /* Check the Rowid Filter, if present */ - if (mi_check_rowid_filter_is_active(info)) + if (info->rowid_filter_func) { - /* Unpack the index tuple if we haven't done it already */ - if (need_unpack && mi_unpack_index_tuple(info, keynr, record)) - res= CHECK_ERROR; - else + if ((res= info->rowid_filter_func(info->rowid_filter_func_arg)) == + CHECK_OUT_OF_RANGE) { - if ((res= info->rowid_filter_func(info->rowid_filter_func_arg)) == - CHECK_OUT_OF_RANGE) - { - /* We got beyond the end of scanned range */ - info->lastpos= HA_OFFSET_ERROR; /* No active record */ - my_errno= HA_ERR_END_OF_FILE; - } + /* We got beyond the end of scanned range */ + info->lastpos= HA_OFFSET_ERROR; /* No active record */ + my_errno= HA_ERR_END_OF_FILE; } } return res; diff --git a/storage/myisam/mi_rkey.c b/storage/myisam/mi_rkey.c index bf6f3ef852c..590981fb790 100644 --- a/storage/myisam/mi_rkey.c +++ b/storage/myisam/mi_rkey.c @@ -119,7 +119,7 @@ int mi_rkey(MI_INFO *info, uchar *buf, int inx, const uchar *key, while ((info->lastpos >= info->state->data_file_length && (search_flag != HA_READ_KEY_EXACT || last_used_keyseg != keyinfo->seg + keyinfo->keysegs)) || - (res= mi_check_index_tuple(info, inx, buf)) == CHECK_NEG) + (res= mi_check_index_tuple(info, inx, buf)) == CHECK_NEG) { uint not_used[2]; /* diff --git a/storage/myisam/myisamdef.h b/storage/myisam/myisamdef.h index c90d989c975..5ede6a6159c 100644 --- a/storage/myisam/myisamdef.h +++ b/storage/myisam/myisamdef.h @@ -304,10 +304,10 @@ struct st_myisam_info /* If info->buff has to be reread for rnext */ my_bool buff_used; my_bool create_unique_index_by_sort; + my_bool has_cond_pushdown; index_cond_func_t index_cond_func; /* Index condition function */ void *index_cond_func_arg; /* parameter for the func */ rowid_filter_func_t rowid_filter_func; /* rowid filter check function */ - rowid_filter_is_active_func_t rowid_filter_is_active_func; /* is activefunction */ void *rowid_filter_func_arg; /* parameter for the func */ THR_LOCK_DATA lock; uchar *rtree_recursion_state; /* For RTREE */ @@ -742,7 +742,15 @@ my_bool mi_dynmap_file(MI_INFO *info, my_off_t size); int mi_munmap_file(MI_INFO *info); void mi_remap_file(MI_INFO *info, my_off_t size); -check_result_t mi_check_index_tuple(MI_INFO *info, uint keynr, uchar *record); +check_result_t mi_check_index_tuple_real(MI_INFO *info, uint keynr, + uchar *record); +static inline check_result_t mi_check_index_tuple(MI_INFO *info, uint keynr, + uchar *record) +{ + if (!info->has_cond_pushdown && ! info->rowid_filter_func) + return CHECK_POS; + return mi_check_index_tuple_real(info, keynr, record); +} /* Functions needed by mi_check */ int killed_ptr(HA_CHECK *param); @@ -754,7 +762,6 @@ extern void mi_set_index_cond_func(MI_INFO *info, index_cond_func_t check_func, void *func_arg); extern void mi_set_rowid_filter_func(MI_INFO *info, rowid_filter_func_t check_func, - rowid_filter_is_active_func_t is_active_func, void *func_arg); int flush_blocks(HA_CHECK *param, KEY_CACHE *key_cache, File file, ulonglong *dirty_part_map);