Java学习记录(七)

正则表达式:

正则表达式可以用来判断一些字符串是否满足该正则表达式的内容,可以将正则表达式理解为一种规则,而可以用该规则来衡量一些字符串是否符合要求。书写正则表达式时,应按照正确的例子从左到右分析逻辑,依次书写。

以下为部分格式,详细请参考api文档:

以下为一个正则表达式的练习,判断字符串是否符合正则表达式

package com.itazhang.demo4;

import java.math.BigDecimal;
import java.util.regex.Pattern;

public class Test4 {
    public static void main(String[] args) {
        String str1 = "13112345678";
        String str2 = "13112341575";
        String str3 = "13112345678";
        String str4 = "131123454556";
        //创建正则表达式
        String regex1 = "1[3-9]\\d{9}";
        System.out.println("13112345678".matches(regex1));
        System.out.println("13112341575".matches(regex1));
        System.out.println("13112345678".matches(regex1));
        System.out.println("131123454556".matches(regex1));
        System.out.println("---------------1---------------");

        //创建正则表达式
        /*
        第一部分:区号以0开头
        第二部分:0开头以后还有2-3位的区号,用\\d{2,3}表示
        第三部分:有些区号可能会有-,即用-?判断可能会有一次或没有-
        第四部分:在-之后,不能以0开头,即[1-9]表示以1-9的一个数字开头
        第五部分:后面可以为4-9个[0-9]区间的数字,即\\d{4,9}
         */
        String regex2 = "0\\d{2,3}-?[1-9]\\d{4,9}";

        String str5 = "020-2324242";
        String str6 = "02122442";
        String str7 = "027-42424";
        String str8 = "0712-3242434";
        System.out.println("020-2324242".matches(regex2));
        System.out.println("02122442".matches(regex2));
        System.out.println("027-42424".matches(regex2));
        System.out.println("0712-3242434".matches(regex2));
        System.out.println("---------------2---------------");

        /*
        第一部分:@之前的部分,即只要是数字和字母以及下划线就行,出现次数只要一次及以上就可以,即\\w+
        第二部分:即@
        第三部分:即@后面.前面的位置,此时应为2-6位的数字和字母(不含下划线),即[\\w&&[^_]]{2,6}
        第四部分:即.以及.之后的部分,此时.在Java中默认为任意字符,如果要用.本身的含义,即使用\\.则表示.
        而在.之后则是字母2-3个[a-zA-Z]范围的字母,例如:com,cn。但有些邮箱可能有多个.com.cn,此时就需要
        将(.com)作为一个整体使其出现1-2次,即(\\.[a-zA-Z]{2,3}){1,2}此时正则表达式完成。
         */
        String regex3 = "\\w+@[\\w&&[^_]]{2,6}(\\.[a-zA-Z]{2,3}){1,2}";
        String str9 = "3232323@qq.com";
        String str10 = "zhangsan@itcast.cnn";
        String str11 = "dlei0009@163.com";
        String str12 = "dlei0009@pci.com.cn";
        System.out.println("3232323@qq.com".matches(regex3));
        System.out.println("zhangsan@itcast.cnn".matches(regex3));
        System.out.println("dlei0009@163.com".matches(regex3));
        System.out.println("dlei0009@pci.com.cn".matches(regex3));
    }
}

同理,以下为正则表达式的练习2,要求匹配用户名和身份证号

package com.itazhang.demo4;

public class Test5 {
    public static void main(String[] args) {
        //编写用户名是否满足要求:大小写字母,数字,下划线,一共4-16位
        String regex1 = "\\w{4,16}";
        String username1 = "1235_kk";
        String username2 = "itazhang11";
        String username3 = "it@azhang0";
        System.out.println(username1.matches(regex1));
        System.out.println(username2.matches(regex1));
        System.out.println(username3.matches(regex1));
        System.out.println("----------------1-------------------");
        /*编写身份证号码是否满足要求:
        1、18位,前17位任意数字,最后一位可以是大小写的x
         */
        //可以写为[1-9]\\d{16}[xX\\d],也能写成[1-9]\\d{16}[\\d|(?i)x],这里的(?i)表示的忽略大小写
        String regex2 = "[1-9]\\d{16}[xX\\d]";
        String id1 = "212024200212135578";
        String id2 = "21202420021213557x";
        String id3 = "21202420021213557X";
        String id4 = "21202420021213557a";
        System.out.println(id1.matches(regex2));
        System.out.println(id2.matches(regex2));
        System.out.println(id3.matches(regex2));
        System.out.println(id4.matches(regex2));
        System.out.println("----------------2-------------------");
        //但现实生活中身份证号码不会像以上这么简单,所以以下为现实的身份证号码正则表达式
        String regex3 = "[1-9]\\d{5}(?:18|19|20)\\d{2}(?:0[1-9]|10|11|12)(?:0[1-9]|[1-2]\\d|30|31)\\d{3}[\\dXx]";
        String id5 = "42092219731015461X";
        String id6 = "210811196005132133";
        System.out.println(id5.matches(regex3));
        System.out.println(id6.matches(regex3));
    }
}

