判断一个字符串是否是有效IP(包括IPv4和IPv6)

  1. IPv4是 Internet Protocol version 4 的缩写,表示IP协议的第四个版本。现在互联网上绝大多数的通信流量都是以IPv4数据包的格式封装的。IPv4使用32位2进制位的地址,因此IPv4的地址空间是 2^32 = 4294967296。IPv4通常用点分十进制记法书写,例如192.168.0.1,其中的数字都是十进制的数字,中间用实心圆点分隔
          一个IPv4地址可以分为网络地址和主机地址两部分,其中网络地址可以使用如下形式描述:192.168.0.0/16,其中斜线后的数字表示网络地址部分的长度是16位,这对应2个字节,即网络地址部分是192.168.0.0。
          为了便于对IP地址进行管理, 根据IPv4地址的第一个字节,IPv4地址可以分为以下五类。
A类:0~127
B类:128~191
C类:192~223
D类:224~239,组播地址
E类:240~254,保留为研究测试使用

2.IPv6的128位地址通常写成8组,每组为四个十六进制数的形式。比如:AD80:0000:0000:0000:ABAA:0000:00C2:0002 是一个合法的IPv6地址。这个地址比较长,看起来不方便也不易于书写。零压缩法可以用来缩减其长度。如果几个连续段位的值都是0,那么这些0就可以简单的以::来表示,上述地址就可写成AD80::ABAA:0000:00C2:0002。这里要注意的是只能简化连续的段位的0,其前后的0都要保留,比如AD80的最后的这个0,不能被简化。还有这个只能用一次,在上例中的ABAA后面的0000就不能再次简化。当然也可以在AAAA后面使用::,这样的话前面的12个0就不能压缩了。这个限制的目的是为了能准确还原被压缩的0,不然就无法确定每个::代表了多少个0。例如,下面是一些合法的IPv6地址:
CDCD:910A:2222:5498:8475:1111:3900:2020
1030::C9B4:FF12:48AA:1A2B
2000:0:0:0:0:0:0:1
同时前导的零可以省略,因此2001:0DB8:02de::0e13等价于2001:DB8:2de::e13。
     一个IPv6地址可以将一个IPv4地址内嵌进去,并且写成IPv6形式和平常习惯的IPv4形式的混合体。IPv6有两种内嵌IPv4的方式:IPv4映像地址和IPv4兼容地址。

/**
 * Created by yguo on 2017/8/25.
 * @ 输入:字符串
 * @ 输出:这个字符串是不是有效ip(分别判断了IPv4和IPv6)
 * @ note: 在IPv4中 0.0.0.0段的ip视为无效
 *         在IPv6中 :: 视为有效ip
 */

//**判断规则:first 首先判断字符串是否只包含数字,(:),(.)
//                  如果不成立,直接输出不是有效ip
//            second 判断是否只包含 数字和(.)
//                  如果成立判断是否是有效IPv4 --> IPv4断定
//                  如果不成立,判断是否是有效IPv6
//  using Java
import java.util.Scanner;
import java.util.regex.Pattern;

