You've already forked mariadb-columnstore-engine
mirror of
https://github.com/mariadb-corporation/mariadb-columnstore-engine.git
synced 2025-07-29 08:21:15 +03:00
MCOL-641 Add support for functions (Part 1).
This commit is contained in:
committed by
Roman Nozdrin
parent
554c6da8e8
commit
cfe35b5c7f
@ -256,14 +256,24 @@ public:
|
||||
(datatypes::Decimal::isWideDecimalType(decimal.precision)) ?
|
||||
decimal.s128Value : decimal.value;
|
||||
|
||||
int128_t scaleMultiplier, result;
|
||||
int128_t scaleMultiplier;
|
||||
int32_t scaleDiff = fResultType.scale - decimal.scale;
|
||||
datatypes::getScaleDivisor(scaleMultiplier, abs(scaleDiff));
|
||||
// WIP MCOL-641 Unconditionall overflow check
|
||||
datatypes::MultiplicationOverflowCheck mul;
|
||||
decimal.s128Value = (scaleDiff > 0
|
||||
&& mul(decimal.s128Value, scaleMultiplier, result))
|
||||
? result : decimal.s128Value / scaleMultiplier;
|
||||
if (scaleMultiplier > 1)
|
||||
{
|
||||
if (scaleDiff > 0)
|
||||
{
|
||||
// WIP MCOL-641 Unconditionall overflow check
|
||||
datatypes::MultiplicationNoOverflowCheck mul;
|
||||
mul(decimal.s128Value, scaleMultiplier, decimal.s128Value);
|
||||
}
|
||||
else
|
||||
{
|
||||
decimal.s128Value = (int128_t)(decimal.s128Value > 0 ?
|
||||
(__float128)decimal.s128Value / scaleMultiplier + 0.5 :
|
||||
(__float128)decimal.s128Value / scaleMultiplier - 0.5);
|
||||
}
|
||||
}
|
||||
}
|
||||
else if (fResultType.colWidth == utils::MAXLEGACYWIDTH)
|
||||
{
|
||||
|
@ -63,17 +63,16 @@ typedef execplan::CalpontSystemCatalog::ColType Type;
|
||||
*/
|
||||
struct IDB_Decimal
|
||||
{
|
||||
IDB_Decimal(): value(0), scale(0), precision(0)
|
||||
IDB_Decimal(): s128Value(0), value(0), scale(0), precision(0)
|
||||
{
|
||||
s128Value = 0;
|
||||
}
|
||||
|
||||
IDB_Decimal(int64_t val, int8_t s, uint8_t p) :
|
||||
value (val),
|
||||
IDB_Decimal(int64_t val, int8_t s, uint8_t p, int128_t val128 = 0) :
|
||||
s128Value(val128),
|
||||
value(val),
|
||||
scale(s),
|
||||
precision(p)
|
||||
{
|
||||
s128Value = 0;
|
||||
}
|
||||
|
||||
int decimalComp(const IDB_Decimal& d) const
|
||||
@ -117,13 +116,32 @@ struct IDB_Decimal
|
||||
|
||||
bool operator==(const IDB_Decimal& rhs) const
|
||||
{
|
||||
if (utils::widthByPrecision(precision) == 16)
|
||||
if (precision > datatypes::INT64MAXPRECISION &&
|
||||
rhs.precision > datatypes::INT64MAXPRECISION)
|
||||
{
|
||||
if (scale == rhs.scale)
|
||||
return s128Value == rhs.s128Value;
|
||||
else
|
||||
return (datatypes::Decimal::compare(*this, rhs) == 0);
|
||||
}
|
||||
else if (precision > datatypes::INT64MAXPRECISION &&
|
||||
rhs.precision <= datatypes::INT64MAXPRECISION)
|
||||
{
|
||||
const_cast<IDB_Decimal&>(rhs).s128Value = rhs.value;
|
||||
|
||||
if (scale == rhs.scale)
|
||||
return s128Value == rhs.s128Value;
|
||||
else
|
||||
return (datatypes::Decimal::compare(*this, rhs) == 0);
|
||||
}
|
||||
else if (precision <= datatypes::INT64MAXPRECISION &&
|
||||
rhs.precision > datatypes::INT64MAXPRECISION)
|
||||
{
|
||||
if (scale == rhs.scale)
|
||||
return (int128_t) value == rhs.s128Value;
|
||||
else
|
||||
return (datatypes::Decimal::compare(IDB_Decimal(0, scale, precision, (int128_t) value), rhs) == 0);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (scale == rhs.scale)
|
||||
@ -135,13 +153,32 @@ struct IDB_Decimal
|
||||
|
||||
bool operator>(const IDB_Decimal& rhs) const
|
||||
{
|
||||
if (utils::widthByPrecision(precision) == 16)
|
||||
if (precision > datatypes::INT64MAXPRECISION &&
|
||||
rhs.precision > datatypes::INT64MAXPRECISION)
|
||||
{
|
||||
if (scale == rhs.scale)
|
||||
return s128Value > rhs.s128Value;
|
||||
else
|
||||
return (datatypes::Decimal::compare(*this, rhs) > 0);
|
||||
}
|
||||
else if (precision > datatypes::INT64MAXPRECISION &&
|
||||
rhs.precision <= datatypes::INT64MAXPRECISION)
|
||||
{
|
||||
IDB_Decimal rhstmp(0, rhs.scale, rhs.precision, (int128_t) rhs.value);
|
||||
|
||||
if (scale == rhstmp.scale)
|
||||
return s128Value > rhstmp.s128Value;
|
||||
else
|
||||
return (datatypes::Decimal::compare(*this, rhstmp) > 0);
|
||||
}
|
||||
else if (precision <= datatypes::INT64MAXPRECISION &&
|
||||
rhs.precision > datatypes::INT64MAXPRECISION)
|
||||
{
|
||||
if (scale == rhs.scale)
|
||||
return (int128_t) value > rhs.s128Value;
|
||||
else
|
||||
return (datatypes::Decimal::compare(IDB_Decimal(0, scale, precision, (int128_t) value), rhs) > 0);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (scale == rhs.scale)
|
||||
@ -153,13 +190,32 @@ struct IDB_Decimal
|
||||
|
||||
bool operator<(const IDB_Decimal& rhs) const
|
||||
{
|
||||
if (utils::widthByPrecision(precision) == 16)
|
||||
if (precision > datatypes::INT64MAXPRECISION &&
|
||||
rhs.precision > datatypes::INT64MAXPRECISION)
|
||||
{
|
||||
if (scale == rhs.scale)
|
||||
return s128Value < rhs.s128Value;
|
||||
else
|
||||
return (datatypes::Decimal::compare(*this, rhs) < 0);
|
||||
}
|
||||
else if (precision > datatypes::INT64MAXPRECISION &&
|
||||
rhs.precision <= datatypes::INT64MAXPRECISION)
|
||||
{
|
||||
IDB_Decimal rhstmp(0, rhs.scale, rhs.precision, (int128_t) rhs.value);
|
||||
|
||||
if (scale == rhstmp.scale)
|
||||
return s128Value < rhstmp.s128Value;
|
||||
else
|
||||
return (datatypes::Decimal::compare(*this, rhstmp) < 0);
|
||||
}
|
||||
else if (precision <= datatypes::INT64MAXPRECISION &&
|
||||
rhs.precision > datatypes::INT64MAXPRECISION)
|
||||
{
|
||||
if (scale == rhs.scale)
|
||||
return (int128_t) value < rhs.s128Value;
|
||||
else
|
||||
return (datatypes::Decimal::compare(IDB_Decimal(0, scale, precision, (int128_t) value), rhs) < 0);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (scale == rhs.scale)
|
||||
@ -171,13 +227,32 @@ struct IDB_Decimal
|
||||
|
||||
bool operator>=(const IDB_Decimal& rhs) const
|
||||
{
|
||||
if (utils::widthByPrecision(precision) == 16)
|
||||
if (precision > datatypes::INT64MAXPRECISION &&
|
||||
rhs.precision > datatypes::INT64MAXPRECISION)
|
||||
{
|
||||
if (scale == rhs.scale)
|
||||
return s128Value >= rhs.s128Value;
|
||||
else
|
||||
return (datatypes::Decimal::compare(*this, rhs) >= 0);
|
||||
}
|
||||
else if (precision > datatypes::INT64MAXPRECISION &&
|
||||
rhs.precision <= datatypes::INT64MAXPRECISION)
|
||||
{
|
||||
IDB_Decimal rhstmp(0, rhs.scale, rhs.precision, (int128_t) rhs.value);
|
||||
|
||||
if (scale == rhstmp.scale)
|
||||
return s128Value >= rhstmp.s128Value;
|
||||
else
|
||||
return (datatypes::Decimal::compare(*this, rhstmp) >= 0);
|
||||
}
|
||||
else if (precision <= datatypes::INT64MAXPRECISION &&
|
||||
rhs.precision > datatypes::INT64MAXPRECISION)
|
||||
{
|
||||
if (scale == rhs.scale)
|
||||
return (int128_t) value >= rhs.s128Value;
|
||||
else
|
||||
return (datatypes::Decimal::compare(IDB_Decimal(0, scale, precision, (int128_t) value), rhs) >= 0);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (scale == rhs.scale)
|
||||
@ -189,13 +264,32 @@ struct IDB_Decimal
|
||||
|
||||
bool operator<=(const IDB_Decimal& rhs) const
|
||||
{
|
||||
if (utils::widthByPrecision(precision) == 16)
|
||||
if (precision > datatypes::INT64MAXPRECISION &&
|
||||
rhs.precision > datatypes::INT64MAXPRECISION)
|
||||
{
|
||||
if (scale == rhs.scale)
|
||||
return s128Value <= rhs.s128Value;
|
||||
else
|
||||
return (datatypes::Decimal::compare(*this, rhs) <= 0);
|
||||
}
|
||||
else if (precision > datatypes::INT64MAXPRECISION &&
|
||||
rhs.precision <= datatypes::INT64MAXPRECISION)
|
||||
{
|
||||
IDB_Decimal rhstmp(0, rhs.scale, rhs.precision, (int128_t) rhs.value);
|
||||
|
||||
if (scale == rhstmp.scale)
|
||||
return s128Value <= rhstmp.s128Value;
|
||||
else
|
||||
return (datatypes::Decimal::compare(*this, rhstmp) <= 0);
|
||||
}
|
||||
else if (precision <= datatypes::INT64MAXPRECISION &&
|
||||
rhs.precision > datatypes::INT64MAXPRECISION)
|
||||
{
|
||||
if (scale == rhs.scale)
|
||||
return (int128_t) value <= rhs.s128Value;
|
||||
else
|
||||
return (datatypes::Decimal::compare(IDB_Decimal(0, scale, precision, (int128_t) value), rhs) <= 0);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (scale == rhs.scale)
|
||||
@ -207,13 +301,32 @@ struct IDB_Decimal
|
||||
|
||||
bool operator!=(const IDB_Decimal& rhs) const
|
||||
{
|
||||
if (utils::widthByPrecision(precision) == 16)
|
||||
if (precision > datatypes::INT64MAXPRECISION &&
|
||||
rhs.precision > datatypes::INT64MAXPRECISION)
|
||||
{
|
||||
if (scale == rhs.scale)
|
||||
return s128Value != rhs.s128Value;
|
||||
else
|
||||
return (datatypes::Decimal::compare(*this, rhs) != 0);
|
||||
}
|
||||
else if (precision > datatypes::INT64MAXPRECISION &&
|
||||
rhs.precision <= datatypes::INT64MAXPRECISION)
|
||||
{
|
||||
IDB_Decimal rhstmp(0, rhs.scale, rhs.precision, (int128_t) rhs.value);
|
||||
|
||||
if (scale == rhstmp.scale)
|
||||
return s128Value != rhstmp.s128Value;
|
||||
else
|
||||
return (datatypes::Decimal::compare(*this, rhstmp) != 0);
|
||||
}
|
||||
else if (precision <= datatypes::INT64MAXPRECISION &&
|
||||
rhs.precision > datatypes::INT64MAXPRECISION)
|
||||
{
|
||||
if (scale == rhs.scale)
|
||||
return (int128_t) value != rhs.s128Value;
|
||||
else
|
||||
return (datatypes::Decimal::compare(IDB_Decimal(0, scale, precision, (int128_t) value), rhs) != 0);
|
||||
}
|
||||
else
|
||||
{
|
||||
if (scale == rhs.scale)
|
||||
@ -308,7 +421,7 @@ struct Result
|
||||
{
|
||||
Result(): intVal(0), uintVal(0), origIntVal(0), dummy(0),
|
||||
doubleVal(0), longDoubleVal(0), floatVal(0), boolVal(false),
|
||||
strVal(""), decimalVal(IDB_Decimal(0, 0, 0)),
|
||||
strVal(""), decimalVal(IDB_Decimal()),
|
||||
valueConverted(false) {}
|
||||
int64_t intVal;
|
||||
uint64_t uintVal;
|
||||
@ -783,7 +896,10 @@ inline const std::string& TreeNode::getStrVal(const std::string& timeZone)
|
||||
case CalpontSystemCatalog::DECIMAL:
|
||||
case CalpontSystemCatalog::UDECIMAL:
|
||||
{
|
||||
dataconvert::DataConvert::decimalToString(fResult.decimalVal.value, fResult.decimalVal.scale, tmp, 22, fResultType.colDataType);
|
||||
if (fResultType.colWidth == datatypes::MAXDECIMALWIDTH)
|
||||
dataconvert::DataConvert::decimalToString(&fResult.decimalVal.s128Value, fResult.decimalVal.scale, tmp, utils::MAXLENGTH16BYTES, fResultType.colDataType);
|
||||
else
|
||||
dataconvert::DataConvert::decimalToString(fResult.decimalVal.value, fResult.decimalVal.scale, tmp, 22, fResultType.colDataType);
|
||||
fResult.strVal = std::string(tmp);
|
||||
break;
|
||||
}
|
||||
@ -880,7 +996,20 @@ inline int64_t TreeNode::getIntVal()
|
||||
case CalpontSystemCatalog::DECIMAL:
|
||||
case CalpontSystemCatalog::UDECIMAL:
|
||||
{
|
||||
return (int64_t)(fResult.decimalVal.value / pow((double)10, fResult.decimalVal.scale));
|
||||
if (fResultType.colWidth == datatypes::MAXDECIMALWIDTH)
|
||||
{
|
||||
int128_t scaleDivisor;
|
||||
|
||||
datatypes::getScaleDivisor(scaleDivisor, fResult.decimalVal.scale);
|
||||
|
||||
int128_t tmpval = fResult.decimalVal.s128Value / scaleDivisor;
|
||||
|
||||
return datatypes::Decimal::getInt64FromWideDecimal(tmpval);
|
||||
}
|
||||
else
|
||||
{
|
||||
return (int64_t)(fResult.decimalVal.value / pow((double)10, fResult.decimalVal.scale));
|
||||
}
|
||||
}
|
||||
|
||||
case CalpontSystemCatalog::DATE:
|
||||
@ -1062,8 +1191,15 @@ inline double TreeNode::getDoubleVal()
|
||||
case CalpontSystemCatalog::DECIMAL:
|
||||
case CalpontSystemCatalog::UDECIMAL:
|
||||
{
|
||||
// this may not be accurate. if this is problematic, change to pre-calculated power array.
|
||||
return (double)(fResult.decimalVal.value / pow((double)10, fResult.decimalVal.scale));
|
||||
if (fResultType.colWidth == datatypes::MAXDECIMALWIDTH)
|
||||
{
|
||||
return datatypes::Decimal::getDoubleFromWideDecimal(fResult.decimalVal.s128Value, fResult.decimalVal.scale);
|
||||
}
|
||||
else
|
||||
{
|
||||
// this may not be accurate. if this is problematic, change to pre-calculated power array.
|
||||
return (double)(fResult.decimalVal.value / pow((double)10, fResult.decimalVal.scale));
|
||||
}
|
||||
}
|
||||
|
||||
case CalpontSystemCatalog::DATE:
|
||||
|
Reference in New Issue
Block a user