From 1d1061eae6f4891e0d183b71e5ee94769ce311cb Mon Sep 17 00:00:00 2001 From: ZZemptypoint Date: Sat, 4 Feb 2023 21:44:59 +0800 Subject: [PATCH] =?UTF-8?q?fix=20bug=20Ipv4Util.list(String,String)?= =?UTF-8?q?=E6=96=B9=E6=B3=95=E7=94=9F=E6=88=90=E7=9A=84ip=E4=B8=8D?= =?UTF-8?q?=E5=85=A8;?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../java/cn/hutool/core/net/Ipv4Util.java | 37 ++++++++++++++----- .../java/cn/hutool/core/net/Ipv4UtilTest.java | 32 ++++++++++++++++ 2 files changed, 59 insertions(+), 10 deletions(-) diff --git a/hutool-core/src/main/java/cn/hutool/core/net/Ipv4Util.java b/hutool-core/src/main/java/cn/hutool/core/net/Ipv4Util.java index 15adb041c..10695b220 100755 --- a/hutool-core/src/main/java/cn/hutool/core/net/Ipv4Util.java +++ b/hutool-core/src/main/java/cn/hutool/core/net/Ipv4Util.java @@ -112,21 +112,38 @@ public class Ipv4Util { * @return 区间地址 */ public static List list(String ipFrom, String ipTo) { - final int[] ipf = Convert.convert(int[].class, StrUtil.splitToArray(ipFrom, CharUtil.DOT)); - final int[] ipt = Convert.convert(int[].class, StrUtil.splitToArray(ipTo, CharUtil.DOT)); + // 确定ip数量 + final int count = countByIpRange(ipFrom, ipTo); + final int[] from = Convert.convert(int[].class, StrUtil.splitToArray(ipFrom, CharUtil.DOT)); + final int[] to = Convert.convert(int[].class, StrUtil.splitToArray(ipTo, CharUtil.DOT)); - final List ips = new ArrayList<>(); - for (int a = ipf[0]; a <= ipt[0]; a++) { - for (int b = (a == ipf[0] ? ipf[1] : 0); b <= (a == ipt[0] ? ipt[1] - : 255); b++) { - for (int c = (b == ipf[1] ? ipf[2] : 0); c <= (b == ipt[1] ? ipt[2] - : 255); c++) { - for (int d = (c == ipf[2] ? ipf[3] : 0); d <= (c == ipt[2] ? ipt[3] - : 255); d++) { + final List ips = new ArrayList<>(count); + // 是否是循环的第一个值 + boolean aIsStart = true, bIsStart = true, cIsStart = true; + // 是否是循环的最后一个值 + boolean aIsEnd, bIsEnd, cIsEnd; + // 循环的结束值 + int aEnd = to[0], bEnd, cEnd, dEnd; + for (int a = from[0]; a <= aEnd; a++) { + aIsEnd = (a == aEnd); + // 本次循环的结束结束值 + bEnd = aIsEnd ? to[1] : 255; + for (int b = (aIsStart ? from[1] : 0); b <= bEnd; b++) { + // 在上一个循环是最后值的基础上进行判断 + bIsEnd = aIsEnd && (b == bEnd); + cEnd = bIsEnd ? to[2] : 255; + for (int c = (bIsStart ? from[2] : 0); c <= cEnd; c++) { + // 在之前循环是最后值的基础上进行判断 + cIsEnd = bIsEnd && (c == cEnd); + dEnd = cIsEnd ? to[3] : 255; + for (int d = (cIsStart ? from[3] : 0); d <= dEnd; d++) { ips.add(a + "." + b + "." + c + "." + d); } + cIsStart = false; } + bIsStart = false; } + aIsStart = false; } return ips; } diff --git a/hutool-core/src/test/java/cn/hutool/core/net/Ipv4UtilTest.java b/hutool-core/src/test/java/cn/hutool/core/net/Ipv4UtilTest.java index 3d590f9b0..f549852db 100644 --- a/hutool-core/src/test/java/cn/hutool/core/net/Ipv4UtilTest.java +++ b/hutool-core/src/test/java/cn/hutool/core/net/Ipv4UtilTest.java @@ -47,6 +47,38 @@ public class Ipv4UtilTest { int maskBit = Ipv4Util.getMaskBitByMask("255.255.255.0"); final List list = Ipv4Util.list("192.168.100.2", maskBit, false); Assert.assertEquals(254, list.size()); + + testGenerateIpList("10.1.0.1", "10.2.1.2"); + + testGenerateIpList("10.2.1.1", "10.2.1.2"); + testGenerateIpList("10.2.0.1", "10.2.1.2"); + testGenerateIpList("10.1.0.1", "10.2.1.2"); + testGenerateIpList("10.1.2.1", "10.2.1.2"); + + testGenerateIpList("10.2.1.2", "10.2.1.2"); + testGenerateIpList("10.2.0.2", "10.2.1.2"); + testGenerateIpList("10.1.1.2", "10.2.1.2"); + testGenerateIpList("10.1.2.2", "10.2.1.2"); + + testGenerateIpList("10.2.0.3", "10.2.1.2"); + testGenerateIpList("10.1.0.3", "10.2.1.2"); + testGenerateIpList("10.1.1.3", "10.2.1.2"); + testGenerateIpList("10.1.2.3", "10.2.1.2"); + + testGenerateIpList("9.255.2.1", "10.2.1.2"); + testGenerateIpList("9.255.2.2", "10.2.1.2"); + testGenerateIpList("9.255.2.3", "10.2.1.2"); + + testGenerateIpList("9.255.1.2", "10.2.1.2"); + testGenerateIpList("9.255.0.2", "10.2.1.2"); + testGenerateIpList("9.255.3.2", "10.2.1.2"); + } + + private void testGenerateIpList(final String fromIp, final String toIp) { + Assert.assertEquals( + Ipv4Util.countByIpRange(fromIp, toIp), + Ipv4Util.list(fromIp, toIp).size() + ); } @Test