public class Main {
    public static void main(String[] args) {
        Scanner s = new Scanner(System.in);
        while (s.hasNext()) {
            String str = s.nextLine();
            if(!Pattern.matches("[0-9a-fA-F:.]+",str)){
                System.out.println("不是一个有效的ip地址");
            }else if(Pattern.matches("[0-9]+[.][0-9]+[.][0-9]+[.][0-9]+",str)){  //判断是否是ipv4格式
               isIPv4(str);
            }
            //==========以下为IPv6的判断=================
            else if(Pattern.matches("([0-9a-fA-F]{1,4}[:]){7}[0-9a-fA-F]{1,4}",str)){
                System.out.println("是一个有效的ip地址");
            }else if(str == "::"){
                System.out.println("是一个有效的ip地址");
            }else if(Pattern.matches("^(([0-9a-f]{1,4}:){1,6})((:[0-9a-f]{1,4}){1,6})",str)){//判断2::2:2:22是否有效
                str = str.replaceAll(":"," ");
                String[] strings = str.split("\\s+");
                if(str.length() <=7){
                    System.out.println("是一个有效的ip地址");
                }else
                    System.out.println("不是一个有效的ip地址");
            }else if(Pattern.matches("([0-9a-fA-F]{1,4}:){1,7}:",str)){   //判断 1:1::
                System.out.println("是一个有效的ip地址");
            }
            else if(Pattern.matches(":(:[0-9a-fA-F]{1,4}){1,7}",str)) {  //判断 ::1:1
                System.out.println("是一个有效的ip地址");
            }else if(Pattern.matches("([0-9a-fA-F]{1,4}:){6}(([0-9]+.){3}[0-9]+)",str)){  //判断 4:4:4:4:4:4:10.90.20.0是否有效
                str = str.substring(str.lastIndexOf(":")+1,str.length());
                iPv6IncludeIPv4(str);
            }else if(Pattern.matches("([0-9a-fA-F]{1,4}:){1,5}:(([0-9]+.){3}[0-9]+)",str)){ // 判断 1::1.1.1.1
                str = str.substring(str.lastIndexOf(":")+1,str.length());
                iPv6IncludeIPv4(str);
            }else if(Pattern.matches("::([0-9a-fA-F]{1,4}:){0,5}(([0-9]+.){3}[0-9]+)",str)){  // 判断  ::1.1.1.1
                str = str.substring(str.lastIndexOf(":")+1,str.length());
                iPv6IncludeIPv4(str);
            }else if(Pattern.matches("([0-9a-fA-F]{1,4}:){1,4}(:[0-9a-fA-F]{1,4}){1,4}:(([0-9]+.){3}[0-9]+)",str)){  //判断 1::1:1:1.1.1.1
                String m = str.substring(0,str.lastIndexOf(":"));
                String[] mm = m.replaceAll(":"," ").split("\\s+");
                if(mm.length <= 5){
                    str = str.substring(str.lastIndexOf(":")+1,str.length());
                    iPv6IncludeIPv4(str);
                }else {
                    System.out.println("不是一个有效的ip地址");
                }
            }else {
                System.out.println("不是一个有效的ip地址");
            }
        }
    }

    public static void isIPv4(String str){
        String[] sp = str.split("\\.");
        //判断每个字段的范围是否有效  另外需要判断 10.01.0.0是不合法的 10.0.0.0是有效的
        if(Integer.parseInt(sp[0])>0 && Integer.parseInt(sp[0])<256 && sp[0].equals(String.valueOf(Integer.parseInt(sp[0]))) &&
                Integer.parseInt(sp[1])>=0 && Integer.parseInt(sp[1])<256 && sp[1].equals(String.valueOf(Integer.parseInt(sp[1]))) &&
                Integer.parseInt(sp[2])>=0 && Integer.parseInt(sp[2])<256 && sp[2].equals(String.valueOf(Integer.parseInt(sp[2]))) &&
                Integer.parseInt(sp[3])>=0 && Integer.parseInt(sp[3])<256 && sp[3].equals(String.valueOf(Integer.parseInt(sp[3]))))
            System.out.println("是一个有效的ip地址");
        else
            System.out.println("不是一个有效的ip地址");
    }
    public static void iPv6IncludeIPv4(String str) {
        String[] sp = str.split("\\.");
        //判断每个字段的范围是否有效  另外需要判断 10.01.0.0是不合法的 10.0.0.0是有效的
        if(Integer.parseInt(sp[0])>=0 && Integer.parseInt(sp[0])<256 && sp[0].equals(String.valueOf(Integer.parseInt(sp[0]))) &&
                Integer.parseInt(sp[1])>=0 && Integer.parseInt(sp[1])<256 && sp[1].equals(String.valueOf(Integer.parseInt(sp[1]))) &&
                Integer.parseInt(sp[2])>=0 && Integer.parseInt(sp[2])<256 && sp[2].equals(String.valueOf(Integer.parseInt(sp[2]))) &&
                Integer.parseInt(sp[3])>=0 && Integer.parseInt(sp[3])<256 && sp[3].equals(String.valueOf(Integer.parseInt(sp[3]))))
            System.out.println("是一个有效的ip地址");
        else
            System.out.println("不是一个有效的ip地址");
    }
}

测试结果
测试结果如图所示

猜你喜欢

转载自blog.csdn.net/yguoelect/article/details/77718615