[CP] reorder the order of complex filters
This commit is contained in:
@ -60,6 +60,7 @@
|
||||
#include "sql/engine/px/p2p_datahub/ob_p2p_dh_mgr.h"
|
||||
#include "sql/engine/expr/ob_expr_join_filter.h"
|
||||
#include "sql/engine/px/p2p_datahub/ob_runtime_filter_query_range.h"
|
||||
#include "sql/optimizer/ob_opt_est_parameter_normal.h"
|
||||
|
||||
|
||||
using namespace oceanbase::sql;
|
||||
@ -501,6 +502,18 @@ double FilterCompare::get_selectivity(ObRawExpr *expr)
|
||||
return selectivity;
|
||||
}
|
||||
|
||||
int ObLogicalOperator::get_card_without_filter(double &card)
|
||||
{
|
||||
int ret = OB_SUCCESS;
|
||||
ObLogicalOperator *child_op = NULL;
|
||||
if (OB_NOT_NULL(child_op = get_child(ObLogicalOperator::first_child))) {
|
||||
card = child_op->get_card();
|
||||
} else {
|
||||
card = 1.0;
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
// Add a child to the end of the array
|
||||
int ObLogicalOperator::add_child(ObLogicalOperator *child_op)
|
||||
{
|
||||
@ -2524,9 +2537,60 @@ int ObLogicalOperator::reorder_filter_exprs()
|
||||
if (OB_ISNULL(get_plan())) {
|
||||
ret = OB_ERR_UNEXPECTED;
|
||||
LOG_WARN("Get unexpeced null", K(ret), K(get_plan()));
|
||||
} else {
|
||||
FilterCompare filter_compare(get_plan()->get_predicate_selectivities());
|
||||
std::sort(filter_exprs_.begin(), filter_exprs_.end(), filter_compare);
|
||||
} else if (OB_FAIL(reorder_filters_exprs(get_plan()->get_predicate_selectivities(),
|
||||
filter_exprs_))) {
|
||||
LOG_WARN("reorder filter exprs failed", K(ret));
|
||||
} else if (log_op_def::LOG_JOIN == get_type()) {
|
||||
ObLogJoin *join_op = static_cast<ObLogJoin *>(this);
|
||||
if (OB_FAIL(reorder_filters_exprs(get_plan()->get_predicate_selectivities(),
|
||||
join_op->get_join_filters()))) {
|
||||
LOG_WARN("reorder join filters failed", K(ret));
|
||||
}
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
int ObLogicalOperator::reorder_filters_exprs(common::ObIArray<ObExprSelPair> &predicate_selectivities,
|
||||
ObIArray<ObRawExpr *> &filter_exprs)
|
||||
{
|
||||
int ret = OB_SUCCESS;
|
||||
double card = 0;
|
||||
FilterCompare filter_compare(predicate_selectivities);
|
||||
common::ObSEArray<ObExprRankPair, 4> filter_ranks;
|
||||
if (OB_ISNULL(get_plan())) {
|
||||
ret = OB_ERR_UNEXPECTED;
|
||||
LOG_WARN("get unexpected null", K(ret), K(get_plan()));
|
||||
} else if (OB_FAIL(get_card_without_filter(card))) {
|
||||
LOG_WARN("get num of rows to be filtered failed", K(ret));
|
||||
} else if (card < 1.0) {
|
||||
card = 1.0;
|
||||
}
|
||||
for (int64_t i = 0; OB_SUCC(ret) && i < filter_exprs.count(); ++i) {
|
||||
double cost_per_tuple = 0.0;
|
||||
double sel = filter_compare.get_selectivity(filter_exprs.at(i));
|
||||
double rank = 0;
|
||||
if (sel < 0) {
|
||||
// security filter should be calc firstly
|
||||
rank = -NAN;
|
||||
} else if (OB_FAIL(ObOptEstCost::calc_pred_cost_per_row(filter_exprs.at(i),
|
||||
card,
|
||||
cost_per_tuple,
|
||||
get_plan()->get_optimizer_context()))) {
|
||||
LOG_WARN("calc pred cost failed", K(ret));
|
||||
} else {
|
||||
rank = (sel - 1) / cost_per_tuple;
|
||||
}
|
||||
if (OB_SUCC(ret)) {
|
||||
if (OB_FAIL(filter_ranks.push_back(ObExprRankPair(rank, filter_exprs.at(i))))) {
|
||||
LOG_WARN("push back failed", K(ret));
|
||||
}
|
||||
}
|
||||
}
|
||||
if (OB_SUCC(ret)) {
|
||||
std::sort(filter_ranks.begin(), filter_ranks.end(), ObExprRankPairCompare());
|
||||
for(int64_t i = 0; i < filter_ranks.count(); ++i) {
|
||||
filter_exprs.at(i) = filter_ranks.at(i).second;
|
||||
}
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user