当前位置: 首页 > 面试题库 >

在Java中,给定IP地址范围,返回覆盖该范围的最小CIDR块列表

魏楷
2023-03-14
问题内容

我在将IP地址范围转换为CIDR块列表时遇到一些逻辑上的麻烦。我确实相信这个网站做对了:http :
//ip2cidr.com/

我想输入一个起始IP地址和一个结束IP地址,并让Java吐出CIDR块的最小列表,以仅覆盖传入的范围,仅此而已。

例如,如果我传入的起始地址为1.1.1.111,终止地址为1.1.1.120,则我希望得到回报:1.1.1.111/32 1.1.1.112/29
1.1.1.120/32

(/ 32表示单个地址。)


问题答案:

我的最后一个答案中包含一些错误,这些错误是由于IP地址的第一个八位字节太大而引起的。这个效果更好。几乎完全从这里解除:http : //facedroid.blogspot.com/2010/06/ip-range-to-
cidr.html

import java.util.ArrayList;
import java.util.List;

public class RangeToCidr {
    public static List<String> range2cidrlist( String startIp, String endIp ) {         
        long start = ipToLong(startIp);         
        long end = ipToLong(endIp);

        ArrayList<String> pairs = new ArrayList<String>();         
        while ( end >= start ) {             
            byte maxsize = 32;             
            while ( maxsize > 0) {                 
                long mask = CIDR2MASK[ maxsize -1 ];                 
                long maskedBase = start & mask;

                if ( maskedBase != start ) {                     
                    break;                 
                }

                maxsize--;             
            }               
            double x = Math.log( end - start + 1) / Math.log( 2 );             
            byte maxdiff = (byte)( 32 - Math.floor( x ) );             
            if ( maxsize < maxdiff) {                 
                maxsize = maxdiff;             
            }             
            String ip = longToIP(start);             
            pairs.add( ip + "/" + maxsize);             
            start += Math.pow( 2, (32 - maxsize) );         
        }         
        return pairs;     
    }

    public static final int[] CIDR2MASK = new int[] { 0x00000000, 0x80000000,             
        0xC0000000, 0xE0000000, 0xF0000000, 0xF8000000, 0xFC000000,             
        0xFE000000, 0xFF000000, 0xFF800000, 0xFFC00000, 0xFFE00000,             
        0xFFF00000, 0xFFF80000, 0xFFFC0000, 0xFFFE0000, 0xFFFF0000,             
        0xFFFF8000, 0xFFFFC000, 0xFFFFE000, 0xFFFFF000, 0xFFFFF800,             
        0xFFFFFC00, 0xFFFFFE00, 0xFFFFFF00, 0xFFFFFF80, 0xFFFFFFC0,             
        0xFFFFFFE0, 0xFFFFFFF0, 0xFFFFFFF8, 0xFFFFFFFC, 0xFFFFFFFE,             
        0xFFFFFFFF };

    private static long ipToLong(String strIP) {         
        long[] ip = new long[4];         
        String[] ipSec = strIP.split("\\.");         
        for (int k = 0; k < 4; k++) {             
            ip[k] = Long.valueOf(ipSec[k]);         
        }

        return (ip[0] << 24) + (ip[1] << 16) + (ip[2] << 8) + ip[3];     
    }

    private static String longToIP(long longIP) {         
        StringBuffer sb = new StringBuffer("");         
        sb.append(String.valueOf(longIP >>> 24));         
        sb.append(".");         
        sb.append(String.valueOf((longIP & 0x00FFFFFF) >>> 16));         
        sb.append(".");         
        sb.append(String.valueOf((longIP & 0x0000FFFF) >>> 8));         
        sb.append(".");         
        sb.append(String.valueOf(longIP & 0x000000FF));

        return sb.toString();     
    } 
}


 类似资料:
  • 问题内容: 我希望能够根据其他两个IP范围内的IP返回true / false。 例如: 结果应为true。 其他例子: 问题答案: 检查范围的最简单方法可能是将IP地址转换为32位整数,然后比较这些整数。 而不是,您可能想要查看具有InetAddresses帮助器类的Guava库,该类避免了DNS查找的可能性。

  • 我对C#UTF8编码感到困惑... 假设这些“事实”是正确的: Unicode是定义每个字符的“协议” 根据C#参考,每个字符的可接受范围为0x0000到0xFFFF。我不明白另一个字符是什么,它在0xFFFF之上,在Unicode协议中定义的? 与C#相比,当我使用Python编写UTF8文本时-它涵盖了所有预期范围(0x0000到0x10FFFF)。例如: 这对C不起作用。此外,当我将Pyth

  • 问题内容: 如何从起始IP地址和结束IP地址生成一系列IP地址? 网络“ 192.168.0.0/24”的示例: 我希望有: PS:网络,起始和结束IP可以是动态的,上面仅是一个示例。 谢谢… 问题答案: 认识到IPv4地址的4个组成部分实际上都是00到FF之间的十六进制数字。 如果将起始IP地址和结束IP地址更改为32位无符号整数,则可以从最低的一个循环到最高的一个,然后将循环通过的每个值转换回

  • 我有来自Microsoft Azure数据中心(http://www.microsoft.com/en-us/download/confirmation.aspx?id=41653)的900个IP地址范围,我想知道IP地址是否来自其中一个地址。我已经把它转换成一个列表,可以存储在文本文件中。 所以:循环遍历每个地址并使用ip2long()如这里的第3点是否成本更高(https://mebsd.co

  • 问题内容: 我有一个表,其中包含一列作为CIDR值,例如,我还有其他2列(start_ip_range和end_ip_range),我想填充这2列FROM CIDR列 Java代码可能如下所示: 如何将其转换为MySql查询。 问题答案: 你可以这样转换 询问 样品表 或者,您可以在虚拟列中使用它。因此,您可以直接获得正确的值。 虚拟领域

  • 我试图找出使用PHP从一系列IP地址中获取单个/24 IP块的最佳/最有效的方法。 我有一个MySQL数据库中的IP地址范围(我不能改变这是如何呈现的),必须有单独的范围的 /24块保存,也以特定的方式(我不能改变MySQL条目,也不能改变软件如何处理列表)。 例如,我有各种范围的IPv4 IP地址在这种格式: 我需要将其保存为此特定格式,以表示给定地址范围内的每个/24块: 我对如何在不写非常复