2012-01-04 198 views
1

我正在尋找匹配HTML錨點中未包含的所有格式爲foo:12345的文本。例如,我想從以下匹配線1和3:c#正則表達式來匹配特定文本

foo:123456

<a href="http://www.google.com">foo:123456</a>

foo:123456

我已經試過這些正則表達式沒有成功:

負面預測嘗試(錯誤匹配,但不包括最後一位數字)

foo:(\d+)(?!</a>)

負先行與非捕獲分組

(?:foo:(\d+))(?!</a>)

負回顧後嘗試(通配符似乎不支持)

(?<!<a[^>]>)foo:(\d+)

+0

我假設你的最後一個例子意思是'(?] *>)foo:(\ d +)',這樣它將在錨標記中匹配多於一個字符。 – Chris 2012-01-04 18:15:27

+0

幾乎每天都會問這個問題......用正則表達式解析HTML幾乎總是[壞主意](http://stackoverflow.com/questions/1732348/regex-match-open-tags-except-xhtml-self -contained-tags) – 2012-01-04 18:28:36

回答

0

正則表達式通常不是最好的該工作的工具,但如果你的情況是非常具體的,就像在你的例子中,你可以使用:

foo:((?>\d+))(?!</a>) 

您的第一個表達式不起作用,因爲\d+會回溯到(?!</a>)匹配。這可以通過不允許\d+原路返回,如以上的原子量/ nonbacktracking組的幫助下被固定,或者你也可以讓先行的情況下,\d+回溯失敗,如:

foo:((?>\d+))(?!</a>|\d) 

本書雖然是效率不高。

+0

將此標記爲答案,因爲它確實修正了正則表達式的工作原理 – dherman 2012-01-04 19:13:51

0

。注意,回顧後不會與不同的充字符串長度內工作,可以工作了不同

例如

  1. 找到和標記中包含的錨所有FOO-S
  2. 查找並與所有其他
  3. 刪除標記
3

如果你想要做的第一你的目標藝術分析這樣的HTML然後你可能想要實際解析HTML而不是使用正則表達式。 HTML Agility Pack是通常的第一停靠港。使用正則表達式很難處理像<a></a>foo:123456<a></a>這些當然應該拉出中間位但很難編寫正則表達式的東西。

我應該補充一點,我假設你確實有一塊HTML,而不僅僅是單個的短字符串,比如你上面的每一行。部分我排除它因爲匹配它,如果它是唯一的行是非常容易的,所以我想你會得到它,如果你想這樣做。:)

+0

這是一個很好的觀點 - 我將研究如何使用該lib。謝謝。 – dherman 2012-01-04 19:15:02

0

這是一個概率長篇大論這樣的方式,但你可以簡單地帶回FOO的所有出現:一些數字則排除他們事後..

string pattern = @"foo:\d+ |" + 
       @"foo:\d+[<]"; 

然後使用matchcollection

MatchCollection m0 = Regex.Matches(file, pattern, RegexOptions.Singleline); 

然後通過每次出現循環:

foreach (Match m in m0) 
{ 
       . . . exclude the matches that contain the "<" 
} 
0

我會使用LINQ和治療HTML,如XML,例如: var query = MyHtml.Descendants()。ToArray(); 的foreach(的XElement結果查詢) {

  if (Regex.IsMatch(result.value, @"foo:123456") && result.Name.ToString() != "a") 
      { 
       //do something... 
      } 
     } 

也許有更好的方式,但我不知道這...這似乎相當直截了當給我:P