adjust allocate window function operator, enhance pq_distribute_window hint

This commit is contained in:
chimyue
2023-07-19 03:12:22 +00:00
committed by ob-robot
parent 9a244755cd
commit 32636e05c4
20 changed files with 2204 additions and 1204 deletions

View File

@ -952,7 +952,7 @@ const char* ObHint::get_hint_name(ObItemType type, bool is_enable_hint /* defaul
case T_USE_HASH_AGGREGATE: return is_enable_hint ? "USE_HASH_AGGREGATION"
: "NO_USE_HASH_AGGREGATION";
case T_TABLE_PARALLEL: return "PARALLEL";
case T_PQ_DISTRIBUTE_WINDOW: return "PQ_DISIRIBUTE_WINDOW";
case T_PQ_DISTRIBUTE_WINDOW: return "PQ_DISTRIBUTE_WINDOW";
case T_GBY_PUSHDOWN: return is_enable_hint ? "GBY_PUSHDOWN" : "NO_GBY_PUSHDOWN";
case T_USE_HASH_DISTINCT: return is_enable_hint ? "USE_HASH_DISTINCT" : "NO_USE_HASH_DISTINCT";
case T_DISTINCT_PUSHDOWN: return is_enable_hint ? "DISTINCT_PUSHDOWN" : "NO_DISTINCT_PUSHDOWN";
@ -2561,10 +2561,10 @@ void ObTableInHint::set_table(const TableItem& table)
const char *ObWindowDistHint::get_dist_algo_str(WinDistAlgo dist_algo)
{
switch (dist_algo) {
case WinDistAlgo::NONE: return "NONE";
case WinDistAlgo::HASH: return "HASH";
case WinDistAlgo::RANGE: return "RANGE";
case WinDistAlgo::LIST: return "LIST";
case WinDistAlgo::WIN_DIST_NONE: return "NONE";
case WinDistAlgo::WIN_DIST_HASH: return "HASH";
case WinDistAlgo::WIN_DIST_RANGE: return "RANGE";
case WinDistAlgo::WIN_DIST_LIST: return "LIST";
default: return NULL;
}
return NULL;
@ -2573,17 +2573,130 @@ const char *ObWindowDistHint::get_dist_algo_str(WinDistAlgo dist_algo)
int ObWindowDistHint::print_hint_desc(PlanText &plan_text) const
{
int ret = OB_SUCCESS;
char *buf = plan_text.buf_;
int64_t &buf_len = plan_text.buf_len_;
int64_t &pos = plan_text.pos_;
FOREACH_CNT_X(v, algos_, OB_SUCC(ret)) {
if (OB_FAIL(BUF_PRINTF(" %s", get_dist_algo_str(*v)))) {
LOG_WARN("print failed", K(ret));
for (int64_t i = 0; OB_SUCC(ret) && i < win_dist_options_.count(); ++i) {
if (OB_FAIL(win_dist_options_.at(i).print_win_dist_option(plan_text))) {
LOG_WARN("failed to print win dist option", K(ret), K(i));
}
}
return ret;
}
int ObWindowDistHint::add_win_dist_option(const ObIArray<ObWinFunRawExpr*> &all_win_funcs,
const ObIArray<ObWinFunRawExpr*> &cur_win_funcs,
const WinDistAlgo algo,
const bool is_push_down,
const bool use_hash_sort)
{
int ret = OB_SUCCESS;
ObSEArray<int64_t, 4> win_func_idxs;
int64_t idx = OB_INVALID_INDEX;
for (int64_t i = 0; OB_SUCC(ret) && i < cur_win_funcs.count(); ++i) {
if (OB_UNLIKELY(!ObOptimizerUtil::find_item(all_win_funcs, cur_win_funcs.at(i), &idx))) {
ret = OB_ERR_UNEXPECTED;
LOG_WARN("failed to find item", K(ret), K(all_win_funcs), K(cur_win_funcs));
} else if (OB_FAIL(win_func_idxs.push_back(idx))) {
LOG_WARN("failed to push back", K(ret));
}
}
if (OB_SUCC(ret) && add_win_dist_option(win_func_idxs, algo, is_push_down, use_hash_sort)) {
LOG_WARN("failed to add win dist option", K(ret));
}
return ret;
}
int ObWindowDistHint::add_win_dist_option(const ObIArray<int64_t> &win_func_idxs,
const WinDistAlgo algo,
const bool is_push_down,
const bool use_hash_sort)
{
int ret = OB_SUCCESS;
int64_t idx = win_dist_options_.count();
if (OB_FAIL(win_dist_options_.prepare_allocate(win_dist_options_.count() + 1))) {
LOG_WARN("array prepare allocate failed", K(ret));
} else {
WinDistOption &win_dist_option = win_dist_options_.at(idx);
win_dist_option.algo_ = algo;
win_dist_option.is_push_down_ = is_push_down;
win_dist_option.use_hash_sort_ = use_hash_sort;
if (win_dist_option.win_func_idxs_.assign(win_func_idxs)) {
LOG_WARN("failed to add win dist option", K(ret));
}
}
return ret;
}
int ObWindowDistHint::WinDistOption::print_win_dist_option(PlanText &plan_text) const
{
int ret = OB_SUCCESS;
char *buf = plan_text.buf_;
int64_t &buf_len = plan_text.buf_len_;
int64_t &pos = plan_text.pos_;
if (OB_UNLIKELY(!is_valid())) {
ret = OB_ERR_UNEXPECTED;
LOG_WARN("invalid WinDistOption", K(ret), K(*this));
} else if (win_func_idxs_.empty()) {
/* do nothing */
} else if (OB_FAIL(BUF_PRINTF(" (%ld", win_func_idxs_.at(0)))) {
LOG_WARN("fail to print win func idx", K(ret), K(win_func_idxs_));
} else {
for (int64_t i = 1; OB_SUCC(ret) && i < win_func_idxs_.count(); ++i) {
if (OB_FAIL(BUF_PRINTF(",%ld", win_func_idxs_.at(i)))) {
LOG_WARN("fail to print win func idx", K(ret), K(win_func_idxs_));
}
}
if (OB_SUCC(ret) && OB_FAIL(BUF_PRINTF(")"))) {
LOG_WARN("failed to print win func idx", K(ret));
}
}
if (OB_FAIL(ret)) {
} else if (OB_FAIL(BUF_PRINTF(" %s", ObWindowDistHint::get_dist_algo_str(algo_)))) {
LOG_WARN("failed to print win func dist algo", K(ret));
} else if (use_hash_sort_ && OB_FAIL(BUF_PRINTF(" PARTITION_SORT"))) {
LOG_WARN("failed to print win func sort", K(ret));
} else if (is_push_down_ && OB_FAIL(BUF_PRINTF(" PUSHDOWN"))) {
LOG_WARN("failed to print win func push down", K(ret));
}
return ret;
}
bool ObWindowDistHint::WinDistOption::is_valid() const
{
bool bret = true;
if (WinDistAlgo::WIN_DIST_INVALID == algo_) {
bret = false;
} else if (WinDistAlgo::WIN_DIST_HASH != algo_ && is_push_down_) {
bret = false;
} else if (WinDistAlgo::WIN_DIST_HASH != algo_ && WinDistAlgo::WIN_DIST_NONE != algo_ && use_hash_sort_) {
bret = false;
} else {
for (int64_t i = 0; bret && i < win_func_idxs_.count(); ++i) {
bret = win_func_idxs_.at(i) >= 0;
}
}
return bret;
}
int ObWindowDistHint::WinDistOption::assign(const WinDistOption& other)
{
int ret = OB_SUCCESS;
algo_ = other.algo_;
use_hash_sort_ = other.use_hash_sort_;
is_push_down_ = other.is_push_down_;
if (OB_FAIL(win_func_idxs_.assign(other.win_func_idxs_))) {
LOG_WARN("failed to assign", K(ret));
}
return ret;
}
void ObWindowDistHint::WinDistOption::reset()
{
algo_ = WinDistAlgo::WIN_DIST_INVALID;
use_hash_sort_ = false;
is_push_down_ = false;
win_func_idxs_.reuse();
}
int ObAggHint::assign(const ObAggHint &other)
{
int ret = OB_SUCCESS;