天天看點

正規表達式 “雙向最小比對”

如下:

 String input = " <a  href=\" <a  href=\"authentication.html?file=KF619L_Z.pdf\" class=\"icondrawing balloonbtn\"  

  rel=\"shadowbox;width=720\">外観図面</a>";

需要提取   "authentication.html?file=KF619L_Z.pdf"

代碼 如下:

using System;

using System.Collections.Generic;

using System.Linq;

using System.Text;

using System.Text.RegularExpressions;

using System.Threading.Tasks;

namespace regDemo

{

   class Program

   {

       static void Main(string[] args)

       {

           String input = " <a  href=\" <a  href=\"authentication.html?file=KF619L_Z.pdf\" class=\"icondrawing balloonbtn\"  rel=\"shadowbox;width=720\">外観図面</a>";

           Console.WriteLine(getCenterString(input, "href=\"", "\" class="));

           Console.ReadKey();

       }

       public static String getCenterString(String input,String left,String right)

           Match match = Regex.Match(input, left + "(.+?)" + right);

           while (match.Success)

           {

               return match.Groups[1].Value;

           }

           return "";  

   }

}

中間加了 ?  目的是  非貪婪比對。

但是效果并不理想,效果如下:

正規表達式 “雙向最小比對”

按照最小比對原則,原則上我們應該得到理想結果,但是卻沒有。

這是因為在正則的解釋器中,對于最小比對原則的了解為正向最小比對,

而不是雙向最小比對。

左側比對後 定住左側邊界   直到找到右側為止

我們換個思路:

中間包含在我們左側的字元即可,

我們對代碼進行改進:

Match match = Regex.Match(input, left + "(((?!" + left + ").)+?)" + right);

得到了我們想要的結果:

正規表達式 “雙向最小比對”

補充:

【零寬斷言】

正則表達四一些字元可以比對一句話的開始、結束(^ $)或者比對一個單詞的開始、結束(\b)。這些元字元隻比對一個位置,指定這個位置滿足一定的條件,而不是比對某些字元,是以,它們被成為 零寬斷言。所謂零寬,指的是它們不與任何字元相比對,而比對一個位置;所謂斷言,指的是一個判斷。正規表達式中隻有當斷言為真時才會繼續進行比對。

在有些時候,我們精确的比對一個位置,而不僅僅是句子或者單詞,這就需要我們自己寫出斷言來進行比對。下面是斷言的文法:

斷言文法

說明

(?=pattern)

前向肯定斷言,比對pattern前面的位置

(?!pattern)

前向否定斷言,比對後面不是pattern的位置

(?<=pattern)

後向肯定斷言,比對pattern後面的位置

(?<!pattern)

後向否定斷言,比對前面不是pattern的位置

更多參考:

http://www.cnblogs.com/youring2/archive/2009/11/07/1597786.html

————————————————

版權聲明:本文為CSDN部落客「明明如月學長」的原創文章,遵循CC 4.0 BY-SA版權協定,轉載請附上原文出處連結及本聲明。

原文連結:

https://blog.csdn.net/w605283073/article/details/48933895

繼續閱讀