update rewrite rules

* adjust re est cost for nestloop semi/anti join

* add threshold for cost base transform
This commit is contained in:
zs
2021-06-16 11:36:24 +08:00
committed by MizuhaHimuraki
parent cbeee6568e
commit 03001c1fe3
6 changed files with 70 additions and 84 deletions

View File

@ -3515,12 +3515,10 @@ int JoinPath::re_est_cost(sql::Path* path, double need_row_count, double& cost)
if (OB_ISNULL(path)) { if (OB_ISNULL(path)) {
ret = OB_ERR_UNEXPECTED; ret = OB_ERR_UNEXPECTED;
LOG_WARN("unexpect null path", K(ret)); LOG_WARN("unexpect null path", K(ret));
} else if (ACCESS == path->path_type_ && } else if (ACCESS == path->path_type_) {
OB_FAIL(re_est_access_cost(static_cast<AccessPath*>(path), need_row_count, cost))) { ret = re_est_access_cost(static_cast<AccessPath*>(path), need_row_count, cost);
LOG_WARN("failed to est access cost", K(ret)); } else if (SUBQUERY == path->path_type_) {
} else if (SUBQUERY == path->path_type_ && ret = re_est_subquery_cost(static_cast<SubQueryPath*>(path), need_row_count, cost);
OB_FAIL(re_est_subquery_cost(static_cast<SubQueryPath*>(path), need_row_count, cost))) {
LOG_WARN("failed to est subquery cost", K(ret));
} else { } else {
cost = path->cost_; cost = path->cost_;
} }
@ -3570,11 +3568,6 @@ int JoinPath::re_est_access_cost(AccessPath* path, double need_row_count, double
cost, cost,
index_back_cost))) { index_back_cost))) {
LOG_WARN("failed to estimate cost", K(ret)); LOG_WARN("failed to estimate cost", K(ret));
} else {
path->cost_ = cost;
path->op_cost_ = cost;
path->inner_row_count_ = need_row_count;
path->output_row_count_ = need_row_count;
} }
} else { } else {
cost = path->cost_; cost = path->cost_;

View File

@ -167,7 +167,7 @@ int ObTransformRule::accept_transform(
LOG_WARN("failed to evaluate cost for the origin stmt", K(ret)); LOG_WARN("failed to evaluate cost for the origin stmt", K(ret));
} }
if (OB_SUCC(ret)) { if (OB_SUCC(ret)) {
if (trans_stmt_cost < stmt_cost_) { if (trans_stmt_cost < stmt_cost_ * COST_BASE_TRANSFORM_THRESHOLD) {
LOG_TRACE("accept transform because the cost is decreased", K_(stmt_cost), K(trans_stmt_cost)); LOG_TRACE("accept transform because the cost is decreased", K_(stmt_cost), K(trans_stmt_cost));
stmt = trans_stmt; stmt = trans_stmt;
stmt_cost_ = trans_stmt_cost; stmt_cost_ = trans_stmt_cost;

View File

@ -129,6 +129,7 @@ struct ObParentDMLStmt {
class ObTransformRule { class ObTransformRule {
public: public:
static constexpr const double COST_BASE_TRANSFORM_THRESHOLD = 0.999;
static const int64_t TRANSFORMER_DEFAULT_MAX_RECURSIVE_LEVEL = 150; static const int64_t TRANSFORMER_DEFAULT_MAX_RECURSIVE_LEVEL = 150;
static const uint64_t ALL_TRANSFORM_RULES = TRANSFORM_TYPE_COUNT_PLUS_ONE - 1; static const uint64_t ALL_TRANSFORM_RULES = TRANSFORM_TYPE_COUNT_PLUS_ONE - 1;
static const uint64_t ALL_HEURISTICS_RULES = SIMPLIFY | ANYALL | AGGR | ELIMINATE_OJ | VIEW_MERGE | WHERE_SQ_PULL_UP | static const uint64_t ALL_HEURISTICS_RULES = SIMPLIFY | ANYALL | AGGR | ELIMINATE_OJ | VIEW_MERGE | WHERE_SQ_PULL_UP |

View File

@ -9476,50 +9476,48 @@ Outputs & filters:
SQL: select * from t4,t4 t5 where t4.c1 in (select t7.c1 from t7,t8); SQL: select * from t4,t4 t5 where t4.c1 in (select t7.c1 from t7,t8);
================================================================= ===============================================================
|ID|OPERATOR |NAME |EST. ROWS |COST | |ID|OPERATOR |NAME |EST. ROWS |COST |
----------------------------------------------------------------- ---------------------------------------------------------------
|0 |NESTED-LOOP JOIN CARTESIAN | |15504908587|11299759339| |0 |NESTED-LOOP JOIN CARTESIAN | |9900000000|7216269494|
|1 | NESTED-LOOP JOIN | |155050 |3869186 | |1 | TABLE SCAN |t5 |100000 |64066 |
|2 | TABLE SCAN |t4 |100000 |64066 | |2 | MATERIAL | |99000 |3771257 |
|3 | SUBPLAN SCAN |VIEW2|1 |38 | |3 | NESTED-LOOP SEMI JOIN | |99000 |3716682 |
|4 | LIMIT | |1 |38 | |4 | TABLE SCAN |t4 |100000 |64066 |
|5 | NESTED-LOOP JOIN CARTESIAN| |1 |37 | |5 | SUBPLAN SCAN |VIEW1|1 |36 |
|6 | TABLE GET |t7 |1 |36 | |6 | NESTED-LOOP JOIN CARTESIAN| |1 |36 |
|7 | TABLE SCAN |t8 |100000 |59654 | |7 | TABLE GET |t7 |1 |36 |
|8 | MATERIAL | |100000 |119192 | |8 | TABLE SCAN |t8 |100000 |59654 |
|9 | TABLE SCAN |t5 |100000 |64066 | ===============================================================
=================================================================
Outputs & filters: Outputs & filters:
------------------------------------- -------------------------------------
0 - output([t4.c1], [t4.c2], [t4.c3], [t5.c1], [t5.c2], [t5.c3]), filter(nil), 0 - output([t4.c1], [t4.c2], [t4.c3], [t5.c1], [t5.c2], [t5.c3]), filter(nil),
conds(nil), nl_params_(nil), batch_join=false conds(nil), nl_params_(nil), batch_join=false
1 - output([t4.c1], [t4.c2], [t4.c3]), filter(nil), 1 - output([t5.c1], [t5.c2], [t5.c3]), filter(nil),
access([t5.c1], [t5.c2], [t5.c3]), partitions(p0),
is_index_back=false,
range_key([t5.c1], [t5.c2]), range(MIN,MIN ; MAX,MAX)always true
2 - output([t4.c1], [t4.c2], [t4.c3]), filter(nil)
3 - output([t4.c1], [t4.c2], [t4.c3]), filter(nil),
conds(nil), nl_params_([t4.c1]), batch_join=false conds(nil), nl_params_([t4.c1]), batch_join=false
2 - output([t4.c1], [t4.c2], [t4.c3]), filter(nil), 4 - output([t4.c1], [t4.c2], [t4.c3]), filter(nil),
access([t4.c1], [t4.c2], [t4.c3]), partitions(p0), access([t4.c1], [t4.c2], [t4.c3]), partitions(p0),
is_index_back=false, is_index_back=false,
range_key([t4.c1], [t4.c2]), range(MIN,MIN ; MAX,MAX)always true range_key([t4.c1], [t4.c2]), range(MIN,MIN ; MAX,MAX)always true
3 - output([1]), filter(nil), 5 - output([1]), filter(nil),
access([VIEW2.VIEW1.c1]) access([VIEW1.c1])
4 - output([t7.c1]), filter(nil), limit(1), offset(nil)
5 - output([t7.c1]), filter(nil),
conds(nil), nl_params_(nil), batch_join=true
6 - output([t7.c1]), filter(nil), 6 - output([t7.c1]), filter(nil),
conds(nil), nl_params_(nil), batch_join=true
7 - output([t7.c1]), filter(nil),
access([t7.c1]), partitions(p0), access([t7.c1]), partitions(p0),
is_index_back=false, is_index_back=false,
range_key([t7.c1]), range(MIN ; MAX)always true, range_key([t7.c1]), range(MIN ; MAX)always true,
range_cond([? = t7.c1]) range_cond([? = t7.c1])
7 - output([1]), filter(nil), 8 - output([1]), filter(nil),
access([t8.c1]), partitions(p0), access([t8.c1]), partitions(p0),
is_index_back=false, is_index_back=false,
range_key([t8.c1]), range(MIN ; MAX)always true range_key([t8.c1]), range(MIN ; MAX)always true
8 - output([t5.c1], [t5.c2], [t5.c3]), filter(nil)
9 - output([t5.c1], [t5.c2], [t5.c3]), filter(nil),
access([t5.c1], [t5.c2], [t5.c3]), partitions(p0),
is_index_back=false,
range_key([t5.c1], [t5.c2]), range(MIN,MIN ; MAX,MAX)always true
*************** Case 273(end) ************** *************** Case 273(end) **************

View File

@ -3003,17 +3003,15 @@ SQL: select t20.c1 from t20 join t0 where t0.c1 in (select t7.c1 from t7 join t8
======================================================== ========================================================
|ID|OPERATOR |NAME |EST. ROWS|COST | |ID|OPERATOR |NAME |EST. ROWS|COST |
-------------------------------------------------------- --------------------------------------------------------
|0 |NESTED-LOOP JOIN CARTESIAN | |10000 |17490| |0 |NESTED-LOOP JOIN CARTESIAN | |10000 |10934|
|1 | MERGE SEMI JOIN | |100 |10301| |1 | NESTED-LOOP SEMI JOIN | |100 |3745 |
|2 | SORT | |100 |198 | |2 | TABLE SCAN |t0 |100 |90 |
|3 | TABLE SCAN |t0 |100 |90 | |3 | SUBPLAN SCAN |VIEW1|1 |36 |
|4 | SUBPLAN SCAN |VIEW1|10000 |8650 | |4 | NESTED-LOOP JOIN CARTESIAN| |1 |36 |
|5 | NESTED-LOOP JOIN CARTESIAN| |10000 |7270 | |5 | TABLE GET |t7 |1 |36 |
|6 | TABLE SCAN |t7 |100 |88 | |6 | TABLE SCAN |t8 |100 |88 |
|7 | MATERIAL | |100 |106 | |7 | MATERIAL | |100 |113 |
|8 | TABLE SCAN |t8 |100 |88 | |8 | TABLE SCAN |t20 |100 |95 |
|9 | MATERIAL | |100 |113 |
|10| TABLE SCAN |t20 |100 |95 |
======================================================== ========================================================
Outputs & filters: Outputs & filters:
@ -3021,21 +3019,19 @@ Outputs & filters:
0 - output([t20.c1]), filter(nil), 0 - output([t20.c1]), filter(nil),
conds(nil), nl_params_(nil) conds(nil), nl_params_(nil)
1 - output([1]), filter(nil), 1 - output([1]), filter(nil),
equal_conds([t0.c1 = VIEW1.c1]), other_conds(nil) conds(nil), nl_params_([t0.c1])
2 - output([t0.c1]), filter(nil), sort_keys([t0.c1, ASC]) 2 - output([t0.c1]), filter(nil),
3 - output([t0.c1]), filter(nil),
access([t0.c1]), partitions(p0) access([t0.c1]), partitions(p0)
4 - output([VIEW1.c1]), filter(nil), 3 - output([1]), filter(nil),
access([VIEW1.c1]) access([VIEW1.c1])
5 - output([t7.c1]), filter(nil), 4 - output([t7.c1]), filter(nil),
conds(nil), nl_params_(nil) conds(nil), nl_params_(nil)
6 - output([t7.c1]), filter(nil), 5 - output([t7.c1]), filter(nil),
access([t7.c1]), partitions(p0) access([t7.c1]), partitions(p0)
7 - output([1]), filter(nil) 6 - output([1]), filter(nil),
8 - output([1]), filter(nil),
access([t8.c1]), partitions(p0) access([t8.c1]), partitions(p0)
9 - output([t20.c1]), filter(nil) 7 - output([t20.c1]), filter(nil)
10 - output([t20.c1]), filter(nil), 8 - output([t20.c1]), filter(nil),
access([t20.c1]), partitions(p0) access([t20.c1]), partitions(p0)
Outline Data: Outline Data:
@ -3045,11 +3041,12 @@ Outline Data:
LEADING(@"SEL$1" (("opt.t0"@"SEL$1" "VIEW1"@"SEL$1" )"opt.t20"@"SEL$1" )) LEADING(@"SEL$1" (("opt.t0"@"SEL$1" "VIEW1"@"SEL$1" )"opt.t20"@"SEL$1" ))
USE_NL(@"SEL$1" ("opt.t20"@"SEL$1" )) USE_NL(@"SEL$1" ("opt.t20"@"SEL$1" ))
USE_NL_MATERIALIZATION(@"SEL$1" ("opt.t20"@"SEL$1" )) USE_NL_MATERIALIZATION(@"SEL$1" ("opt.t20"@"SEL$1" ))
USE_MERGE(@"SEL$1" ("VIEW1"@"SEL$1" )) USE_NL(@"SEL$1" ("VIEW1"@"SEL$1" ))
NO_USE_NL_MATERIALIZATION(@"SEL$1" ("VIEW1"@"SEL$1" ))
FULL(@"SEL$1" "opt.t0"@"SEL$1") FULL(@"SEL$1" "opt.t0"@"SEL$1")
LEADING(@"SEL$2" ("opt.t7"@"SEL$2" "opt.t8"@"SEL$2" )) LEADING(@"SEL$2" ("opt.t7"@"SEL$2" "opt.t8"@"SEL$2" ))
USE_NL(@"SEL$2" ("opt.t8"@"SEL$2" )) USE_NL(@"SEL$2" ("opt.t8"@"SEL$2" ))
USE_NL_MATERIALIZATION(@"SEL$2" ("opt.t8"@"SEL$2" )) NO_USE_NL_MATERIALIZATION(@"SEL$2" ("opt.t8"@"SEL$2" ))
FULL(@"SEL$2" "opt.t7"@"SEL$2") FULL(@"SEL$2" "opt.t7"@"SEL$2")
FULL(@"SEL$2" "opt.t8"@"SEL$2") FULL(@"SEL$2" "opt.t8"@"SEL$2")
FULL(@"SEL$1" "opt.t20"@"SEL$1") FULL(@"SEL$1" "opt.t20"@"SEL$1")

View File

@ -2472,34 +2472,30 @@ Outline Data:
*************** Case 77 *************** *************** Case 77 ***************
SQL: SELECT c1 FROM pullup1 WHERE c1 IN (SELECT pullup2.pk FROM pullup2, pullup3); SQL: SELECT c1 FROM pullup1 WHERE c1 IN (SELECT pullup2.pk FROM pullup2, pullup3);
=============================================================== ==============================================================
|ID|OPERATOR |NAME |EST. ROWS|COST| |ID|OPERATOR |NAME |EST. ROWS|COST|
--------------------------------------------------------------- --------------------------------------------------------------
|0 |MERGE SEMI JOIN | |100 |10265| |0 |NESTED-LOOP SEMI JOIN | |100 |3745|
|1 | SORT | |100 |198 | |1 | TABLE SCAN |pullup1 |100 |90 |
|2 | TABLE SCAN |pullup1 |100 |90 | |2 | SUBPLAN SCAN |VIEW1 |1 |36 |
|3 | SUBPLAN SCAN |VIEW1 |10000 |8615 | |3 | NESTED-LOOP JOIN CARTESIAN| |1 |36 |
|4 | NESTED-LOOP JOIN CARTESIAN| |10000 |7235 | |4 | TABLE GET |pullup2 |1 |36 |
|5 | TABLE SCAN |pullup2 |100 |88 | |5 | TABLE SCAN |pullup3(uniq)|100 |52 |
|6 | MATERIAL | |100 |71 | ==============================================================
|7 | TABLE SCAN |pullup3(uniq)|100 |52 |
===============================================================
Outputs & filters: Outputs & filters:
------------------------------------- -------------------------------------
0 - output([pullup1.c1]), filter(nil), 0 - output([pullup1.c1]), filter(nil),
equal_conds([pullup1.c1 = VIEW1.pk]), other_conds(nil) conds(nil), nl_params_([pullup1.c1])
1 - output([pullup1.c1]), filter(nil), sort_keys([pullup1.c1, ASC]) 1 - output([pullup1.c1]), filter(nil),
2 - output([pullup1.c1]), filter(nil),
access([pullup1.c1]), partitions(p0) access([pullup1.c1]), partitions(p0)
3 - output([VIEW1.pk]), filter(nil), 2 - output([1]), filter(nil),
access([VIEW1.pk]) access([VIEW1.pk])
4 - output([pullup2.pk]), filter(nil), 3 - output([pullup2.pk]), filter(nil),
conds(nil), nl_params_(nil) conds(nil), nl_params_(nil)
5 - output([pullup2.pk]), filter(nil), 4 - output([pullup2.pk]), filter(nil),
access([pullup2.pk]), partitions(p0) access([pullup2.pk]), partitions(p0)
6 - output([1]), filter(nil) 5 - output([1]), filter(nil),
7 - output([1]), filter(nil),
access([pullup3.uniq_c2]), partitions(p0) access([pullup3.uniq_c2]), partitions(p0)
Outline Data: Outline Data:
@ -2507,11 +2503,12 @@ Outline Data:
/*+ /*+
BEGIN_OUTLINE_DATA BEGIN_OUTLINE_DATA
LEADING(@"SEL$1" ("opt.pullup1"@"SEL$1" "VIEW1"@"SEL$1" )) LEADING(@"SEL$1" ("opt.pullup1"@"SEL$1" "VIEW1"@"SEL$1" ))
USE_MERGE(@"SEL$1" ("VIEW1"@"SEL$1" )) USE_NL(@"SEL$1" ("VIEW1"@"SEL$1" ))
NO_USE_NL_MATERIALIZATION(@"SEL$1" ("VIEW1"@"SEL$1" ))
FULL(@"SEL$1" "opt.pullup1"@"SEL$1") FULL(@"SEL$1" "opt.pullup1"@"SEL$1")
LEADING(@"SEL$2" ("opt.pullup2"@"SEL$2" "opt.pullup3"@"SEL$2" )) LEADING(@"SEL$2" ("opt.pullup2"@"SEL$2" "opt.pullup3"@"SEL$2" ))
USE_NL(@"SEL$2" ("opt.pullup3"@"SEL$2" )) USE_NL(@"SEL$2" ("opt.pullup3"@"SEL$2" ))
USE_NL_MATERIALIZATION(@"SEL$2" ("opt.pullup3"@"SEL$2" )) NO_USE_NL_MATERIALIZATION(@"SEL$2" ("opt.pullup3"@"SEL$2" ))
FULL(@"SEL$2" "opt.pullup2"@"SEL$2") FULL(@"SEL$2" "opt.pullup2"@"SEL$2")
INDEX(@"SEL$2" "opt.pullup3"@"SEL$2" "uniq") INDEX(@"SEL$2" "opt.pullup3"@"SEL$2" "uniq")
END_OUTLINE_DATA END_OUTLINE_DATA