MySQL中Regexp结果转Decimal丢失小数位,硬编码字符串正常
问题描述
在MySQL 8.0.21版本中执行以下SQL语句:
select regexp_substr('56.948959;24.121503|56.950469;24.119765', '^[0-9\.]+') raw_txt, cast('56.948959' as decimal(10,8)) just_cast, case when regexp_substr('56.948959;24.121503|56.950469;24.119765', '^[0-9\.]+') = '56.948959' then 'yisss' else 'nope' end text_comparison, cast(regexp_substr('56.948959;24.121503|56.950469;24.119765', '^[0-9\.]+') as decimal(10,8)) full_decimal, cast(regexp_substr('56.948959;24.121503|56.950469;24.119765', '^[0-9\.]+') as double) full_double
得到结果:
raw_txt: 56.948959 just_cast: 56.94895900 text_comparison: yisss full_decimal: 56.00000000 full_double: 56.948959
其中full_decimal丢失了小数位,但硬编码字符串转Decimal的just_cast正常,文本比对显示Regexp结果与硬编码字符串一致,转Double也正常,请问该现象的原因是什么?
原因分析
- REGEXP_SUBSTR返回二进制字符串:MySQL 8.0.21版本中,
REGEXP_SUBSTR的匹配结果是二进制字符集(binary)的字符串,而硬编码字符串使用的是默认字符集(如utf8mb4)。 - 二进制字符串转DECIMAL的特殊逻辑:当把二进制字符串
CAST为DECIMAL类型时,MySQL会逐字符解析,将.判定为非数字字符,仅保留小数点前的整数部分,导致小数位丢失。 - 其他操作正常的原因:
- 文本比对时,MySQL会自动将二进制字符串转换为与硬编码字符串相同的字符集,因此比对结果一致。
CAST为DOUBLE的解析逻辑不同于DECIMAL,能正确识别二进制字符串中的小数点,转换结果正常。- 硬编码字符串属于默认字符集,
CAST到DECIMAL时按常规数字字符串解析,不会触发截断问题。
内容的提问来源于stack exchange,提问作者Vilx-
相关产品推荐
相关产品推荐

