diff --git a/hutool-core/src/main/java/cn/hutool/core/lang/Validator.java b/hutool-core/src/main/java/cn/hutool/core/lang/Validator.java index 5551832fff..839f06547e 100755 --- a/hutool-core/src/main/java/cn/hutool/core/lang/Validator.java +++ b/hutool-core/src/main/java/cn/hutool/core/lang/Validator.java @@ -9,6 +9,7 @@ import cn.hutool.core.util.ReUtil; import cn.hutool.core.util.StrUtil; import cn.hutool.core.util.IdcardUtil; +import java.math.BigDecimal; import java.net.MalformedURLException; import java.util.regex.Matcher; import java.util.regex.Pattern; @@ -1123,8 +1124,11 @@ public class Validator { Assert.notNull(value); Assert.notNull(min); Assert.notNull(max); - final double doubleValue = value.doubleValue(); - return (doubleValue >= min.doubleValue()) && (doubleValue <= max.doubleValue()); + // 通过 NumberUtil 转换为 BigDecimal,使用 BigDecimal 进行比较以保留精度 + BigDecimal valBd = NumberUtil.toBigDecimal(value); + BigDecimal minBd = NumberUtil.toBigDecimal(min); + BigDecimal maxBd = NumberUtil.toBigDecimal(max); + return valBd.compareTo(minBd) >= 0 && valBd.compareTo(maxBd) <= 0; } /** diff --git a/hutool-core/src/test/java/cn/hutool/core/lang/ValidatorTest.java b/hutool-core/src/test/java/cn/hutool/core/lang/ValidatorTest.java index 40be8a6d11..c09cb77df5 100755 --- a/hutool-core/src/test/java/cn/hutool/core/lang/ValidatorTest.java +++ b/hutool-core/src/test/java/cn/hutool/core/lang/ValidatorTest.java @@ -227,6 +227,19 @@ public class ValidatorTest { assertTrue(Validator.isBetween(0.19, 0.1, 0.2)); } + + @Test + public void isBetweenPrecisionLossTest() { + // 使用超过 double 精度的值 + long base = 10000000000000000L; + long min = base + 1; + long max = base + 2; + + // 在 double 转换下,base、min 和 max 是完全相等的,因为 double 精度不够 + // 预期结果为false,但是因为double 精度不够,导致输出为true + assertFalse(Validator.isBetween(base, min, max)); + } + @Test public void isCarVinTest() { assertTrue(Validator.isCarVin("LSJA24U62JG269225"));