mirror of
https://github.com/MariaDB/server.git
synced 2025-07-29 05:21:33 +03:00
Bug #17043: Casting trimmed string to decimal loses precision
Results of string functions were being converted to decimals by first being converted to integers, resulting in a loss of precision. mysql-test/r/func_str.result: Add new results mysql-test/t/func_str.test: Add new regression test sql/item_strfunc.cc: Convert string function results to decimal using string-to-decimal conversion sql/item_strfunc.h: Add Item_str_func::val_decimal()
This commit is contained in:
@ -1030,3 +1030,13 @@ c res
|
|||||||
y,abc abc
|
y,abc abc
|
||||||
y,abc abc
|
y,abc abc
|
||||||
drop table t1;
|
drop table t1;
|
||||||
|
select cast(rtrim(' 20.06 ') as decimal(19,2));
|
||||||
|
cast(rtrim(' 20.06 ') as decimal(19,2))
|
||||||
|
20.06
|
||||||
|
select cast(ltrim(' 20.06 ') as decimal(19,2));
|
||||||
|
cast(ltrim(' 20.06 ') as decimal(19,2))
|
||||||
|
20.06
|
||||||
|
select cast(rtrim(ltrim(' 20.06 ')) as decimal(19,2));
|
||||||
|
cast(rtrim(ltrim(' 20.06 ')) as decimal(19,2))
|
||||||
|
20.06
|
||||||
|
End of 5.0 tests
|
||||||
|
@ -684,4 +684,11 @@ insert into t1 values ('y,abc'),('y,abc');
|
|||||||
select c, substring_index(lcase(c), @q:=',', -1) as res from t1;
|
select c, substring_index(lcase(c), @q:=',', -1) as res from t1;
|
||||||
drop table t1;
|
drop table t1;
|
||||||
|
|
||||||
# End of 5.0 tests
|
#
|
||||||
|
# Bug #17043: Casting trimmed string to decimal loses precision
|
||||||
|
#
|
||||||
|
select cast(rtrim(' 20.06 ') as decimal(19,2));
|
||||||
|
select cast(ltrim(' 20.06 ') as decimal(19,2));
|
||||||
|
select cast(rtrim(ltrim(' 20.06 ')) as decimal(19,2));
|
||||||
|
|
||||||
|
--echo End of 5.0 tests
|
||||||
|
@ -80,6 +80,20 @@ String *Item_str_func::check_well_formed_result(String *str)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
my_decimal *Item_str_func::val_decimal(my_decimal *decimal_value)
|
||||||
|
{
|
||||||
|
DBUG_ASSERT(fixed == 1);
|
||||||
|
char buff[64];
|
||||||
|
String *res, tmp(buff,sizeof(buff), &my_charset_bin);
|
||||||
|
res= val_str(&tmp);
|
||||||
|
if (!res)
|
||||||
|
return 0;
|
||||||
|
(void)str2my_decimal(E_DEC_FATAL_ERROR, (char*) res->ptr(),
|
||||||
|
res->length(), res->charset(), decimal_value);
|
||||||
|
return decimal_value;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
double Item_str_func::val_real()
|
double Item_str_func::val_real()
|
||||||
{
|
{
|
||||||
DBUG_ASSERT(fixed == 1);
|
DBUG_ASSERT(fixed == 1);
|
||||||
|
@ -33,6 +33,7 @@ public:
|
|||||||
Item_str_func(List<Item> &list) :Item_func(list) {decimals=NOT_FIXED_DEC; }
|
Item_str_func(List<Item> &list) :Item_func(list) {decimals=NOT_FIXED_DEC; }
|
||||||
longlong val_int();
|
longlong val_int();
|
||||||
double val_real();
|
double val_real();
|
||||||
|
my_decimal *val_decimal(my_decimal *);
|
||||||
enum Item_result result_type () const { return STRING_RESULT; }
|
enum Item_result result_type () const { return STRING_RESULT; }
|
||||||
void left_right_max_length();
|
void left_right_max_length();
|
||||||
String *check_well_formed_result(String *str);
|
String *check_well_formed_result(String *str);
|
||||||
|
Reference in New Issue
Block a user