4

以下のようなIP配列があり、それを最小のcidrサブネットリストに変換したいと思います。Javaにそのためのライブラリはありますか?

例えば:

1.1.3.0
1.1.3.1
1.1.3.2
1.1.3.3
..
1.1.3.254
1.1.3.255
1.2.3.0
1.2.3.1
1.2.3.2
1.2.3.3
..
1.2.3.254
1.2.3.255
1.3.3.0
1.3.3.1
1.3.3.2
1.3.3.3
..
1.3.3.128
1.3.3.129

に変換

1.1.3.0/24
1.2.3.0/24
1.3.3.0/25
1.3.3.128/31

前もって感謝します。

4

3 に答える 3

2

Javaで利用できるライブラリがあるかどうかはわかりません。確かに、私はJavaについてほとんど知りません:)しかし、それが助けになるなら、私はあなたに問題を解決するためのアルゴリズムを与えることができます。

1)IPアドレスを整数のペアに変換します。最初の整数はIPアドレスのバイナリ表現(abcd-> a << 24 + b << 16 + c << 8 + d)で、2番目の整数は32です。 (つまり、最初は各アドレスはそれ自身のサブネットです[1])。

2)ペアのリストを並べ替えます。

3)次に、2番目のペアから始めて、ソートされたリストをスキャンします。ペアごとに、前のペアと組み合わせることができる場合は、それを行い、可能な限り組み合わせるまで試してください。2つのペア[base1, bits1]であり、およびの[base2, bits2]場合は組み合わせることができます。その場合、組み合わせはです。bits1 == bits2base2 ^ base1 == 1 << (32 - bits1)[base1, bits1 - 1]

4)最後に、ペアをCIDR表記に変換し直します。最初の整数はサブネットのベース(ドット付き10進に変換して戻す場合)であり、2番目の整数はビット幅です。

ステップ2と3はどちらもO(n log n)

脚注1:あなたの例では、最後のバイトが0のアドレスを含めていません。これは、私のアルゴリズムがテストケースで失敗することを意味します。それらをリストに追加する必要があります。この点は、CIDRサブネットとは何かの定義における微妙ですが重要な詳細を明らかにします。技術的には、範囲の最初と最後のIPの両方が予約されているため、可能な最小のサブネットは/30です。したがって、/31には有効なIPアドレスがありません。ただし、CIDRサブネットという用語は、フィルター式として使用する場合のように、「IPアドレスのセットを認識するビットマスク」を意味するためによく使用されます。

于 2012-09-20T17:08:09.963 に答える
1

There is a library available in Java for this. The open-source IPAddress Java library has methods for merging addresses into prefix block subnets. Disclaimer: I am the project manager of the IPAddress library.

The following method "merge" shows the code, relying on the method mergeToPrefixBlocks from the library:

static String[] merge(List<String> strs) {
    // convert first to address
    IPAddress first = new IPAddressString(strs.get(0)).getAddress();
    // convert remaining to address
    IPAddress others[] = strs.subList(1, strs.size()).stream().map(str -> new IPAddressString(str).getAddress()).toArray(IPAddress[]::new);
    // merge them all
    IPAddress[] blocks = first.mergeToPrefixBlocks(others);
    // convert back to strings
    return Arrays.stream(blocks).map(block -> block.toString()).toArray(String[]::new);
}

The method can be demonstrated with your set of example addresses as shown with the following code:

ArrayList<String> strs = new ArrayList<>();
String firstPref = "1.1.3.";
String secondPref = "1.2.3.";
String thirdPref = "1.3.3.";
for(int i = 0; i <= 255; i++) {
    strs.add(firstPref + i);
    strs.add(secondPref + i);
}           
for(int i = 0; i <= 129; i++) {
    strs.add(thirdPref + i);
}
String result[] = merge(strs);
System.out.println("blocks are " + Arrays.asList(result));

The output is:

blocks are [1.3.3.128/31, 1.3.3.0/25, 1.1.3.0/24, 1.2.3.0/24]
于 2019-03-25T04:40:14.413 に答える
-6

Try as :

public class Test {
    public static void main(String[] args) {
        String[] ipArray1 = new String[]{"1.1.3.1", "1.1.3.3", "1.1.3.2", "1.3.3.254"};
        String[] ipArray2 = new String[ipArray1.length];
        for(int i=0; i < ipArray1.length; i++) {
            String temp = ipArray1[i];
            ipArray2[i] = temp.substring(0,6) + "0/24";
        }
        for(String  ip : ipArray2) {
            System.out.println(ip);
        }
    }
}

Output :

    1.1.3.0/24
    1.1.3.0/24
    1.1.3.0/24
    1.3.3.0/24
于 2012-09-20T15:29:14.840 に答える