planner/core: use constant propagate before predicates push down (#21061)

This commit is contained in:
欧冰
2020-12-08 16:32:32 +08:00
committed by GitHub
parent b269ef89d9
commit 03f385de5f
9 changed files with 75 additions and 55 deletions

View File

@ -425,10 +425,10 @@ IndexReader_6 10.00 root index:IndexRangeScan_5
└─IndexRangeScan_5 10.00 cop[tikv] table:t, index:idx(a, b) range:[1,1], keep order:false, stats:pseudo
explain select * from t where a = 1 and a = 2;
id estRows task access object operator info
TableDual_5 0.00 root rows:0
TableDual_5 8000.00 root rows:0
explain select * from t where b = 1 and b = 2;
id estRows task access object operator info
TableDual_5 0.00 root rows:0
TableDual_5 8000.00 root rows:0
explain select * from t t1 join t t2 where t1.b = t2.b and t2.b is null;
id estRows task access object operator info
Projection_7 0.00 root test.t.a, test.t.b, test.t.a, test.t.b
@ -450,7 +450,7 @@ drop table if exists t;
create table t(a bigint primary key);
explain select * from t where a = 1 and a = 2;
id estRows task access object operator info
TableDual_5 0.00 root rows:0
TableDual_5 8000.00 root rows:0
explain select null or a > 1 from t;
id estRows task access object operator info
Projection_3 10000.00 root or(<nil>, gt(test.t.a, 1))->Column#2
@ -498,18 +498,17 @@ PRIMARY KEY (`id`)
EXPLAIN SELECT COUNT(1) FROM (SELECT COALESCE(b.region_name, '不详') region_name, SUM(a.registration_num) registration_num FROM (SELECT stat_date, show_date, region_id, 0 registration_num FROM test01 WHERE period = 1 AND stat_date >= 20191202 AND stat_date <= 20191202 UNION ALL SELECT stat_date, show_date, region_id, registration_num registration_num FROM test01 WHERE period = 1 AND stat_date >= 20191202 AND stat_date <= 20191202) a LEFT JOIN test02 b ON a.region_id = b.id WHERE registration_num > 0 AND a.stat_date >= '20191202' AND a.stat_date <= '20191202' GROUP BY a.stat_date , a.show_date , COALESCE(b.region_name, '不详') ) JLS;
id estRows task access object operator info
StreamAgg_22 1.00 root funcs:count(1)->Column#22
└─HashAgg_25 1.00 root group by:Column#32, Column#33, Column#34, funcs:firstrow(1)->Column#31
└─Projection_46 0.01 root Column#14, Column#15, coalesce(test.test02.region_name, 不详)->Column#34
└─IndexMergeJoin_34 0.01 root left outer join, inner:TableReader_29, outer key:Column#16, inner key:test.test02.id
├─Union_37(Build) 0.01 root
├─Projection_38 0.00 root test.test01.stat_date, test.test01.show_date, test.test01.region_id
│ │ └─TableDual_39 0.00 root rows:0
│ └─Projection_40 0.01 root test.test01.stat_date, test.test01.show_date, test.test01.region_id
└─TableReader_43 0.01 root data:Selection_42
└─Selection_42 0.01 cop[tikv] eq(test.test01.period, 1), ge(test.test01.stat_date, 20191202), ge(test.test01.stat_date, 20191202), gt(cast(test.test01.registration_num), 0), le(test.test01.stat_date, 20191202), le(test.test01.stat_date, 20191202)
└─TableFullScan_41 10000.00 cop[tikv] table:test01 keep order:false, stats:pseudo
└─TableReader_29(Probe) 1.00 root data:TableRangeScan_28
└─TableRangeScan_28 1.00 cop[tikv] table:b range: decided by [Column#16], keep order:true, stats:pseudo
└─HashAgg_48 8000.00 root group by:Column#32, Column#33, Column#34, funcs:firstrow(1)->Column#31
└─Projection_49 10000.01 root Column#14, Column#15, coalesce(test.test02.region_name, 不详)->Column#34
└─HashJoin_35 10000.01 root left outer join, equal:[eq(Column#16, test.test02.id)]
├─TableReader_45(Build) 10000.00 root data:TableFullScan_44
└─TableFullScan_44 10000.00 cop[tikv] table:b keep order:false, stats:pseudo
└─Union_37(Probe) 8000.01 root
├─TableDual_39 8000.00 root rows:0
└─Projection_40 0.01 root test.test01.stat_date, test.test01.show_date, test.test01.region_id
└─TableReader_43 0.01 root data:Selection_42
└─Selection_42 0.01 cop[tikv] eq(test.test01.period, 1), ge(test.test01.stat_date, 20191202), ge(test.test01.stat_date, 20191202), gt(cast(test.test01.registration_num), 0), le(test.test01.stat_date, 20191202), le(test.test01.stat_date, 20191202)
└─TableFullScan_41 10000.00 cop[tikv] table:test01 keep order:false, stats:pseudo
drop table if exists t;
create table t(a int, nb int not null, nc int not null);
explain select ifnull(a, 0) from t;

View File

@ -110,7 +110,7 @@
"Result": [
"HashJoin_6 100000.00 root CARTESIAN left outer join, other cond:gt(test.t1.a, test.t2.a)",
"├─TableReader_12(Build) 10.00 root data:Selection_11",
"│ └─Selection_11 10.00 cop[tikv] eq(test.t2.a, 1), not(isnull(test.t2.a))",
"│ └─Selection_11 10.00 cop[tikv] eq(test.t2.a, 1)",
"│ └─TableFullScan_10 10000.00 cop[tikv] table:t2 keep order:false, stats:pseudo",
"└─TableReader_9(Probe) 10000.00 root data:TableFullScan_8",
" └─TableFullScan_8 10000.00 cop[tikv] table:t1 keep order:false, stats:pseudo"
@ -121,7 +121,7 @@
"Result": [
"HashJoin_6 100000.00 root CARTESIAN right outer join, other cond:gt(test.t1.a, test.t2.a)",
"├─TableReader_10(Build) 10.00 root data:Selection_9",
"│ └─Selection_9 10.00 cop[tikv] eq(test.t1.a, 1), not(isnull(test.t1.a))",
"│ └─Selection_9 10.00 cop[tikv] eq(test.t1.a, 1)",
"│ └─TableFullScan_8 10000.00 cop[tikv] table:t1 keep order:false, stats:pseudo",
"└─TableReader_12(Probe) 10000.00 root data:TableFullScan_11",
" └─TableFullScan_11 10000.00 cop[tikv] table:t2 keep order:false, stats:pseudo"
@ -151,9 +151,9 @@
{
"SQL": "explain select * from t1 left join t2 on t2.a = t2.b and t2.a > 1",
"Result": [
"HashJoin_6 26666666.67 root CARTESIAN left outer join",
"├─TableReader_12(Build) 2666.67 root data:Selection_11",
"│ └─Selection_11 2666.67 cop[tikv] eq(test.t2.a, test.t2.b), gt(test.t2.a, 1)",
"HashJoin_6 8888888.89 root CARTESIAN left outer join",
"├─TableReader_12(Build) 888.89 root data:Selection_11",
"│ └─Selection_11 888.89 cop[tikv] eq(test.t2.a, test.t2.b), gt(test.t2.a, 1), gt(test.t2.b, 1)",
"│ └─TableFullScan_10 10000.00 cop[tikv] table:t2 keep order:false, stats:pseudo",
"└─TableReader_9(Probe) 10000.00 root data:TableFullScan_8",
" └─TableFullScan_8 10000.00 cop[tikv] table:t1 keep order:false, stats:pseudo"
@ -234,10 +234,8 @@
{
"SQL": "explain select * from t1 left join t2 on t2.a = 1 and t2.a = 2",
"Result": [
"HashJoin_6 10000.00 root CARTESIAN left outer join",
"├─TableReader_12(Build) 0.00 root data:Selection_11",
"│ └─Selection_11 0.00 cop[tikv] eq(test.t2.a, 1), eq(test.t2.a, 2)",
"│ └─TableFullScan_10 10000.00 cop[tikv] table:t2 keep order:false, stats:pseudo",
"HashJoin_6 80000000.00 root CARTESIAN left outer join",
"├─TableDual_10(Build) 8000.00 root rows:0",
"└─TableReader_9(Probe) 10000.00 root data:TableFullScan_8",
" └─TableFullScan_8 10000.00 cop[tikv] table:t1 keep order:false, stats:pseudo"
]

View File

@ -296,7 +296,7 @@
],
"Plan": [
"TableReader_7 0.01 root partition:p0,p1 data:Selection_6",
"└─Selection_6 0.01 cop[tikv] or(and(and(eq(test_partition.t2.id, 1), eq(test_partition.t2.a, 1)), eq(test_partition.t2.b, 1)), and(isnull(test_partition.t2.a), isnull(test_partition.t2.b)))",
"└─Selection_6 0.01 cop[tikv] or(and(eq(test_partition.t2.id, 1), and(eq(test_partition.t2.a, 1), eq(test_partition.t2.b, 1))), and(isnull(test_partition.t2.a), isnull(test_partition.t2.b)))",
" └─TableFullScan_5 10000.00 cop[tikv] table:t2 keep order:false, stats:pseudo"
]
},
@ -330,7 +330,7 @@
],
"Plan": [
"TableReader_7 0.00 root partition:p0 data:Selection_6",
"└─Selection_6 0.00 cop[tikv] or(and(and(eq(test_partition.t2.id, 1), eq(test_partition.t2.a, 1)), eq(test_partition.t2.b, 1)), and(and(eq(test_partition.t2.a, 1), eq(test_partition.t2.id, 1)), eq(test_partition.t2.b, 1)))",
"└─Selection_6 0.00 cop[tikv] or(and(eq(test_partition.t2.id, 1), and(eq(test_partition.t2.a, 1), eq(test_partition.t2.b, 1))), and(eq(test_partition.t2.a, 1), and(eq(test_partition.t2.id, 1), eq(test_partition.t2.b, 1))))",
" └─TableFullScan_5 10000.00 cop[tikv] table:t2 keep order:false, stats:pseudo"
]
},
@ -382,8 +382,8 @@
"SQL": "select * from t1 where a=id and id >10",
"Result": null,
"Plan": [
"TableReader_7 2666.67 root partition:all data:Selection_6",
"└─Selection_6 2666.67 cop[tikv] eq(test_partition.t1.a, test_partition.t1.id), gt(test_partition.t1.id, 10)",
"TableReader_7 888.89 root partition:all data:Selection_6",
"└─Selection_6 888.89 cop[tikv] eq(test_partition.t1.a, test_partition.t1.id), gt(test_partition.t1.a, 10), gt(test_partition.t1.id, 10)",
" └─TableFullScan_5 10000.00 cop[tikv] table:t1 keep order:false, stats:pseudo"
]
},
@ -391,8 +391,8 @@
"SQL": "select * from t2 where a=id and id >10",
"Result": null,
"Plan": [
"TableReader_7 2666.67 root partition:all data:Selection_6",
"└─Selection_6 2666.67 cop[tikv] eq(test_partition.t2.a, test_partition.t2.id), gt(test_partition.t2.id, 10)",
"TableReader_7 888.89 root partition:all data:Selection_6",
"└─Selection_6 888.89 cop[tikv] eq(test_partition.t2.a, test_partition.t2.id), gt(test_partition.t2.a, 10), gt(test_partition.t2.id, 10)",
" └─TableFullScan_5 10000.00 cop[tikv] table:t2 keep order:false, stats:pseudo"
]
},
@ -400,8 +400,8 @@
"SQL": "select * from t3 where a=id and id >10",
"Result": null,
"Plan": [
"TableReader_7 2666.67 root partition:all data:Selection_6",
"└─Selection_6 2666.67 cop[tikv] eq(test_partition.t3.a, test_partition.t3.id), gt(test_partition.t3.id, 10)",
"TableReader_7 888.89 root partition:all data:Selection_6",
"└─Selection_6 888.89 cop[tikv] eq(test_partition.t3.a, test_partition.t3.id), gt(test_partition.t3.a, 10), gt(test_partition.t3.id, 10)",
" └─TableFullScan_5 10000.00 cop[tikv] table:t3 keep order:false, stats:pseudo"
]
},
@ -411,8 +411,8 @@
"<nil> <nil> <nil>"
],
"Plan": [
"TableReader_7 2674.00 root partition:all data:Selection_6",
"└─Selection_6 2674.00 cop[tikv] or(and(eq(test_partition.t1.a, test_partition.t1.id), gt(test_partition.t1.id, 10)), isnull(test_partition.t1.a))",
"TableReader_7 898.00 root partition:all data:Selection_6",
"└─Selection_6 898.00 cop[tikv] or(and(eq(test_partition.t1.a, test_partition.t1.id), and(gt(test_partition.t1.id, 10), gt(test_partition.t1.a, 10))), isnull(test_partition.t1.a))",
" └─TableFullScan_5 10000.00 cop[tikv] table:t1 keep order:false, stats:pseudo"
]
},
@ -422,8 +422,8 @@
"<nil> <nil> <nil>"
],
"Plan": [
"TableReader_7 2674.00 root partition:all data:Selection_6",
"└─Selection_6 2674.00 cop[tikv] or(and(eq(test_partition.t2.a, test_partition.t2.id), gt(test_partition.t2.id, 10)), isnull(test_partition.t2.a))",
"TableReader_7 898.00 root partition:all data:Selection_6",
"└─Selection_6 898.00 cop[tikv] or(and(eq(test_partition.t2.a, test_partition.t2.id), and(gt(test_partition.t2.id, 10), gt(test_partition.t2.a, 10))), isnull(test_partition.t2.a))",
" └─TableFullScan_5 10000.00 cop[tikv] table:t2 keep order:false, stats:pseudo"
]
},
@ -433,8 +433,8 @@
"<nil> <nil> <nil>"
],
"Plan": [
"TableReader_7 2674.00 root partition:all data:Selection_6",
"└─Selection_6 2674.00 cop[tikv] or(and(eq(test_partition.t3.a, test_partition.t3.id), gt(test_partition.t3.id, 10)), isnull(test_partition.t3.a))",
"TableReader_7 898.00 root partition:all data:Selection_6",
"└─Selection_6 898.00 cop[tikv] or(and(eq(test_partition.t3.a, test_partition.t3.id), and(gt(test_partition.t3.id, 10), gt(test_partition.t3.a, 10))), isnull(test_partition.t3.a))",
" └─TableFullScan_5 10000.00 cop[tikv] table:t3 keep order:false, stats:pseudo"
]
},

