正则表达式从入门到精通(提高篇)

我们来一起看一下正则表达式的一些高级的用法。

1.正则表达式之子模式

为了弄清子模式的用法,我们先来看一个正则表达式。”((ab)+)dfs”。在这个正则表达式中,我们可以将表达式分为两部分,第一部分是”((ab+))”,第二部分是”dfs”。假如现在有一个字符串”ababdfs”,那么正则表达式的第一部分匹配到了”abab”。加入我想取出来这个第一部分的匹配结果,那么我就可以使用”$1”来引用”abab”。也就是说我们的到的匹配结果其实是一个数组。在正则表达式中,左括号的计数,就是子模式的下标。
关于子模式通常有两种用法。

  1. 在正则表达式本身中使用子模式\n,n代表子模式的下标。
    比如我们要匹配”aabb”这样的串,那么我们可以这样写正则”(.)\1(.)\2”。(.)匹配到a,\1表示第一个子模式,即(.),因此也匹配a.后面的同理。
  2. 在正则表达式外面使用子模式$n,n代表子模式的下标。
    下面我们用例子来说明。
    比如有这样一个字符串”aabccddeeeeeffff”,我要去掉重复的字符,将结果变成”abcdef”,那么我们可以这么做。
        String reg="(.)(\\1)+";//正则表达式,第一个\是为了转义
        String ret = "aabccddeeeeeffff".replaceAll(reg, "$1");//将匹配到的重复字符变成单个字符
        System.out.println(ret);

输出结果为:abcdef。

2.正则表达式之非捕获组

非捕获组的意思是不需要在结果中捕获。还是举个例子来说明。正则表达式”(a+)(b+)”正常情况下”$1”代表”a+”即第一个子模式,”$2”代表”b+”即第二个子模式。但是现在我不需要引用第一个子模式,我值关心第二个子模式。我就可以再第一个子模式的前面加上”?:”来排除第一个子模式。这个时候我再使用”$1”的时候,引用的就是”b+”这个子模式了。

String reg="(?:http|ftp|svn)://([^/]+)([/].+)";//正则表达式,匹配任意网址,(?:http|ftp|svn)                                                                      将第一个子模式作为非捕获组
        String webSite = "http://www.baidu.com/zhang".replaceAll(reg, "$1");//将任意网址替换为它本身的一级主域名
        System.out.println(webSite);

输出结果为:www.baidu.com

3.正则表达式之环视

环视是指在做匹配时不只着眼当前,还要环视这个表达串,来进行匹配。依然举个例子。
正则表达式”(b+?<=aaa)”代表匹配多个b(可能是一个或者多个),?<在这里就表示环视的意思,代表多个b后面必须跟着3个a。环视一般有四个用法,分别是:
(?<=expr)匹配前面是expr的字符串。
(?<!expr)匹配前面不是expr的字符串。
(?=expr)匹配后面是expr的字符串。
(?!expr)匹配后面不是expr的字符串。
环视有两个特性:

              - 环视部分不占宽度  
              - 环视部分可以重复匹配

看上去似乎很难理解,我们依然举个例子来说明。
先说第一点。
下面的例子输出结果为ab。也就是说环视只是一个是否匹配的附加条件,并不会作为匹配结果的一部分。

        String reg="ab(?=def)";
        Pattern p=Pattern.compile(reg);
        Matcher matcher = p.matcher("abdef");
        //Matcher matcher = p.matcher("");
        while(matcher.find()){
            System.out.println(matcher.group());
        }

再说第二点。
下面例子中的正则表达式表示一个7-15位的字符串,不能全部是数字,不能全部是字母(包括全部大写,全部小写,全部大小写混合),不能全部是小写字母和数字。

        String reg=
        "(?!^[0-9]+$)(?!^[A-Z]+$)(?!^[a-z]$)(?!^[a-z0-9]+$)(?!^[A-Za-z]+$)(^[a-zA-Z0-9]{7,15}$)";
        Pattern p=Pattern.compile(reg);
        Matcher matcher = p.matcher("a6BdeDFSAFASf");
        //Matcher matcher = p.matcher("");
        while(matcher.find()){
            System.out.println(matcher.group());
        }

这个例子中的正则其实加入了很多环视,(?!^[0-9]+$)是第一个环视,排除掉了全部是数字的情况,(?!^[A-Z]+$)排除掉了全部是大写字母的情况。(?!^[a-z]$)排除掉了全部是小写字母的情况,(?!^[a-z0-9]+$)排除掉了小写字母和数字混合的情况,(?!^[A-Za-z]+$)排除掉了大小写字母混合的情况。(^[a-zA-Z0-9]{7,15}$)是我们需要的通用正则表达式,在符合上述环视条件的情况下,我们拿到的就是我们需要的字符串。从这个例子中可以看出来,环视是可以重复匹配的,第一个环视从头匹配到结尾,第二个环视还可以从头匹配到结尾,后面的每一个环视都是如此。
最后,想说一点,正则表达式是实际变成中应用广泛,勤加练习,我们每一个人都能很好的掌握它。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章