cleanup: Item::can_eval_in_optimize()
a helper method to check whether an item can be evaluated in the query optimization phase (in and below JOIN::optimize()).
This commit is contained in:
parent
30f0a246a0
commit
6de84e6f4e
@ -1636,6 +1636,10 @@ public:
|
|||||||
DBUG_ASSERT(!is_expensive());
|
DBUG_ASSERT(!is_expensive());
|
||||||
return val_bool();
|
return val_bool();
|
||||||
}
|
}
|
||||||
|
bool can_eval_in_optimize()
|
||||||
|
{
|
||||||
|
return const_item() && !is_expensive();
|
||||||
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
save_val() is method of val_* family which stores value in the given
|
save_val() is method of val_* family which stores value in the given
|
||||||
|
@ -318,7 +318,7 @@ static bool convert_const_to_int(THD *thd, Item_field *field_item,
|
|||||||
field_item->field_type() != MYSQL_TYPE_YEAR)
|
field_item->field_type() != MYSQL_TYPE_YEAR)
|
||||||
return 1;
|
return 1;
|
||||||
|
|
||||||
if ((*item)->const_item() && !(*item)->is_expensive())
|
if ((*item)->can_eval_in_optimize())
|
||||||
{
|
{
|
||||||
TABLE *table= field->table;
|
TABLE *table= field->table;
|
||||||
Sql_mode_save sql_mode(thd);
|
Sql_mode_save sql_mode(thd);
|
||||||
@ -4899,8 +4899,8 @@ Item_cond::fix_fields(THD *thd, Item **ref)
|
|||||||
return TRUE; /* purecov: inspected */
|
return TRUE; /* purecov: inspected */
|
||||||
item= *li.ref(); // item can be substituted in fix_fields
|
item= *li.ref(); // item can be substituted in fix_fields
|
||||||
used_tables_cache|= item->used_tables();
|
used_tables_cache|= item->used_tables();
|
||||||
if (item->const_item() && !item->with_sp_var() &&
|
if (item->can_eval_in_optimize() && !item->with_sp_var() &&
|
||||||
!item->is_expensive() && !cond_has_datetime_is_null(item))
|
!cond_has_datetime_is_null(item))
|
||||||
{
|
{
|
||||||
if (item->eval_const_cond() == is_and_cond && top_level())
|
if (item->eval_const_cond() == is_and_cond && top_level())
|
||||||
{
|
{
|
||||||
@ -4956,8 +4956,8 @@ Item_cond::eval_not_null_tables(void *opt_arg)
|
|||||||
while ((item=li++))
|
while ((item=li++))
|
||||||
{
|
{
|
||||||
table_map tmp_table_map;
|
table_map tmp_table_map;
|
||||||
if (item->const_item() && !item->with_sp_var() &&
|
if (item->can_eval_in_optimize() && !item->with_sp_var() &&
|
||||||
!item->is_expensive() && !cond_has_datetime_is_null(item))
|
!cond_has_datetime_is_null(item))
|
||||||
{
|
{
|
||||||
if (item->eval_const_cond() == is_and_cond && top_level())
|
if (item->eval_const_cond() == is_and_cond && top_level())
|
||||||
{
|
{
|
||||||
@ -5640,7 +5640,7 @@ bool Item_func_like::with_sargable_pattern() const
|
|||||||
if (negated)
|
if (negated)
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
if (!args[1]->const_item() || args[1]->is_expensive())
|
if (!args[1]->can_eval_in_optimize())
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
String* res2= args[1]->val_str((String *) &cmp_value2);
|
String* res2= args[1]->val_str((String *) &cmp_value2);
|
||||||
@ -5785,8 +5785,7 @@ bool Item_func_like::fix_fields(THD *thd, Item **ref)
|
|||||||
We could also do boyer-more for non-const items, but as we would have to
|
We could also do boyer-more for non-const items, but as we would have to
|
||||||
recompute the tables for each row it's not worth it.
|
recompute the tables for each row it's not worth it.
|
||||||
*/
|
*/
|
||||||
if (args[1]->const_item() && !use_strnxfrm(collation.collation) &&
|
if (args[1]->can_eval_in_optimize() && !use_strnxfrm(collation.collation))
|
||||||
!args[1]->is_expensive())
|
|
||||||
{
|
{
|
||||||
String* res2= args[1]->val_str(&cmp_value2);
|
String* res2= args[1]->val_str(&cmp_value2);
|
||||||
if (!res2)
|
if (!res2)
|
||||||
@ -6980,7 +6979,7 @@ void Item_equal::update_const(THD *thd)
|
|||||||
Item *item;
|
Item *item;
|
||||||
while ((item= it++))
|
while ((item= it++))
|
||||||
{
|
{
|
||||||
if (item->const_item() && !item->is_expensive() &&
|
if (item->can_eval_in_optimize() &&
|
||||||
/*
|
/*
|
||||||
Don't propagate constant status of outer-joined column.
|
Don't propagate constant status of outer-joined column.
|
||||||
Such a constant status here is a result of:
|
Such a constant status here is a result of:
|
||||||
|
@ -2486,7 +2486,7 @@ class Item_func_in :public Item_func_opt_neg,
|
|||||||
{
|
{
|
||||||
for (uint i= 0; i < nitems; i++)
|
for (uint i= 0; i < nitems; i++)
|
||||||
{
|
{
|
||||||
if (!items[i]->const_item() || items[i]->is_expensive())
|
if (!items[i]->can_eval_in_optimize())
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
return true;
|
return true;
|
||||||
|
@ -2525,7 +2525,7 @@ void Item_func_round::fix_arg_temporal(const Type_handler *h,
|
|||||||
uint int_part_length)
|
uint int_part_length)
|
||||||
{
|
{
|
||||||
set_handler(h);
|
set_handler(h);
|
||||||
if (args[1]->const_item() && !args[1]->is_expensive())
|
if (args[1]->can_eval_in_optimize())
|
||||||
{
|
{
|
||||||
Longlong_hybrid_null dec= args[1]->to_longlong_hybrid_null();
|
Longlong_hybrid_null dec= args[1]->to_longlong_hybrid_null();
|
||||||
fix_attributes_temporal(int_part_length,
|
fix_attributes_temporal(int_part_length,
|
||||||
@ -2561,7 +2561,7 @@ bool Item_func_round::test_if_length_can_increase()
|
|||||||
{
|
{
|
||||||
if (truncate)
|
if (truncate)
|
||||||
return false;
|
return false;
|
||||||
if (args[1]->const_item() && !args[1]->is_expensive())
|
if (args[1]->can_eval_in_optimize())
|
||||||
{
|
{
|
||||||
// Length can increase in some cases: e.g. ROUND(9,-1) -> 10.
|
// Length can increase in some cases: e.g. ROUND(9,-1) -> 10.
|
||||||
Longlong_hybrid val1= args[1]->to_longlong_hybrid();
|
Longlong_hybrid val1= args[1]->to_longlong_hybrid();
|
||||||
|
@ -1639,7 +1639,7 @@ String *Item_func_left::val_str(String *str)
|
|||||||
void Item_str_func::left_right_max_length()
|
void Item_str_func::left_right_max_length()
|
||||||
{
|
{
|
||||||
uint32 char_length= args[0]->max_char_length();
|
uint32 char_length= args[0]->max_char_length();
|
||||||
if (args[1]->const_item() && !args[1]->is_expensive())
|
if (args[1]->can_eval_in_optimize())
|
||||||
{
|
{
|
||||||
uint32 length= max_length_for_string(args[1]);
|
uint32 length= max_length_for_string(args[1]);
|
||||||
set_if_smaller(char_length, length);
|
set_if_smaller(char_length, length);
|
||||||
@ -2669,7 +2669,7 @@ bool Item_func_format::fix_length_and_dec()
|
|||||||
the number of decimals and round to the next integer.
|
the number of decimals and round to the next integer.
|
||||||
*/
|
*/
|
||||||
bool need_extra_digit_for_rounding= args[0]->decimals > 0;
|
bool need_extra_digit_for_rounding= args[0]->decimals > 0;
|
||||||
if (args[1]->const_item() && !args[1]->is_expensive())
|
if (args[1]->can_eval_in_optimize())
|
||||||
{
|
{
|
||||||
Longlong_hybrid tmp= args[1]->to_longlong_hybrid();
|
Longlong_hybrid tmp= args[1]->to_longlong_hybrid();
|
||||||
if (!args[1]->null_value)
|
if (!args[1]->null_value)
|
||||||
@ -3034,7 +3034,7 @@ bool Item_func_repeat::fix_length_and_dec()
|
|||||||
if (agg_arg_charsets_for_string_result(collation, args, 1))
|
if (agg_arg_charsets_for_string_result(collation, args, 1))
|
||||||
return TRUE;
|
return TRUE;
|
||||||
DBUG_ASSERT(collation.collation != NULL);
|
DBUG_ASSERT(collation.collation != NULL);
|
||||||
if (args[1]->const_item() && !args[1]->is_expensive())
|
if (args[1]->can_eval_in_optimize())
|
||||||
{
|
{
|
||||||
uint32 length= max_length_for_string(args[1]);
|
uint32 length= max_length_for_string(args[1]);
|
||||||
ulonglong char_length= (ulonglong) args[0]->max_char_length() * length;
|
ulonglong char_length= (ulonglong) args[0]->max_char_length() * length;
|
||||||
@ -3108,7 +3108,7 @@ err:
|
|||||||
bool Item_func_space::fix_length_and_dec()
|
bool Item_func_space::fix_length_and_dec()
|
||||||
{
|
{
|
||||||
collation.set(default_charset(), DERIVATION_COERCIBLE, MY_REPERTOIRE_ASCII);
|
collation.set(default_charset(), DERIVATION_COERCIBLE, MY_REPERTOIRE_ASCII);
|
||||||
if (args[0]->const_item() && !args[0]->is_expensive())
|
if (args[0]->can_eval_in_optimize())
|
||||||
{
|
{
|
||||||
fix_char_length_ulonglong(max_length_for_string(args[0]));
|
fix_char_length_ulonglong(max_length_for_string(args[0]));
|
||||||
return false;
|
return false;
|
||||||
@ -3228,7 +3228,7 @@ bool Item_func_pad::fix_length_and_dec()
|
|||||||
}
|
}
|
||||||
|
|
||||||
DBUG_ASSERT(collation.collation->mbmaxlen > 0);
|
DBUG_ASSERT(collation.collation->mbmaxlen > 0);
|
||||||
if (args[1]->const_item() && !args[1]->is_expensive())
|
if (args[1]->can_eval_in_optimize())
|
||||||
{
|
{
|
||||||
fix_char_length_ulonglong(max_length_for_string(args[1]));
|
fix_char_length_ulonglong(max_length_for_string(args[1]));
|
||||||
return false;
|
return false;
|
||||||
|
@ -1706,7 +1706,7 @@ public:
|
|||||||
Item_str_func(thd, a)
|
Item_str_func(thd, a)
|
||||||
{
|
{
|
||||||
collation.set(cs, DERIVATION_IMPLICIT);
|
collation.set(cs, DERIVATION_IMPLICIT);
|
||||||
if (cache_if_const && args[0]->const_item() && !args[0]->is_expensive())
|
if (cache_if_const && args[0]->can_eval_in_optimize())
|
||||||
{
|
{
|
||||||
uint errors= 0;
|
uint errors= 0;
|
||||||
String tmp, *str= args[0]->val_str(&tmp);
|
String tmp, *str= args[0]->val_str(&tmp);
|
||||||
|
@ -2775,7 +2775,7 @@ bool Item_in_subselect::create_in_to_exists_cond(JOIN *join_arg)
|
|||||||
/*
|
/*
|
||||||
The IN=>EXISTS transformation makes non-correlated subqueries correlated.
|
The IN=>EXISTS transformation makes non-correlated subqueries correlated.
|
||||||
*/
|
*/
|
||||||
if (!left_expr->const_item() || left_expr->is_expensive())
|
if (!left_expr->can_eval_in_optimize())
|
||||||
{
|
{
|
||||||
join_arg->select_lex->uncacheable|= UNCACHEABLE_DEPENDENT_INJECTED;
|
join_arg->select_lex->uncacheable|= UNCACHEABLE_DEPENDENT_INJECTED;
|
||||||
join_arg->select_lex->master_unit()->uncacheable|=
|
join_arg->select_lex->master_unit()->uncacheable|=
|
||||||
|
@ -668,7 +668,7 @@ public:
|
|||||||
|
|
||||||
void disable_cond_guard_for_const_null_left_expr(int i)
|
void disable_cond_guard_for_const_null_left_expr(int i)
|
||||||
{
|
{
|
||||||
if (left_expr->const_item() && !left_expr->is_expensive())
|
if (left_expr->can_eval_in_optimize())
|
||||||
{
|
{
|
||||||
if (left_expr->element_index(i)->is_null())
|
if (left_expr->element_index(i)->is_null())
|
||||||
set_cond_guard_var(i,FALSE);
|
set_cond_guard_var(i,FALSE);
|
||||||
|
@ -14368,7 +14368,7 @@ check_group_min_max_predicates(Item *cond, Item_field *min_max_arg_item,
|
|||||||
&has_min_max, &has_other))
|
&has_min_max, &has_other))
|
||||||
DBUG_RETURN(FALSE);
|
DBUG_RETURN(FALSE);
|
||||||
}
|
}
|
||||||
else if (cur_arg->const_item() && !cur_arg->is_expensive())
|
else if (cur_arg->can_eval_in_optimize())
|
||||||
{
|
{
|
||||||
/*
|
/*
|
||||||
For predicates of the form "const OP expr" we also have to check 'expr'
|
For predicates of the form "const OP expr" we also have to check 'expr'
|
||||||
|
@ -5939,8 +5939,7 @@ merge_key_fields(KEY_FIELD *start,KEY_FIELD *new_fields,KEY_FIELD *end,
|
|||||||
new_fields->null_rejecting);
|
new_fields->null_rejecting);
|
||||||
}
|
}
|
||||||
else if (old->eq_func && new_fields->eq_func &&
|
else if (old->eq_func && new_fields->eq_func &&
|
||||||
((old->val->const_item() && !old->val->is_expensive() &&
|
((old->val->can_eval_in_optimize() && old->val->is_null()) ||
|
||||||
old->val->is_null()) ||
|
|
||||||
(!new_fields->val->is_expensive() &&
|
(!new_fields->val->is_expensive() &&
|
||||||
new_fields->val->is_null())))
|
new_fields->val->is_null())))
|
||||||
{
|
{
|
||||||
@ -11212,8 +11211,7 @@ static void add_not_null_conds(JOIN *join)
|
|||||||
Item *item= tab->ref.items[keypart];
|
Item *item= tab->ref.items[keypart];
|
||||||
Item *notnull;
|
Item *notnull;
|
||||||
Item *real= item->real_item();
|
Item *real= item->real_item();
|
||||||
if (real->const_item() && real->type() != Item::FIELD_ITEM &&
|
if (real->can_eval_in_optimize() && real->type() != Item::FIELD_ITEM)
|
||||||
!real->is_expensive())
|
|
||||||
{
|
{
|
||||||
/*
|
/*
|
||||||
It could be constant instead of field after constant
|
It could be constant instead of field after constant
|
||||||
@ -14982,7 +14980,7 @@ bool check_simple_equality(THD *thd, const Item::Context &ctx,
|
|||||||
Item *orig_field_item= 0;
|
Item *orig_field_item= 0;
|
||||||
if (left_item->type() == Item::FIELD_ITEM &&
|
if (left_item->type() == Item::FIELD_ITEM &&
|
||||||
!((Item_field*)left_item)->get_depended_from() &&
|
!((Item_field*)left_item)->get_depended_from() &&
|
||||||
right_item->const_item() && !right_item->is_expensive())
|
right_item->can_eval_in_optimize())
|
||||||
{
|
{
|
||||||
orig_field_item= orig_left_item;
|
orig_field_item= orig_left_item;
|
||||||
field_item= (Item_field *) left_item;
|
field_item= (Item_field *) left_item;
|
||||||
@ -14990,7 +14988,7 @@ bool check_simple_equality(THD *thd, const Item::Context &ctx,
|
|||||||
}
|
}
|
||||||
else if (right_item->type() == Item::FIELD_ITEM &&
|
else if (right_item->type() == Item::FIELD_ITEM &&
|
||||||
!((Item_field*)right_item)->get_depended_from() &&
|
!((Item_field*)right_item)->get_depended_from() &&
|
||||||
left_item->const_item() && !left_item->is_expensive())
|
left_item->can_eval_in_optimize())
|
||||||
{
|
{
|
||||||
orig_field_item= orig_right_item;
|
orig_field_item= orig_right_item;
|
||||||
field_item= (Item_field *) right_item;
|
field_item= (Item_field *) right_item;
|
||||||
@ -16432,8 +16430,8 @@ propagate_cond_constants(THD *thd, I_List<COND_CMP> *save_list,
|
|||||||
{
|
{
|
||||||
Item_bool_func2 *func= dynamic_cast<Item_bool_func2*>(cond);
|
Item_bool_func2 *func= dynamic_cast<Item_bool_func2*>(cond);
|
||||||
Item **args= func->arguments();
|
Item **args= func->arguments();
|
||||||
bool left_const= args[0]->const_item() && !args[0]->is_expensive();
|
bool left_const= args[0]->can_eval_in_optimize();
|
||||||
bool right_const= args[1]->const_item() && !args[1]->is_expensive();
|
bool right_const= args[1]->can_eval_in_optimize();
|
||||||
if (!(left_const && right_const) &&
|
if (!(left_const && right_const) &&
|
||||||
args[0]->cmp_type() == args[1]->cmp_type())
|
args[0]->cmp_type() == args[1]->cmp_type())
|
||||||
{
|
{
|
||||||
@ -17736,7 +17734,7 @@ Item_cond::remove_eq_conds(THD *thd, Item::cond_result *cond_value,
|
|||||||
COND *
|
COND *
|
||||||
Item::remove_eq_conds(THD *thd, Item::cond_result *cond_value, bool top_level_arg)
|
Item::remove_eq_conds(THD *thd, Item::cond_result *cond_value, bool top_level_arg)
|
||||||
{
|
{
|
||||||
if (const_item() && !is_expensive())
|
if (can_eval_in_optimize())
|
||||||
{
|
{
|
||||||
*cond_value= eval_const_cond() ? Item::COND_TRUE : Item::COND_FALSE;
|
*cond_value= eval_const_cond() ? Item::COND_TRUE : Item::COND_FALSE;
|
||||||
return (COND*) 0;
|
return (COND*) 0;
|
||||||
@ -17750,7 +17748,7 @@ COND *
|
|||||||
Item_bool_func2::remove_eq_conds(THD *thd, Item::cond_result *cond_value,
|
Item_bool_func2::remove_eq_conds(THD *thd, Item::cond_result *cond_value,
|
||||||
bool top_level_arg)
|
bool top_level_arg)
|
||||||
{
|
{
|
||||||
if (const_item() && !is_expensive())
|
if (can_eval_in_optimize())
|
||||||
{
|
{
|
||||||
*cond_value= eval_const_cond() ? Item::COND_TRUE : Item::COND_FALSE;
|
*cond_value= eval_const_cond() ? Item::COND_TRUE : Item::COND_FALSE;
|
||||||
return (COND*) 0;
|
return (COND*) 0;
|
||||||
|
@ -725,7 +725,7 @@ uint Interval_DDhhmmssff::fsp(THD *thd, Item *item)
|
|||||||
case STRING_RESULT:
|
case STRING_RESULT:
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
if (!item->const_item() || item->is_expensive())
|
if (!item->can_eval_in_optimize())
|
||||||
return TIME_SECOND_PART_DIGITS;
|
return TIME_SECOND_PART_DIGITS;
|
||||||
Status st;
|
Status st;
|
||||||
Interval_DDhhmmssff it(thd, &st, false/*no warnings*/, item, UINT_MAX32,
|
Interval_DDhhmmssff it(thd, &st, false/*no warnings*/, item, UINT_MAX32,
|
||||||
|
Loading…
x
Reference in New Issue
Block a user