View File

@ -1266,19 +1266,17 @@ func (s *testIntegrationSerialSuite) TestIndexMerge(c *C) {
tk.MustExec("drop table if exists t")
tk.MustExec("create table t (a int, b int, unique key(a), unique key(b))")
tk.MustQuery("desc select /*+ use_index_merge(t) */ * from t where a =1 or (b=1 and b+2>1)").Check(testkit.Rows(
"Projection_4 1.80 root test.t.a, test.t.b",
"└─IndexMerge_9 2.00 root ",
" ├─IndexRangeScan_5(Build) 1.00 cop[tikv] table:t, index:a(a) range:[1,1], keep order:false, stats:pseudo",
" ├─Selection_7(Build) 0.80 cop[tikv] gt(plus(test.t.b, 2), 1)",
" │ └─IndexRangeScan_6 1.00 cop[tikv] table:t, index:b(b) range:[1,1], keep order:false, stats:pseudo",
" └─TableRowIDScan_8(Probe) 2.00 cop[tikv] table:t keep order:false, stats:pseudo"))
tk.MustQuery("show warnings").Check(testkit.Rows())
"TableReader_7 8000.00 root data:Selection_6",
"└─Selection_6 8000.00 cop[tikv] or(eq(test.t.a, 1), and(eq(test.t.b, 1), 1))",
" └─TableFullScan_5 10000.00 cop[tikv] table:t keep order:false, stats:pseudo",
))
tk.MustQuery("show warnings").Check(testkit.Rows("Warning 1105 IndexMerge is inapplicable or disabled"))
tk.MustQuery("desc select /*+ use_index_merge(t) */ * from t where a =1 or (b=1 and length(b)=1)").Check(testkit.Rows(
"Projection_4 1.80 root test.t.a, test.t.b",
"└─IndexMerge_9 2.00 root ",
" ├─IndexRangeScan_5(Build) 1.00 cop[tikv] table:t, index:a(a) range:[1,1], keep order:false, stats:pseudo",
" ├─Selection_7(Build) 0.80 cop[tikv] eq(length(cast(test.t.b)), 1)",
" ├─Selection_7(Build) 0.80 cop[tikv] eq(length(cast(1)), 1)",
" │ └─IndexRangeScan_6 1.00 cop[tikv] table:t, index:b(b) range:[1,1], keep order:false, stats:pseudo",
" └─TableRowIDScan_8(Probe) 2.00 cop[tikv] table:t keep order:false, stats:pseudo"))
tk.MustQuery("show warnings").Check(testkit.Rows())
@ -1286,9 +1284,9 @@ func (s *testIntegrationSerialSuite) TestIndexMerge(c *C) {
tk.MustQuery("desc select /*+ use_index_merge(t) */ * from t where (a=1 and length(a)=1) or (b=1 and length(b)=1)").Check(testkit.Rows(
"Projection_4 1.60 root test.t.a, test.t.b",
"└─IndexMerge_10 2.00 root ",
" ├─Selection_6(Build) 0.80 cop[tikv] eq(length(cast(test.t.a)), 1)",
" ├─Selection_6(Build) 0.80 cop[tikv] eq(length(cast(1)), 1)",
" │ └─IndexRangeScan_5 1.00 cop[tikv] table:t, index:a(a) range:[1,1], keep order:false, stats:pseudo",
" ├─Selection_8(Build) 0.80 cop[tikv] eq(length(cast(test.t.b)), 1)",
" ├─Selection_8(Build) 0.80 cop[tikv] eq(length(cast(1)), 1)",
" │ └─IndexRangeScan_7 1.00 cop[tikv] table:t, index:b(b) range:[1,1], keep order:false, stats:pseudo",
" └─TableRowIDScan_9(Probe) 2.00 cop[tikv] table:t keep order:false, stats:pseudo"))
tk.MustQuery("show warnings").Check(testkit.Rows())
@ -1834,7 +1832,33 @@ func (s *testIntegrationSuite) TestPartitionUnionWithPPruningColumn(c *C) {
"2890 LE1300_r5",
"3150 LE1323_r5",
"3290 LE1327_r5"))
}
func (s *testIntegrationSuite) TestIssue20139(c *C) {
tk := testkit.NewTestKit(c, s.store)
tk.MustExec("use test")
tk.MustExec("drop table if exists t")
tk.MustExec("create table t (id int, c int) partition by range (id) (partition p0 values less than (4), partition p1 values less than (7))")
tk.MustExec("insert into t values(3, 3), (5, 5)")
plan := tk.MustQuery("explain select * from t where c = 1 and id = c")
plan.Check(testkit.Rows(
"TableReader_7 0.01 root partition:p0 data:Selection_6",
"└─Selection_6 0.01 cop[tikv] eq(test.t.c, 1), eq(test.t.id, 1)",
" └─TableFullScan_5 10000.00 cop[tikv] table:t keep order:false, stats:pseudo",
))
tk.MustExec("drop table t")
}
func (s *testIntegrationSuite) TestIssue14481(c *C) {
tk := testkit.NewTestKit(c, s.store)
tk.MustExec("use test")
tk.MustExec("drop table if exists t")
tk.MustExec("create table t(a int default null, b int default null, c int default null)")
plan := tk.MustQuery("explain select * from t where a = 1 and a = 2")
plan.Check(testkit.Rows("TableDual_5 8000.00 root rows:0"))
tk.MustExec("drop table t")
}
func (s *testIntegrationSerialSuite) TestIssue20710(c *C) {

View File

@ -99,6 +99,7 @@ func (p *LogicalUnionScan) PredicatePushDown(predicates []expression.Expression)
// PredicatePushDown implements LogicalPlan PredicatePushDown interface.
func (ds *DataSource) PredicatePushDown(predicates []expression.Expression) ([]expression.Expression, LogicalPlan) {
predicates = expression.PropagateConstant(ds.ctx, predicates)
ds.allConds = predicates
ds.pushedDownConds, predicates = expression.PushDownExprs(ds.ctx.GetSessionVars().StmtCtx, predicates, ds.ctx.GetClient(), kv.UnSpecified)
return predicates, ds

View File

@ -285,7 +285,7 @@
"SQL": "explain select /*+ USE_INDEX_MERGE(t, a, b, c) */ * from t where 1 or t.a = 1 or t.b = 2",
"Plan": [
"TableReader_7 8000.40 root data:Selection_6",
"└─Selection_6 8000.40 cop[tikv] or(or(1, eq(test.t.a, 1)), eq(test.t.b, 2))",
"└─Selection_6 8000.40 cop[tikv] or(1, or(eq(test.t.a, 1), eq(test.t.b, 2)))",
" └─TableFullScan_5 10000.00 cop[tikv] table:t keep order:false, stats:pseudo"
]
}

View File

@ -935,7 +935,7 @@
},
{
"Left": "[]",
"Right": "[or(or(eq(test.t.a, 3), eq(test.t.a, 4)), eq(test.t.a, 2))]"
"Right": "[or(eq(test.t.a, 3), or(eq(test.t.a, 4), eq(test.t.a, 2)))]"
},
{
"Left": "[gt(test.t.a, 1)]",

View File

@ -15,7 +15,7 @@
{
"SQL": "select b, c from t where t.b = 2 and t.c = 2 and t.b+1=3",
"Plan": [
"Selection_6 0.80 root eq(plus(test.t.b, 1), 3)",
"Selection_6 0.80 root 1",
"└─Point_Get_5 1.00 root table:t, index:b(b, c) "
],
"Res": [

View File

@ -123,7 +123,7 @@
{
"SQL": "select * from t where a = 1 and (b = 1 or b = 2) and b = 3 and c > 1;",
"Plan": [
"TableDual_5 0.00 root rows:0"
"TableDual_5 8000.00 root rows:0"
],
"Result": null
},
@ -169,9 +169,7 @@
{
"SQL": "select * from t where a = 1 and b is null and b = 1 and c > 1;",
"Plan": [
"IndexReader_7 0.27 root index:Selection_6",
"└─Selection_6 0.27 cop[tikv] isnull(test.t.b)",
" └─IndexRangeScan_5 0.33 cop[tikv] table:t, index:a(a, b, c) range:(1 1 1,1 1 +inf], keep order:false, stats:pseudo"
"TableDual_5 8000.00 root rows:0"
],
"Result": null
}