在 http://www.regexlab.com/zh/regref.htm 看到一个例题。
表达式 "(\w)((?=\1\1\1)(\1))+" 在匹配字符串 "aaa ffffff 999999999" 时,
将可以匹配6个"f"的前4个,可以匹配9个"9"的前7个。
这个表达式可以读解成:重复4次以上的字母数字,则匹配其剩下最后2位之前的部分。
当然,这个表达式可以不这样写,在此的目的是作为演示之用。
上面这个表达式究竟是怎么匹配的,请各位抽丝剥茧的分析一下。
谢谢

解决方案 »

  1.   


    这个回复非常有帮助。 我还有另外一段看不懂,帮忙看一下。 谢谢举例3:表达式 "((?!\bstop\b).)+" 在匹配 "fdjka ljfdl stop fjdsla fdj" 时,将从头一直匹配到 "stop" 之前的位置,如果字符串中没有 "stop",则匹配整个字符串。
      

  2.   


      public static void main(String[] args) {
        String str = "aaa ffffff 999999999";
        //Pattern p = Pattern.compile("(\\w)((?=\\1\\1\\1)(\\1))+");
        Pattern p = Pattern.compile("(\\w)(\\1)+(?=\\1\\1)");
        Matcher m = p.matcher(str);
        while(m.find()){
          System.out.println(m.group());
        }
      }(\\w)(\\1)+(?=\\1\\1)的效果其实一样,不过好像要好理解一些
    1个字符 同一个字符重复1次以上 (最后面还有2个同样的字符)
      

  3.   


    我们先来看一下[^>]+这个表达式
    [^>] 表示除“>”之外的字符,这个清楚吧,那么[^>]+也就表示一个或多个非“>”字符
    [^>]+ 在匹配“<a href="www.csdn.net">床上等你</a>”时,将从开头一直匹配到“>”之前的位置
    [^>]的一个等价写法为“(?!>).”,这种写法的直接解读就是不为“>”的任意字符,那么[^>]+的等价写法就是((?!>).)+
    当然,小数点是不能匹配换行符的,指任意字符时可以用[\s\S],写为(?!>)[\s\S],这不是重点,我们不去深究上面的理解了,再来说说((?!\bstop\b).)+
    由于[^char]这种语法,虽然可以同时排除多个字符,但却不能排除一个有序的字符序列,也就是说,[^stop]表示的除“p”、“o”、“s”、“t”之外的任意一个字符,而不是不为“stop”的字符串
    因此在排除有序字符序列,也就是一个字符串时,必须想其它办法了,这时候就要借助环视了
    先来解读下(?!\bstop\b). ,小数点匹配的是除换行符外的任意字符,(?!\bstop\b)为这个字符的匹配加了一个限定条件,以这个字符开始,这个位置右侧不能是“stop”
    ((?!\bstop\b).)+ 表示符合上面这种条件的字符一个或多个,也就是一直匹配到出现stop或到达字符串结尾为止,最终达到的效果就是,排除了“stop”这样一个字符串
      

  4.   

    这个顺序环视?=\1\1\1的含义明白吧?意思是当前检测字符后面的三个字符要分别和第一个分组(\1)匹配,所以对于aaa ffffff 999999999这样的字符串里,每段字串最后一个匹配位置是倒数第3,4个字符位置之间的位置,再加上顺序环视后面还要匹配一个\1,也就是((?=\1\1\1)(\1))中后面那个分组,所以这样会把倒数第3个字符也匹配进去。你可以试一下把最后那个分组(\1)去掉后的执行一下,即(\w)(?=\1\1\1)+,可以看到会有很多分组,但是最后一个匹配字符总会是倒数第4个字符
      

  5.   

    这个顺序环视?=\1\1\1的含义明白吧?意思是当前检测字符后面的三个字符要分别和第一个分组(\1)匹配,所以对于aaa ffffff 999999999这样的字符串里,每段字串最后一个匹配位置是倒数第3,4个字符位置之间的位置,再加上顺序环视后面还要匹配一个\1,也就是((?=\1\1\1)(\1))中后面那个分组,所以这样会把倒数第3个字符也匹配进去。你可以试一下把最后那个分组(\1)去掉后的执行一下,即(\w)(?=\1\1\1)+,可以看到会有很多分组,但是最后一个匹配字符总会是倒数第4个字符
      

  6.   

    这个顺序环视?=\1\1\1的含义明白吧?意思是当前检测字符后面的三个字符要分别和第一个分组(\1)匹配,所以对于aaa ffffff 999999999这样的字符串里,每段字串最后一个匹配位置是倒数第3,4个字符位置之间的位置,再加上顺序环视后面还要匹配一个\1,也就是((?=\1\1\1)(\1))中后面那个分组,所以这样会把倒数第3个字符也匹配进去。
    你可以试一下把最后那个分组(\1)去掉后的执行一下,即(\w)(?=\1\1\1)+,可以看到会有很多分组,但是最后一个匹配字符总会是倒数第4个字符