而在实际应用中,正则表达式大部分是用来爬虫,利用正则表达式可以筛选信息的特质,能爬取我们想要的信息,以下为本地爬取信息的代码

package com.itazhang.demo5;

import java.util.regex.Matcher;
import java.util.regex.Pattern;

public class PaChongTest1 {
    public static void main(String[] args) {
        String str = "电话:18512516758,18512508907或者联系邮箱:boniu@itcast.cn,座机电话:01036517895,010-98951256邮箱: bozai@itcast.cn,热线电话:400-618-9090,400-618-4000,4006184000,4006189090";
        //手机的正则表达式
        Pattern pattern1 = Pattern.compile("1[\\d]{10}");
        //邮箱的正则表达式
        Pattern pattern2 = Pattern.compile("[a-z]{5}@[a-z]{6}\\.cn");
        //热线电话的正则表达式
        Pattern pattern3 = Pattern.compile("400(-?)618(-?)\\d{4}");
        //座机电话的正则表达式
        Pattern pattern4 = Pattern.compile("010(-?)\\d{8}");
        pachong(pattern1,str);
        System.out.println("--------1--------");
        pachong(pattern2,str);
        System.out.println("--------2--------");
        pachong(pattern3,str);
        System.out.println("--------3--------");
        pachong(pattern4,str);
    }
    public static void pachong(Pattern pattern,String str){
        //获取需要爬取的对象,用pattern规则去爬取大串得到子串
        Matcher m1 = pattern.matcher(str);
        while(m1.find()){
            String temp1 = m1.group();
            System.out.println(temp1);
        }
    }
}

在爬取的时候有时候会有一些限制要求,而根据这些限制要求,利用不同正则表达式的书写能满足相应的要求,如下:

package com.itazhang.demo5;

import java.util.regex.Matcher;
import java.util.regex.Pattern;

public class PaChongTest2 {
    public static void main(String[] args) {
        String str = "Java是世界上最好的语言,目前企业里使用的最多的就是Java8和Java11,因为这两个版本是长期支持的版本,但是相信不久的以后,Java17也能登上舞台";
        /*
        以下要求
        需求1:爬取版本号为8,11,17的Java文本,但是只要]ava,不显示版本号。
        需求2:爬取版本号为8,11,17的Java文本。正确爬取结果为: Java8 Java11 Java17 Java17需求3:爬取除了版本号为8,11,17的Java文本,
        需求3:爬取除了版本号为8,11,17的Java文本
         */
        //使用(?i)(Java)时,会忽略Java这个子串的大小写
        //使用(Java)(?=8|11|17)则会匹配前面为Java,后面跟着8或11或17的子串,并只返回Java这个子串
        Pattern p1 = Pattern.compile("(?i)(Java)(?=8|11|17)");
        pachong(p1,str);
        System.out.println("---------1------------");
        //使用(?:8|11|17)则会找出后面跟相应数字的子串
        Pattern p2 = Pattern.compile("(?i)(Java)(?:8|11|17)");
        pachong(p2,str);
        System.out.println("---------2------------");
        //使用(?!8|11|17)则会找出Java文本后没有相数字的子串
        Pattern p3 = Pattern.compile("(?i)(Java)(?!8|11|17)");
        pachong(p3,str);

    }
    public static void pachong(Pattern p,String str){
        Matcher m = p.matcher(str);
        while(m.find()){
            String temp = m.group();
            System.out.println(temp);
        }
    }
}

