12
12
You should have received a copy of the GNU General Public License
13
13
along with this program; if not, write to the Free Software
14
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA */
14
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */
33
33
#include <drizzled/item/sum.h>
34
34
#include <drizzled/field/decimal.h>
35
35
#include <drizzled/field/double.h>
36
#include <drizzled/field/int64.h>
36
#include <drizzled/field/int64_t.h>
37
37
#include <drizzled/field/date.h>
38
38
#include <drizzled/field/datetime.h>
509
509
uint32_t convert_blob_length)
513
512
switch (result_type()) {
514
513
case REAL_RESULT:
515
514
field= new Field_double(max_length, maybe_null, name, decimals, true);
519
field= new field::Int64(max_length, maybe_null, name, unsigned_flag);
517
field= new Field_int64_t(max_length, maybe_null, name, unsigned_flag);
522
519
case STRING_RESULT:
523
520
if (max_length/collation.collation->mbmaxlen <= 255 ||
524
521
convert_blob_length > Field_varstring::MAX_SIZE ||
525
522
!convert_blob_length)
527
523
return make_string_field(table);
530
table->setVariableWidth();
531
524
field= new Field_varstring(convert_blob_length, maybe_null,
532
name, collation.collation);
525
name, table->getMutableShare(), collation.collation);
535
527
case DECIMAL_RESULT:
536
528
field= new Field_decimal(max_length, maybe_null, name,
537
decimals, unsigned_flag);
529
decimals, unsigned_flag);
541
533
// This case should never be choosen
547
538
field->init(table);
806
798
case DECIMAL_RESULT:
808
/* SUM result can't be longer than length(arg) + length(MAX_ROWS) */
809
int precision= args[0]->decimal_precision() + DECIMAL_LONGLONG_DIGITS;
810
max_length= my_decimal_precision_to_length(precision, decimals,
813
hybrid_type= DECIMAL_RESULT;
814
my_decimal_set_zero(dec_buffs);
800
/* SUM result can't be longer than length(arg) + length(MAX_ROWS) */
801
int precision= args[0]->decimal_precision() + DECIMAL_LONGLONG_DIGITS;
802
max_length= my_decimal_precision_to_length(precision, decimals,
805
hybrid_type= DECIMAL_RESULT;
806
my_decimal_set_zero(dec_buffs);
970
964
table_field_type= DRIZZLE_TYPE_DOUBLE;
974
Preserving int8, int16, int32 field types gives ~10% performance boost
975
as the size of result tree becomes significantly smaller.
976
Another speed up we gain by using int64_t for intermediate
977
calculations. The range of int64 is enough to hold sum 2^32 distinct
978
integers each <= 2^32.
980
if (table_field_type == DRIZZLE_TYPE_LONG)
982
val.traits= Hybrid_type_traits_fast_decimal::instance();
985
table_field_type= DRIZZLE_TYPE_LONGLONG;
968
Preserving int8, int16, int32 field types gives ~10% performance boost
969
as the size of result tree becomes significantly smaller.
970
Another speed up we gain by using int64_t for intermediate
971
calculations. The range of int64 is enough to hold sum 2^32 distinct
972
integers each <= 2^32.
974
if (table_field_type == DRIZZLE_TYPE_LONG)
976
val.traits= Hybrid_type_traits_fast_decimal::instance();
979
table_field_type= DRIZZLE_TYPE_LONGLONG;
987
981
case DECIMAL_RESULT:
988
982
val.traits= Hybrid_type_traits_decimal::instance();
989
983
if (table_field_type != DRIZZLE_TYPE_LONGLONG)
990
984
table_field_type= DRIZZLE_TYPE_DECIMAL;
996
990
val.traits->fix_length_and_dec(this, args[0]);
1031
1025
field_def.init_for_tmp_table(table_field_type, args[0]->max_length,
1032
1026
args[0]->decimals, args[0]->maybe_null);
1034
if (! (table= session->getInstanceTable(field_list)))
1028
if (! (table= session->create_virtual_tmp_table(field_list)))
1037
1031
/* XXX: check that the case of CHAR(0) works OK */
1261
1255
The easiest way is to do this is to store both value in a string
1262
1256
and unpack on access.
1264
table->setVariableWidth();
1265
1258
field= new Field_varstring(((hybrid_type == DECIMAL_RESULT) ?
1266
1259
dec_bin_size : sizeof(double)) + sizeof(int64_t),
1267
0, name, &my_charset_bin);
1260
0, name, table->getMutableShare(), &my_charset_bin);
1269
1262
else if (hybrid_type == DECIMAL_RESULT)
1270
1263
field= new Field_decimal(max_length, maybe_null, name,
1441
1434
case INT_RESULT:
1442
1435
case DECIMAL_RESULT:
1444
int precision= args[0]->decimal_precision()*2 + prec_increment;
1445
decimals= min(args[0]->decimals + prec_increment, (unsigned int) DECIMAL_MAX_SCALE);
1446
max_length= my_decimal_precision_to_length(precision, decimals,
1437
int precision= args[0]->decimal_precision()*2 + prec_increment;
1438
decimals= min(args[0]->decimals + prec_increment, (unsigned int) DECIMAL_MAX_SCALE);
1439
max_length= my_decimal_precision_to_length(precision, decimals,
1451
1444
case ROW_RESULT:
1476
1471
The easiest way is to do this is to store both value in a string
1477
1472
and unpack on access.
1479
table->setVariableWidth();
1480
field= new Field_varstring(sizeof(double)*2 + sizeof(int64_t), 0, name, &my_charset_bin);
1474
field= new Field_varstring(sizeof(double)*2 + sizeof(int64_t), 0, name, table->getMutableShare(), &my_charset_bin);
1483
1477
field= new Field_double(max_length, maybe_null, name, decimals, true);
1619
1613
assert(fixed == 1);
1620
1614
if (null_value)
1623
1616
switch (hybrid_type) {
1624
1617
case STRING_RESULT:
1628
String *res; res=val_str(&str_value);
1629
return (res ? my_strntod(res->charset(), (char*) res->ptr(), res->length(),
1630
&end_not_used, &err_not_used) : 0.0);
1621
String *res; res=val_str(&str_value);
1622
return (res ? my_strntod(res->charset(), (char*) res->ptr(), res->length(),
1623
&end_not_used, &err_not_used) : 0.0);
1632
1625
case INT_RESULT:
1633
1626
return (double) sum_int;
1634
1627
case DECIMAL_RESULT:
1757
1747
switch (hybrid_type) {
1758
1748
case STRING_RESULT:
1750
String *result=args[0]->val_str(&tmp_value);
1751
if (!args[0]->null_value &&
1752
(null_value || sortcmp(&value,result,collation.collation) > 0))
1760
String *result=args[0]->val_str(&tmp_value);
1761
if (!args[0]->null_value &&
1762
(null_value || sortcmp(&value,result,collation.collation) > 0))
1764
value.copy(*result);
1754
value.copy(*result);
1769
1759
case INT_RESULT:
1761
int64_t nr=args[0]->val_int();
1762
if (!args[0]->null_value && (null_value ||
1764
(uint64_t) nr < (uint64_t) sum_int) ||
1765
(!unsigned_flag && nr < sum_int)))
1771
int64_t nr=args[0]->val_int();
1772
if (!args[0]->null_value && (null_value ||
1774
(uint64_t) nr < (uint64_t) sum_int) ||
1775
(!unsigned_flag && nr < sum_int)))
1782
1772
case DECIMAL_RESULT:
1774
my_decimal value_buff, *val= args[0]->val_decimal(&value_buff);
1775
if (!args[0]->null_value &&
1776
(null_value || (my_decimal_cmp(&sum_dec, val) > 0)))
1784
my_decimal value_buff, *val= args[0]->val_decimal(&value_buff);
1785
if (!args[0]->null_value &&
1786
(null_value || (my_decimal_cmp(&sum_dec, val) > 0)))
1788
my_decimal2decimal(val, &sum_dec);
1778
my_decimal2decimal(val, &sum_dec);
1793
1783
case REAL_RESULT:
1785
double nr= args[0]->val_real();
1786
if (!args[0]->null_value && (null_value || nr < sum))
1795
double nr= args[0]->val_real();
1796
if (!args[0]->null_value && (null_value || nr < sum))
1803
1793
case ROW_RESULT:
1804
1795
// This case should never be choosen
1820
1811
switch (hybrid_type) {
1821
1812
case STRING_RESULT:
1814
String *result=args[0]->val_str(&tmp_value);
1815
if (!args[0]->null_value &&
1816
(null_value || sortcmp(&value,result,collation.collation) < 0))
1823
String *result=args[0]->val_str(&tmp_value);
1824
if (!args[0]->null_value &&
1825
(null_value || sortcmp(&value,result,collation.collation) < 0))
1827
value.copy(*result);
1818
value.copy(*result);
1832
1823
case INT_RESULT:
1825
int64_t nr=args[0]->val_int();
1826
if (!args[0]->null_value && (null_value ||
1828
(uint64_t) nr > (uint64_t) sum_int) ||
1829
(!unsigned_flag && nr > sum_int)))
1834
int64_t nr=args[0]->val_int();
1835
if (!args[0]->null_value && (null_value ||
1837
(uint64_t) nr > (uint64_t) sum_int) ||
1838
(!unsigned_flag && nr > sum_int)))
1845
1836
case DECIMAL_RESULT:
1838
my_decimal value_buff, *val= args[0]->val_decimal(&value_buff);
1839
if (!args[0]->null_value &&
1840
(null_value || (my_decimal_cmp(val, &sum_dec) > 0)))
1847
my_decimal value_buff, *val= args[0]->val_decimal(&value_buff);
1848
if (!args[0]->null_value &&
1849
(null_value || (my_decimal_cmp(val, &sum_dec) > 0)))
1851
my_decimal2decimal(val, &sum_dec);
1842
my_decimal2decimal(val, &sum_dec);
1856
1847
case REAL_RESULT:
1849
double nr= args[0]->val_real();
1850
if (!args[0]->null_value && (null_value || nr > sum))
1858
double nr= args[0]->val_real();
1859
if (!args[0]->null_value && (null_value || nr > sum))
1866
1857
case ROW_RESULT:
1867
1859
// This case should never be choosen
1957
1948
switch(hybrid_type) {
1958
1949
case STRING_RESULT:
1960
char buff[MAX_FIELD_WIDTH];
1961
String tmp(buff,sizeof(buff),result_field->charset()),*res;
1963
res=args[0]->val_str(&tmp);
1964
if (args[0]->null_value)
1951
char buff[MAX_FIELD_WIDTH];
1952
String tmp(buff,sizeof(buff),result_field->charset()),*res;
1954
res=args[0]->val_str(&tmp);
1955
if (args[0]->null_value)
1957
result_field->set_null();
1958
result_field->reset();
1962
result_field->set_notnull();
1963
result_field->store(res->ptr(),res->length(),tmp.charset());
1969
int64_t nr=args[0]->val_int();
1973
if (args[0]->null_value)
1976
result_field->set_null();
1979
result_field->set_notnull();
1981
result_field->store(nr, unsigned_flag);
1986
double nr= args[0]->val_real();
1990
if (args[0]->null_value)
1993
result_field->set_null();
1996
result_field->set_notnull();
1998
result_field->store(nr);
2001
case DECIMAL_RESULT:
2003
my_decimal value_buff, *arg_dec= args[0]->val_decimal(&value_buff);
2007
if (args[0]->null_value)
1966
2008
result_field->set_null();
1967
result_field->reset();
1971
2010
result_field->set_notnull();
1972
result_field->store(res->ptr(),res->length(),tmp.charset());
1978
int64_t nr=args[0]->val_int();
1982
if (args[0]->null_value)
1985
result_field->set_null();
1988
result_field->set_notnull();
1990
result_field->store(nr, unsigned_flag);
1995
double nr= args[0]->val_real();
1999
if (args[0]->null_value)
2002
result_field->set_null();
2005
result_field->set_notnull();
2007
result_field->store(nr);
2010
case DECIMAL_RESULT:
2012
my_decimal value_buff, *arg_dec= args[0]->val_decimal(&value_buff);
2016
if (args[0]->null_value)
2017
result_field->set_null();
2019
result_field->set_notnull();
2022
We must store zero in the field as we will use the field value in
2025
if (!arg_dec) // Null
2026
arg_dec= &decimal_zero;
2027
result_field->store_decimal(arg_dec);
2013
We must store zero in the field as we will use the field value in
2016
if (!arg_dec) // Null
2017
arg_dec= &decimal_zero;
2018
result_field->store_decimal(arg_dec);
2030
2021
case ROW_RESULT:
2237
2228
if (!args[0]->null_value)
2239
result_field->val_str_internal(&tmp_value);
2230
result_field->val_str(&tmp_value);
2241
2232
if (result_field->is_null() ||
2242
2233
(cmp_sign * sortcmp(res_str,&tmp_value,collation.collation)) < 0)
2608
2599
tmp_table_param->force_copy_fields= force_copy_fields;
2609
2600
assert(table == 0);
2611
if (!(table= create_tmp_table(session, tmp_table_param, list, (Order*) 0, 1,
2602
if (!(table= create_tmp_table(session, tmp_table_param, list, (order_st*) 0, 1,
2613
2604
(select_lex->options | session->options),
2614
2605
HA_POS_ERROR, (char*)"")))
2719
2710
if (always_null)
2721
2712
copy_fields(tmp_table_param);
2722
if (copy_funcs(tmp_table_param->items_to_copy, table->in_use))
2713
copy_funcs(tmp_table_param->items_to_copy);
2725
2715
for (Field **field= table->getFields() ; *field ; field++)
2844
2834
const void* key2)
2846
2836
Item_func_group_concat* grp_item= (Item_func_group_concat*) arg;
2847
Order **order_item, **end;
2837
order_st **order_item, **end;
2848
2838
Table *table= grp_item->table;
2850
2840
for (order_item= grp_item->order, end=order_item+ grp_item->arg_count_order;
2918
2908
uint32_t offset= (field->offset(field->getTable()->record[0]) -
2919
2909
table->getShare()->null_bytes);
2920
2910
assert(offset < table->getShare()->getRecordLength());
2921
res= field->val_str_internal(&tmp, key + offset);
2911
res= field->val_str(&tmp, key + offset);
2924
2914
res= (*arg)->val_str(&tmp);
2988
2978
order - arg_count_order
2990
2980
if (!(args= (Item**) memory::sql_alloc(sizeof(Item*) * arg_count +
2991
sizeof(Order*)*arg_count_order)))
2981
sizeof(order_st*)*arg_count_order)))
2994
order= (Order**)(args + arg_count);
2984
order= (order_st**)(args + arg_count);
2996
2986
/* fill args items of show and sort */
2997
2987
List_iterator_fast<Item> li(*select_list);
3002
2992
if (arg_count_order)
3004
Order **order_ptr= order;
3005
for (Order *order_item= (Order*) order_list->first;
2994
order_st **order_ptr= order;
2995
for (order_st *order_item= (order_st*) order_list->first;
3006
2996
order_item != NULL;
3007
2997
order_item= order_item->next)
3272
3261
if (!(table= create_tmp_table(session, tmp_table_param, all_fields,
3273
(Order*) 0, 0, true,
3262
(order_st*) 0, 0, true,
3274
3263
(select_lex->options | session->options),
3275
3264
HA_POS_ERROR, (char*) "")))