正则表达式提取匹配组

时间:2014-04-20 09:04:05

标签: c# regex

  

(1479页的50798.3 vol 1)

以上是我的剪贴板内容。 As in my previous question,我提取了50798.3 vol 1 of 14并将其保存为pdf_name,将113保存为pagenumber。这很有效。

            var current_clipboard = Clipboard.GetText();
            var regEx = @"^\((?<Desc>[^-]*)-page\s(?<Page>\d+)";
            var match = Regex.Match(current_clipboard, regEx);
            string pdf_name = match.Groups["Desc"].Value;
            string pagenumber = match.Groups["Page"].Value;

现在,对于剪贴板内容的变体,其中-page的格式为_Page或_Pages,我使用了以下内容,但它无效。通过不工作,我的意思是当我使用MessageBox.Show for pdf_name和pagenumber时,消息框显示空白消息。此外,当我测试RegEx时,它显示3 groups as here。我不需要第二个匹配组。

            var current_clipboard = Clipboard.GetText();
            var regEx = @"^\((?<Desc>[^-]*)_pag(e|es)\s(?<Page>\d+)";
            var match = Regex.Match(current_clipboard, regEx);
            string pdf_name = match.Groups["Desc"].Value;
            string pagenumber = match.Groups["Page"].Value;

所以,我做错了什么。请帮我将正确的值保存到pdf_name和pagenumber。

编辑#

@Jerry

我试过你的版本如下。

            var current_clipboard = Clipboard.GetText();
            var regEx = @"^\((?<Desc>[^-]*)_pages?\s(?<Page>\d+)";
            var match = Regex.Match(current_clipboard, regEx);
            string pdf_name = match.Groups["Desc"].Value;
            string pagenumber = match.Groups["Page"].Value;
            MessageBox.Show(pdf_name);
            MessageBox.Show(pagenumber);

不幸的是,消息框正在返回空白消息。

3 个答案:

答案 0 :(得分:0)

问题似乎是,如果您的网页之前不再有-分隔符,那么您的初始[^-]*模式会吞噬整个字符串。

如果您的说明中未显示下划线,则应将[^-]*替换为[^_]*。或者,使用lazy匹配:(?<Desc>.*?)

答案 1 :(得分:0)

您正在抓取(e|es)作为第二组。

将其更改为non-capturimg group

(?:e|es)
  

非捕获组:(?:通常,您需要使用括号   写一个有意义的表达。通常,括号捕获   他们匹配的是什么非捕获组允许您使用括号   没有捕获任何东西请注意,因为语法非常相似   这是一个先行。

     

非捕获组模式:(?:Bob)匹配Bob,但Bob不匹配   捕获。

http://www.rexegg.com/regex-disambiguation.html

答案 2 :(得分:0)

默认情况下,正则表达式区分大小写,这意味着p仅匹配p而不匹配P。如果你想要一个不区分大小写的正则表达式,那么你可以使用RegexOptions.IgnoreCase或内联修饰符(?i),或者在正则表达式中使用[Pp],它将与p匹配或P(但其他字母将以区分大小写的方式匹配。

使用该选项,.Match的行将更改:

var match = Regex.Match(current_clipboard, regEx, RegexOptions.IgnoreCase);

使用内联修饰符,正则表达式将更改:

var regEx = @"(?i)^\((?<Desc>[^-]*)_pag(e|es)\s(?<Page>\d+)";

使用字符类,正则表达式将会改变:

var regEx = @"^\((?<Desc>[^-]*)_[Pp]ag(e|es)\s(?<Page>\d+)";

在下一期中,避免捕获的基本方法是使用非捕获组。在这里,您有(e|es)这是一个捕获组。将其更改为(?:e|es)

var regEx = @"^\((?<Desc>[^-]*)_[Pp]ag(?:e|es)\s(?<Page>\d+)";

虽然真的,但你不需要在这里进行替换。您可以使用?量词表示0或1次:

var regEx = @"^\((?<Desc>[^-]*)_[Pp]ages?\s(?<Page>\d+)";

选项和?量词的示例:

var current_clipboard = Clipboard.GetText();
var regEx = @"^\((?<Desc>[^-]*)_pages?\s(?<Page>\d+)";
var match = Regex.Match(current_clipboard, regEx, RegexOptions.IgnoreCase);
string pdf_name = match.Groups["Desc"].Value;
string pagenumber = match.Groups["Page"].Value;

here是另一个正则表达式测试站点,支持命名捕获组的这种语法。