Java之IP、子网掩码、网络号、广播地址之间转换与获取

时间:2024-03-03 12:03:25

一、判断子网掩码的有效性 

子网掩码满足的条件:

  1. 是一个合法的IP地址
  2. 掩码中的1是连续的
  3. 各类地址中掩码的范围(此文中不做判断)

Java实现:

 1 //掩码是否是连续1判断   
 2  private boolean IsSubnetMask(String netmask) {
 3         String[] masks = netmask.split("\\.");
 4         int mask = (Integer.parseInt(masks[0]) << 24) | (Integer.parseInt(masks[1]) << 16) | (Integer.parseInt(masks[2]) << 8) | Integer.parseInt(masks[3]);
 5         mask = ~mask + 1;
 6          if((mask & (mask - 1)) == 0) {
 7              return true;
 8         }else {
 9             return false;
10         }
11     }
12 
13 //是否是有效的IP地址
14  public boolean IsIpv4(String ipv4) {
15         if (ipv4 == null || ipv4.length() == 0) {
16             return false;
17         }
18         String[] parts = ipv4.split("\\.");
19         if (parts.length != 4) {
20             return false;
21         }
22         for (int i = 0; i < parts.length; ++i) {
23             try {
24                 int n = Integer.parseInt(parts[i]);
25                 if (n >= 0 && n <= 255) continue;
26                 return false;
27             }
28             catch (NumberFormatException e) {
29                 return false;
30             }
31         }
32         return true;
33     }

二、根据IP与子网掩码获取网络号和广播地址

网络号:子网掩码与IP相与,这里的实现方法是分成了四段,每段&后转成10进制就是网络号

广播号:子网掩码取反,然后将其与网络号取|

注意:

  • java中int占32位,如果我们的值没有32位,高位就会用0来填充,如果取反,切记要去除高位(本文用了 XX&0xFF的方法)
  • ">>"与 ”>>>“的区分

 Java实现:

 1 //根据IP与掩码获取网络号(环回地址)和广播地址
 2   private Map<String, String> getNetwork(String address, String netmask) {
 3           Map<String, String> map = new HashMap<String, String>();
 4           String network = new String();
 5           String broadcast = new String();
 6           String[] addresses = address.split("\\.");
 7           String[] masks = netmask.split("\\.");
 8            for(int i = 0; i < 4; i++) {
 9              int opmasksegement = ~Integer.parseInt(masks[i]) & 0xFF;
10         //此处有坑,正常的int有32位,如果此数没有32位的话,就会用0填充前面的数,从而导致取反0的部分会用1来填充,用上述方法可以获取想要的部分
11              int netsegment = Integer.parseInt(addresses[i]) & Integer.parseInt(masks[i]);
12              network = network + String.valueOf(netsegment) + ".";
13              broadcast = broadcast + String.valueOf(opmasksegement | netsegment) + ".";
14           }
15           map.put("network", network.substring(0, network.length() - 1));
16           map.put("broadcast", broadcast.substring(0, broadcast.length() - 1));
17          return map;
18      }  

三、判断IP是否在某个网段中

将IP与掩码相与,如果其与网络号相同,则返回true

 1 //判断IP是否在某个网段内
 2 private boolean isInRange(String ip, String netmask, String network) {
 3         String[] ips = ip.split("\\.");  
 4         int ipAddr = (Integer.parseInt(ips[0]) << 24) | (Integer.parseInt(ips[1]) << 16) | (Integer.parseInt(ips[2]) << 8) | Integer.parseInt(ips[3]); 
 5         String[] masks = netmask.split("\\.");
 6         int mask = (Integer.parseInt(masks[0]) << 24) | (Integer.parseInt(masks[1]) << 16) | (Integer.parseInt(masks[2]) << 8) | Integer.parseInt(masks[3]);
 7         String[] networks =network.split("\\.");
 8         int net = (Integer.parseInt(networks[0]) << 24) | (Integer.parseInt(networks[1]) << 16) | (Integer.parseInt(networks[2]) << 8) | Integer.parseInt(networks[3]);
 9         return (ipAddr & mask) == net;
10     }