diff options
author | bell@sanja.is.com.ua <> | 2003-08-12 12:38:03 +0300 |
---|---|---|
committer | bell@sanja.is.com.ua <> | 2003-08-12 12:38:03 +0300 |
commit | 6ac8e9b93c8ca84f0fe6bf42a55532092ed2e948 (patch) | |
tree | bf79484f7cc14e515e3fc508ecb3815329621ca3 /sql/item_subselect.cc | |
parent | c06786fa0080e5d2e92b6a036eab3797165ff5b4 (diff) | |
download | mariadb-git-6ac8e9b93c8ca84f0fe6bf42a55532092ed2e948.tar.gz |
optimisation of independent ALL/ANY with aggregate function (WL#1115) (SCRUM)
Diffstat (limited to 'sql/item_subselect.cc')
-rw-r--r-- | sql/item_subselect.cc | 84 |
1 files changed, 54 insertions, 30 deletions
diff --git a/sql/item_subselect.cc b/sql/item_subselect.cc index 77300dd2cf3..c6e421d763c 100644 --- a/sql/item_subselect.cc +++ b/sql/item_subselect.cc @@ -152,8 +152,8 @@ inline table_map Item_subselect::used_tables() const } Item_singlerow_subselect::Item_singlerow_subselect(THD *thd, - st_select_lex *select_lex): - Item_subselect(), value(0) + st_select_lex *select_lex) + :Item_subselect(), value(0) { DBUG_ENTER("Item_singlerow_subselect::Item_singlerow_subselect"); init(thd, select_lex, new select_singlerow_subselect(this)); @@ -163,6 +163,19 @@ Item_singlerow_subselect::Item_singlerow_subselect(THD *thd, DBUG_VOID_RETURN; } +Item_maxmin_subselect::Item_maxmin_subselect(THD *thd, + st_select_lex *select_lex, + bool max) + :Item_singlerow_subselect() +{ + DBUG_ENTER("Item_maxmin_subselect::Item_maxmin_subselect"); + init(thd, select_lex, new select_max_min_finder_subselect(this, max)); + max_columns= 1; + maybe_null= 1; + max_columns= 1; + DBUG_VOID_RETURN; +} + void Item_singlerow_subselect::reset() { null_value= 1; @@ -499,38 +512,50 @@ Item_in_subselect::single_value_transformer(JOIN *join, (func == &Item_bool_func2::gt_creator || func == &Item_bool_func2::lt_creator || func == &Item_bool_func2::ge_creator || - func == &Item_bool_func2::le_creator) && - !select_lex->group_list.elements && - !select_lex->with_sum_func) + func == &Item_bool_func2::le_creator)) { - Item *item; - subs_type type= substype(); - if (func == &Item_bool_func2::le_creator || - func == &Item_bool_func2::lt_creator) + Item *subs; + if (!select_lex->group_list.elements && + !select_lex->with_sum_func) { - /* - (ALL && (> || =>)) || (ANY && (< || =<)) - for ALL condition is inverted - */ - item= new Item_sum_max(*select_lex->ref_pointer_array); + Item *item; + subs_type type= substype(); + if (func == &Item_bool_func2::le_creator || + func == &Item_bool_func2::lt_creator) + { + /* + (ALL && (> || =>)) || (ANY && (< || =<)) + for ALL condition is inverted + */ + item= new Item_sum_max(*select_lex->ref_pointer_array); + } + else + { + /* + (ALL && (< || =<)) || (ANY && (> || =>)) + for ALL condition is inverted + */ + item= new Item_sum_min(*select_lex->ref_pointer_array); + } + *select_lex->ref_pointer_array= item; + select_lex->item_list.empty(); + select_lex->item_list.push_back(item); + + if (item->fix_fields(thd, join->tables_list, &item)) + { + DBUG_RETURN(ERROR); + } + subs= new Item_singlerow_subselect(thd, select_lex); } else { - /* - (ALL && (< || =<)) || (ANY && (> || =>)) - for ALL condition is inverted - */ - item= new Item_sum_min(*select_lex->ref_pointer_array); - } - *select_lex->ref_pointer_array= item; - select_lex->item_list.empty(); - select_lex->item_list.push_back(item); - - if (item->fix_fields(thd, join->tables_list, &item)) - { - DBUG_RETURN(ERROR); + // remove LIMIT placed by ALL/ANY subquery + select_lex->master_unit()->global_parameters->select_limit= + HA_POS_ERROR; + subs= new Item_maxmin_subselect(thd, select_lex, + (func == &Item_bool_func2::le_creator || + func == &Item_bool_func2::lt_creator)); } - // left expression belong to outer select SELECT_LEX *current= thd->lex.current_select, *up; thd->lex.current_select= up= current->return_after_parsing(); @@ -540,8 +565,7 @@ Item_in_subselect::single_value_transformer(JOIN *join, DBUG_RETURN(ERROR); } thd->lex.current_select= current; - substitution= (*func)(left_expr, - new Item_singlerow_subselect(thd, select_lex)); + substitution= (*func)(left_expr, subs); DBUG_RETURN(OK); } |