Commit ee9a19fb authored by Alexander Barkov's avatar Alexander Barkov

MDEV-21392 Cleanup redundant overriding in Item_sum_num

parent b21dc119
......@@ -1093,19 +1093,6 @@ void Aggregator_distinct::endup()
}
String *
Item_sum_num::val_str(String *str)
{
return val_string_from_real(str);
}
my_decimal *Item_sum_num::val_decimal(my_decimal *decimal_value)
{
return val_decimal_from_real(decimal_value);
}
String *
Item_sum_int::val_str(String *str)
{
......@@ -2188,7 +2175,7 @@ static double variance_fp_recurrence_result(double s, ulonglong count, bool is_s
Item_sum_variance::Item_sum_variance(THD *thd, Item_sum_variance *item):
Item_sum_num(thd, item),
Item_sum_double(thd, item),
count(item->count), sample(item->sample),
prec_increment(item->prec_increment)
{
......@@ -2314,13 +2301,6 @@ double Item_sum_variance::val_real()
}
my_decimal *Item_sum_variance::val_decimal(my_decimal *dec_buf)
{
DBUG_ASSERT(fixed == 1);
return val_decimal_from_real(dec_buf);
}
void Item_sum_variance::reset_field()
{
double nr;
......
......@@ -578,6 +578,7 @@ class Item_sum :public Item_func_or_sum
void mark_as_window_func_sum_expr() { window_func_sum_expr_flag= true; }
bool is_window_func_sum_expr() { return window_func_sum_expr_flag; }
virtual void setup_caches(THD *thd) {};
virtual void set_partition_row_count(ulonglong count) { DBUG_ASSERT(0); }
};
......@@ -713,33 +714,45 @@ class Aggregator_simple : public Aggregator
class Item_sum_num :public Item_sum
{
protected:
/*
val_xxx() functions may be called several times during the execution of a
query. Derived classes that require extensive calculation in val_xxx()
maintain cache of aggregate value. This variable governs the validity of
that cache.
*/
bool is_evaluated;
public:
Item_sum_num(THD *thd): Item_sum(thd), is_evaluated(FALSE) {}
Item_sum_num(THD *thd): Item_sum(thd) {}
Item_sum_num(THD *thd, Item *item_par):
Item_sum(thd, item_par), is_evaluated(FALSE) {}
Item_sum(thd, item_par) {}
Item_sum_num(THD *thd, Item *a, Item* b):
Item_sum(thd, a, b), is_evaluated(FALSE) {}
Item_sum(thd, a, b) {}
Item_sum_num(THD *thd, List<Item> &list):
Item_sum(thd, list), is_evaluated(FALSE) {}
Item_sum(thd, list) {}
Item_sum_num(THD *thd, Item_sum_num *item):
Item_sum(thd, item),is_evaluated(item->is_evaluated) {}
Item_sum(thd, item) {}
bool fix_fields(THD *, Item **);
longlong val_int() { return val_int_from_real(); /* Real as default */ }
String *val_str(String*str);
my_decimal *val_decimal(my_decimal *);
void reset_field();
};
class Item_sum_double :public Item_sum_num
{
public:
Item_sum_double(THD *thd): Item_sum_num(thd) {}
Item_sum_double(THD *thd, Item *item_par): Item_sum_num(thd, item_par) {}
Item_sum_double(THD *thd, List<Item> &list): Item_sum_num(thd, list) {}
Item_sum_double(THD *thd, Item_sum_double *item) :Item_sum_num(thd, item) {}
longlong val_int()
{
return val_int_from_real();
}
String *val_str(String*str)
{
return val_string_from_real(str);
}
my_decimal *val_decimal(my_decimal *to)
{
return val_decimal_from_real(to);
}
bool get_date(MYSQL_TIME *ltime, ulonglong fuzzydate)
{
return type_handler()->Item_get_date(this, ltime, fuzzydate);
return get_date_from_real(ltime, fuzzydate);
}
void reset_field();
const Type_handler *type_handler() const { return &type_handler_double; }
};
......@@ -753,6 +766,10 @@ class Item_sum_int :public Item_sum_num
double val_real() { DBUG_ASSERT(fixed == 1); return (double) val_int(); }
String *val_str(String*str);
my_decimal *val_decimal(my_decimal *);
bool get_date(MYSQL_TIME *ltime, ulonglong fuzzydate)
{
return get_date_from_int(ltime, fuzzydate);
}
const Type_handler *type_handler() const { return &type_handler_longlong; }
bool fix_length_and_dec()
{ decimals=0; max_length=21; maybe_null=null_value=0; return FALSE; }
......@@ -794,6 +811,10 @@ class Item_sum_sum :public Item_sum_num,
longlong val_int();
String *val_str(String*str);
my_decimal *val_decimal(my_decimal *);
bool get_date(MYSQL_TIME *ltime, ulonglong fuzzydate)
{
return type_handler()->Item_get_date(this, ltime, fuzzydate);
}
const Type_handler *type_handler() const
{ return Type_handler_hybrid_field_type::type_handler(); }
void fix_length_and_dec_double();
......@@ -964,7 +985,7 @@ But, this falls prey to catastrophic cancellation. Instead, use the recurrence
*/
class Item_sum_variance : public Item_sum_num
class Item_sum_variance : public Item_sum_double
{
bool fix_length_and_dec();
......@@ -975,7 +996,7 @@ class Item_sum_variance : public Item_sum_num
uint prec_increment;
Item_sum_variance(THD *thd, Item *item_par, uint sample_arg):
Item_sum_num(thd, item_par), count(0),
Item_sum_double(thd, item_par), count(0),
sample(sample_arg)
{}
Item_sum_variance(THD *thd, Item_sum_variance *item);
......@@ -985,7 +1006,6 @@ class Item_sum_variance : public Item_sum_num
void clear();
bool add();
double val_real();
my_decimal *val_decimal(my_decimal *);
void reset_field();
void update_field();
Item *result_item(THD *thd, Field *field);
......@@ -994,11 +1014,10 @@ class Item_sum_variance : public Item_sum_num
{ return sample ? "var_samp(" : "variance("; }
Item *copy_or_same(THD* thd);
Field *create_tmp_field(bool group, TABLE *table);
const Type_handler *type_handler() const { return &type_handler_double; }
void cleanup()
{
count= 0;
Item_sum_num::cleanup();
Item_sum_double::cleanup();
}
Item *get_copy(THD *thd)
{ return get_item_copy<Item_sum_variance>(thd, this); }
......@@ -1679,15 +1698,15 @@ class Item_sum_udf_decimal :public Item_udf_sum
#else /* Dummy functions to get sql_yacc.cc compiled */
class Item_sum_udf_float :public Item_sum_num
class Item_sum_udf_float :public Item_sum_double
{
public:
Item_sum_udf_float(THD *thd, udf_func *udf_arg):
Item_sum_num(thd) {}
Item_sum_double(thd) {}
Item_sum_udf_float(THD *thd, udf_func *udf_arg, List<Item> &list):
Item_sum_num(thd) {}
Item_sum_double(thd) {}
Item_sum_udf_float(THD *thd, Item_sum_udf_float *item)
:Item_sum_num(thd, item) {}
:Item_sum_double(thd, item) {}
enum Sumfunctype sum_func () const { return UDF_SUM_FUNC; }
double val_real() { DBUG_ASSERT(fixed == 1); return 0.0; }
void clear() {}
......@@ -1696,15 +1715,15 @@ class Item_sum_udf_float :public Item_sum_num
};
class Item_sum_udf_int :public Item_sum_num
class Item_sum_udf_int :public Item_sum_double
{
public:
Item_sum_udf_int(THD *thd, udf_func *udf_arg):
Item_sum_num(thd) {}
Item_sum_double(thd) {}
Item_sum_udf_int(THD *thd, udf_func *udf_arg, List<Item> &list):
Item_sum_num(thd) {}
Item_sum_double(thd) {}
Item_sum_udf_int(THD *thd, Item_sum_udf_int *item)
:Item_sum_num(thd, item) {}
:Item_sum_double(thd, item) {}
enum Sumfunctype sum_func () const { return UDF_SUM_FUNC; }
longlong val_int() { DBUG_ASSERT(fixed == 1); return 0; }
double val_real() { DBUG_ASSERT(fixed == 1); return 0; }
......@@ -1714,15 +1733,15 @@ class Item_sum_udf_int :public Item_sum_num
};
class Item_sum_udf_decimal :public Item_sum_num
class Item_sum_udf_decimal :public Item_sum_double
{
public:
Item_sum_udf_decimal(THD *thd, udf_func *udf_arg):
Item_sum_num(thd) {}
Item_sum_double(thd) {}
Item_sum_udf_decimal(THD *thd, udf_func *udf_arg, List<Item> &list):
Item_sum_num(thd) {}
Item_sum_double(thd) {}
Item_sum_udf_decimal(THD *thd, Item_sum_udf_float *item)
:Item_sum_num(thd, item) {}
:Item_sum_double(thd, item) {}
enum Sumfunctype sum_func () const { return UDF_SUM_FUNC; }
double val_real() { DBUG_ASSERT(fixed == 1); return 0.0; }
my_decimal *val_decimal(my_decimal *) { DBUG_ASSERT(fixed == 1); return 0; }
......@@ -1732,15 +1751,15 @@ class Item_sum_udf_decimal :public Item_sum_num
};
class Item_sum_udf_str :public Item_sum_num
class Item_sum_udf_str :public Item_sum_double
{
public:
Item_sum_udf_str(THD *thd, udf_func *udf_arg):
Item_sum_num(thd) {}
Item_sum_double(thd) {}
Item_sum_udf_str(THD *thd, udf_func *udf_arg, List<Item> &list):
Item_sum_num(thd) {}
Item_sum_double(thd) {}
Item_sum_udf_str(THD *thd, Item_sum_udf_str *item)
:Item_sum_num(thd, item) {}
:Item_sum_double(thd, item) {}
String *val_str(String *)
{ DBUG_ASSERT(fixed == 1); null_value=1; return 0; }
double val_real() { DBUG_ASSERT(fixed == 1); null_value=1; return 0.0; }
......
......@@ -438,27 +438,38 @@ class Item_sum_lag : public Item_sum_hybrid_simple
{ return get_item_copy<Item_sum_lag>(thd, this); }
};
/*
A base window function (aggregate) that also holds a counter for the number
of rows.
*/
class Item_sum_window_with_row_count : public Item_sum_num
{
public:
Item_sum_window_with_row_count(THD *thd) : Item_sum_num(thd),
partition_row_count_(0) {}
Item_sum_window_with_row_count(THD *thd, Item *arg) :
Item_sum_num(thd, arg), partition_row_count_(0) {};
void set_row_count(ulonglong count) { partition_row_count_ = count; }
protected:
class Partition_row_count
{
public:
Partition_row_count() :partition_row_count_(0) { }
void set_partition_row_count(ulonglong count)
{
partition_row_count_ = count;
}
double calc_val_real(bool *null_value,
ulonglong current_row_count)
{
if ((*null_value= (partition_row_count_ == 0)))
return 0;
return static_cast<double>(current_row_count) / partition_row_count_;
}
protected:
longlong get_row_count() { return partition_row_count_; }
private:
ulonglong partition_row_count_;
};
class Current_row_count
{
public:
Current_row_count() :current_row_count_(0) { }
protected:
ulonglong get_row_number() { return current_row_count_ ; }
ulonglong current_row_count_;
};
/*
@detail
"The relative rank of a row R is defined as (RK-1)/(NR-1), where RK is
......@@ -470,11 +481,12 @@ class Item_sum_window_with_row_count : public Item_sum_num
This is held within the row_count context.
- Second pass to compute rank of current row and the value of the function
*/
class Item_sum_percent_rank: public Item_sum_window_with_row_count
class Item_sum_percent_rank: public Item_sum_double,
public Partition_row_count
{
public:
Item_sum_percent_rank(THD *thd)
: Item_sum_window_with_row_count(thd), cur_rank(1), peer_tracker(NULL) {}
: Item_sum_double(thd), cur_rank(1), peer_tracker(NULL) {}
longlong val_int()
{
......@@ -527,6 +539,12 @@ class Item_sum_percent_rank: public Item_sum_window_with_row_count
}
void setup_window_func(THD *thd, Window_spec *window_spec);
void set_partition_row_count(ulonglong count)
{
Partition_row_count::set_partition_row_count(count);
}
Item *get_copy(THD *thd)
{ return get_item_copy<Item_sum_percent_rank>(thd, this); }
......@@ -561,25 +579,17 @@ class Item_sum_percent_rank: public Item_sum_window_with_row_count
two passes.
*/
class Item_sum_cume_dist: public Item_sum_window_with_row_count
class Item_sum_cume_dist: public Item_sum_double,
public Partition_row_count,
public Current_row_count
{
public:
Item_sum_cume_dist(THD *thd) : Item_sum_window_with_row_count(thd),
current_row_count_(0) {}
Item_sum_cume_dist(THD *thd, Item *arg) : Item_sum_window_with_row_count(thd,arg),
current_row_count_(0) {}
Item_sum_cume_dist(THD *thd) :Item_sum_double(thd) { }
Item_sum_cume_dist(THD *thd, Item *arg) :Item_sum_double(thd, arg) { }
double val_real()
{
if (get_row_count() == 0)
{
null_value= true;
return 0;
}
ulonglong partition_row_count= get_row_count();
null_value= false;
return static_cast<double>(current_row_count_) / partition_row_count;
return calc_val_real(&null_value, current_row_count_);
}
bool add()
......@@ -596,7 +606,7 @@ class Item_sum_cume_dist: public Item_sum_window_with_row_count
void clear()
{
current_row_count_= 0;
set_row_count(0);
partition_row_count_= 0;
}
const char*func_name() const
......@@ -614,29 +624,24 @@ class Item_sum_cume_dist: public Item_sum_window_with_row_count
return FALSE;
}
Item *get_copy(THD *thd)
{ return get_item_copy<Item_sum_cume_dist>(thd, this); }
ulonglong get_row_number()
void set_partition_row_count(ulonglong count)
{
return current_row_count_ ;
Partition_row_count::set_partition_row_count(count);
}
private:
ulonglong current_row_count_;
Item *get_copy(THD *thd)
{ return get_item_copy<Item_sum_cume_dist>(thd, this); }
};
class Item_sum_ntile : public Item_sum_window_with_row_count
class Item_sum_ntile : public Item_sum_int,
public Partition_row_count,
public Current_row_count
{
public:
Item_sum_ntile(THD* thd, Item* num_quantiles_expr) :
Item_sum_window_with_row_count(thd, num_quantiles_expr),
current_row_count_(0) {};
double val_real()
{
return (double) val_int();
}
Item_sum_int(thd, num_quantiles_expr)
{ }
longlong val_int()
{
......@@ -677,7 +682,7 @@ class Item_sum_ntile : public Item_sum_window_with_row_count
void clear()
{
current_row_count_= 0;
set_row_count(0);
partition_row_count_= 0;
}
const char*func_name() const
......@@ -687,21 +692,25 @@ class Item_sum_ntile : public Item_sum_window_with_row_count
void update_field() {}
const Type_handler *type_handler() const { return &type_handler_longlong; }
void set_partition_row_count(ulonglong count)
{
Partition_row_count::set_partition_row_count(count);
}
Item *get_copy(THD *thd)
{ return get_item_copy<Item_sum_ntile>(thd, this); }
private:
longlong get_num_quantiles() { return args[0]->val_int(); }
ulong current_row_count_;
};
class Item_sum_percentile_disc : public Item_sum_cume_dist,
public Type_handler_hybrid_field_type
class Item_sum_percentile_disc : public Item_sum_num,
public Type_handler_hybrid_field_type,
public Partition_row_count,
public Current_row_count
{
public:
Item_sum_percentile_disc(THD *thd, Item* arg) : Item_sum_cume_dist(thd, arg),
Item_sum_percentile_disc(THD *thd, Item* arg) : Item_sum_num(thd, arg),
Type_handler_hybrid_field_type(&type_handler_longlong),
value(NULL), val_calculated(FALSE), first_call(TRUE),
prev_value(0), order_item(NULL){}
......@@ -750,6 +759,17 @@ class Item_sum_percentile_disc : public Item_sum_cume_dist,
return value->val_str(str);
}
bool get_date(MYSQL_TIME *ltime, ulonglong fuzzydate)
{
if (get_row_count() == 0 || get_arg(0)->is_null())
{
null_value= true;
return 0;
}
null_value= false;
return value->get_date(ltime, fuzzydate);
}
bool add()
{
Item *arg= get_arg(0);
......@@ -783,8 +803,8 @@ class Item_sum_percentile_disc : public Item_sum_cume_dist,
if (value->null_value)
return false;
Item_sum_cume_dist::add();
double val= Item_sum_cume_dist::val_real();
current_row_count_++;
double val= calc_val_real(&null_value, current_row_count_);
if (val >= prev_value && !val_calculated)
val_calculated= true;
......@@ -801,7 +821,8 @@ class Item_sum_percentile_disc : public Item_sum_cume_dist,
val_calculated= false;
first_call= true;
value->clear();
Item_sum_cume_dist::clear();
partition_row_count_= 0;
current_row_count_= 0;
}
const char*func_name() const
......@@ -810,7 +831,6 @@ class Item_sum_percentile_disc : public Item_sum_cume_dist,
}
void update_field() {}
void set_type_handler(Window_spec *window_spec);
const Type_handler *type_handler() const
{return Type_handler_hybrid_field_type::type_handler();}
......@@ -821,6 +841,11 @@ class Item_sum_percentile_disc : public Item_sum_cume_dist,
return FALSE;
}
void set_partition_row_count(ulonglong count)
{
Partition_row_count::set_partition_row_count(count);
}
Item *get_copy(THD *thd)
{ return get_item_copy<Item_sum_percentile_disc>(thd, this); }
void setup_window_func(THD *thd, Window_spec *window_spec);
......@@ -835,12 +860,12 @@ class Item_sum_percentile_disc : public Item_sum_cume_dist,
Item *order_item;
};
class Item_sum_percentile_cont : public Item_sum_cume_dist,
public Type_handler_hybrid_field_type
class Item_sum_percentile_cont : public Item_sum_double,
public Partition_row_count,
public Current_row_count
{
public:
Item_sum_percentile_cont(THD *thd, Item* arg) : Item_sum_cume_dist(thd, arg),
Type_handler_hybrid_field_type(&type_handler_double),
Item_sum_percentile_cont(THD *thd, Item* arg) : Item_sum_double(thd, arg),
floor_value(NULL), ceil_value(NULL), first_call(TRUE),prev_value(0),
ceil_val_calculated(FALSE), floor_val_calculated(FALSE), order_item(NULL){}
......@@ -910,7 +935,7 @@ class Item_sum_percentile_cont : public Item_sum_cume_dist,
return false;
}
Item_sum_cume_dist::add();
current_row_count_++;
double val= 1 + prev_value * (get_row_count()-1);
if (!floor_val_calculated && get_row_number() == floor(val))
......@@ -933,7 +958,8 @@ class Item_sum_percentile_cont : public Item_sum_cume_dist,
ceil_value->clear();
floor_val_calculated= false;
ceil_val_calculated= false;
Item_sum_cume_dist::clear();
partition_row_count_= 0;
current_row_count_= 0;
}
const char*func_name() const
......@@ -941,9 +967,6 @@ class Item_sum_percentile_cont : public Item_sum_cume_dist,
return "percentile_cont";
}
void update_field() {}
void set_type_handler(Window_spec *window_spec);
const Type_handler *type_handler() const
{return Type_handler_hybrid_field_type::type_handler();}
bool fix_length_and_dec()
{
......@@ -952,6 +975,11 @@ class Item_sum_percentile_cont : public Item_sum_cume_dist,
return FALSE;
}
void set_partition_row_count(ulonglong count)
{
Partition_row_count::set_partition_row_count(count);
}
Item *get_copy(THD *thd)
{ return get_item_copy<Item_sum_percentile_cont>(thd, this); }
void setup_window_func(THD *thd, Window_spec *window_spec);
......
......@@ -1779,11 +1779,7 @@ class Frame_unbounded_following_set_count : public Frame_unbounded_following
List_iterator_fast<Item_sum> it(sum_functions);
Item_sum* item;
while ((item= it++))
{
Item_sum_window_with_row_count* item_with_row_count =
static_cast<Item_sum_window_with_row_count *>(item);
item_with_row_count->set_row_count(num_rows_in_partition);
}
item->set_partition_row_count(num_rows_in_partition);
}
};
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment