2016-07-02 65 views
0

我用正则表达式选项查找并替换对话框。有一个按钮来测试一个正则表达式,突出显示所有匹配项,以及一个按钮来查找单个匹配项。对于一些正则表达式,两种方法都会进行相同的匹配其他正则表达式与Regex.Match不匹配,但按照预期收集Regex.Matches。我在分配正则表达式时尝试了不同的RegexOptions,但没有找到任何使其表现符合要求的选项。为什么Regex.Match与Regex.Matches不匹配相同的字符串?

这里的目标是能够使用ButtonTestRegex测试正则表达式,然后通过查找或替换按钮来选择每个匹配项。

Public rtb as RichTextBox 

Private Sub ButtonTestRegex_Click(sender As Object, e As EventArgs) 
    rtb.Select(0, rtb.TextLength) 
    rtb.SelectionColor = Color.Black 

    Dim rgx As New Regex("(duplicate of)*([0-9]:+)*") 

    Dim matches As MatchCollection = rgx.Matches(rtb.Text) 
    For Each match In matches 
     rtb.Select(match.index, match.length) 
     rtb.SelectionColor = Color.Red 
    Next 
End Sub 

Private Sub ButtonFind_Click(ByVal sender As Object, ByVal e As EventArgs) 
    rtb.Focus() 
    rtb.selectionstart = 0 
    rtb.selectionlength = 0 
    Dim rgx = New Regex("(duplicate of)*([0-9]:+)*") 
    Dim match As Match = rgx.Match(rtb.Text) 
    If match.Value <> "" Then 
     rtb.SelectionStart = match.Index 
     rtb.SelectionLength = match.Length 
    End If 
End Sub 

用含有如下一个RichTextBox:

1:其余

重复1的

:其余

重复的1个重复的:其余

的上面的代码将匹配除“余数”之外的所有文本ButtonTestRegex_Click()(如预期)。没有什么会与ButtonFind_Click()匹配。代码正在执行,它可以用于一些正则表达式,例如[0-9]

为清楚起见,此代码示例缩写。我的问题是,为什么Regex.Match在这种情况下不匹配任何东西,但Regex.Matches呢?

+2

答案很可能是您的*(*)的重复*([0-9]:+)*'可以匹配空字符串。使用Regex.Matches,这是没有问题的,因为此方法将扫描每个位置在字符串和正则表达式。匹配,如果在开始时没有与可选模式相匹配的文本,则匹配字符串的开头;如果匹配字符串开头的文本匹配可选模式,则匹配返回匹配。解决方案是修改模式以匹配非空字符串。 –

回答

1

我怀疑在您的RichTextBox选定的文本的开头处有空格或东西。在那一点上,它总是有意义的。看看你的正则表达式:

(duplicate of)*([0-9]:+)* 

这将匹配空字符串。例如,如果您发现与"x"相匹配的所有匹配项,则会在x之前找到一个匹配项,在x之后找到一个匹配项。

当您拨打Match时,发现第一个匹配 - 它成功,但匹配空字符串。当您拨打Matches时,它将检索所有的比赛 - 并且有很多。这里有一个小的C#控制台应用程序,以显示所有这些,在文本的开始假设空间:

using System; 
using System.Text.RegularExpressions; 

class Program 
{ 
    static void Main(string[] args) 
    { 
     var regex = new Regex("(duplicate of)*([0-9]:+)*"); 
     var input = @" 1:remainder 
duplicate of 1:remainder 
duplicate of duplicate of 1:remainder"; 
     foreach (Match match in regex.Matches(input)) 
     { 
      Console.WriteLine(match.Length); 
     } 
    } 
} 

,它的输出开始是这样的:

0 
2 
0 
0 
0 
0 
0 
0 
0 
0 
0 
0 
0 
15 
0 

...但有一个产量很多

这并不完全清楚你想匹配什么,但你可能想确保空字符串匹配你的正则表达式。

+0

所以它正在进行比赛。我只是没有点击查找按钮就足以看到它。这里的奖金课是使用控制台查看实际匹配,而不是依赖RichTextBox中的视觉更改。谢谢。 – codingcoding

+0

@codingcoding:我发现在大多数情况下,快速控制台应用程序是一种非常有效的调试方式。没有用户界面的方式,只需要你需要的代码:) –

相关问题