而在爬虫中会有贪婪爬取和非贪婪爬取

//贪婪爬取,使用+时,Java中会默认的多爬取更符合相关正则表达式的子串
//非贪婪爬取,在ab+之后添加?,即ab+?,则会默认爬取最少符合该正则表达式的子串

代码如下:

package com.itazhang.demo5;

import java.util.regex.Matcher;
import java.util.regex.Pattern;

public class PaChongTest3 {
    public static void main(String[] args) {
        String str = "Java是世界上最好的语言,aaaaaaaaabbbbbaaaaaa目前企业里使用的最多的就是Java8和Java11,因为这两个版本是长期支持的版本,但是相信不久的以后,Java17也能登上舞台";
        //贪婪爬取,使用+时,Java中会默认的多爬取更符合相关正则表达式的子串
        Pattern p1 = Pattern.compile("ab+");
        pachong(p1,str);
        //非贪婪爬取,在ab+之后添加?,即ab+?,则会默认爬取最少符合该正则表达式的子串
        Pattern p2 = Pattern.compile("ab+?");
        pachong(p2,str);
    }
    public static void pachong(Pattern p, String str){
        Matcher m = p.matcher(str);
        while(m.find()){
            String temp = m.group();
            System.out.println(temp);
        }
    }
}

正则表达式也还有其他的使用场景,例如字符串里的replace方法和split方法

//使用replaceAll的方法将符合正则表达式的内容更改为相应内容
//使用split方法能将满足正则表达式的子串切割,将其他的子串用数组的方式返回

具体例子代码如下:

package com.itazhang.demo5;

import java.util.regex.Matcher;
import java.util.regex.Pattern;

public class PaChongTest4 {
    public static void main(String[] args) {
        String str = "我真的是_太TMD123tmd477有趣了哈哈哈TmdTmdtmd";
        //使用replaceAll的方法将符合正则表达式的内容更改为相应内容
        String s = str.replaceAll("[\\w&&[^_]]+", "1");
        System.out.println(s);
        //使用split方法能将满足正则表达式的子串切割,将其他的子串用数组的方式返回
        String[] split = str.split("[\\w&&[^_]]+");
        for (int i = 0; i < split.length; i++) {
            System.out.println(split[i] + " ");
        }
    }
    public static void pachong(Pattern p, String str){
        Matcher m = p.matcher(str);
        while(m.find()){
            String temp = m.group();
            System.out.println(temp);
        }
    }
}

在正则表达式应用中会有存在捕获分组的情况,就是在正则表达式后面可能会用到该表达式前面的子串,例如判断aaa123aaa类型,后面的aaa会用到前面的aaa,即用\\1在正则表达式内部表示前面的第一组

实例代码如下:

package com.itazhang.demo5;

import java.util.regex.Pattern;

public class ZhengZhe {
    public static void main(String[] args) {
        //用分组能解决一些常见的字符串问题
        String str = "abc123k1a";
        //这里的\\1表示重新运用第一组,也就是(.)
        String regex1 = "(.).+\\1";
        System.out.println(str.matches(regex1));
        //判断开始与结尾是否一致,可以有多个字符
        String str2 = "abc123k1abc";
        String regex2 = "(.+).+\\1";
        System.out.println(str2.matches(regex2));
        //判断开始结束的部分相同,其中部分里的元素相同例如aaa123aaa
        String str3 = "aaa123aaa";
        String str4 = "aaa123aab";
        String regex3 = "((.)+).+\\1";
        System.out.println(str3.matches(regex3));
        System.out.println(str4.matches(regex3));
    }

}

而有时候会在正则表达式外部使用正则表达式的第i组,用法如下

//此时的$1符号则是在正则表达式外部使用正则表达式中第一组的用法
String str2 = str.replaceAll(regex,"$1");

实例代码如下:

package com.itazhang.demo5;

public class ZhenZhe2 {
    public static void main(String[] args) {
        String str = "我是真真真的的的不不不不不不口吃吃吃吃啊";
        //想要将上诉改为我是真的不口吃啊,会用到在正则外使用前一组的用法
        String regex = "(.)\\1+";
        //此时的$1符号则是在正则表达式外部使用正则表达式中第一组的用法
        String str2 = str.replaceAll(regex,"$1");
        System.out.println(str2);
    }
}

  • 8
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值