I'm sure an answer for exists several times over but I can't seem to find an example of capture between two strings, excluding the two strings.
Line of text:
CH1: Vcc: 3220 mV TXBias 14144 RX pwr: 0 TX pwr: 7184\n
output I desire:
3220 mV
What I've tried:
Regex.Match("CH1: Vcc: 3220 mV TXBias 14144 RX pwr: 0 TX pwr: 7184\n", "Vcc: (.*?) ").ToString
yields:
Vcc: 3220
Thanks in advance!
答案 0 :(得分:1)
让我建议另一种更有效的方法:使用Groups
属性。众所周知,环视是耗费资源的,只有在我们需要重叠匹配时才需要。
在这种情况下,我们有一个固定的上下文,Vcc:
,然后是空格,一些数字,空格,mV
,空格,TXBias
。我们可以用括号捕获(这就是你所做的)我们想要的东西。但是,你的正则表达式具有.*?
懒惰点匹配,实际上只是在空格之间捕获了任何东西。我建议只捕获数字,或者 - 如果可以有任何非空白符号序列 - 那些不是空格的符号。
Dim MyRegex As Regex = New Regex("Vcc:\s+(\d+)\s+mV\s+TXBias") ' This regex captures digits
' Or, you can use this regex capturing non-whitespace sequence
' Dim MyRegex As Regex = New Regex("Vcc:\s+(\S+)\s+mV\s+TXBias")
' Or, if you prefer your own regex to match "3220 mV", use it:
' Dim MyRegex As Regex = New Regex("Vcc:\s+(.*?)\s+TXBias")
Dim match As Match = MyRegex.Match("CH1: Vcc: 3220 mV TXBias 14144 RX pwr: 0 TX pwr: 7184")
If match.Success Then
Console.WriteLine(match.Groups(1).Value)
End If
请参阅IDEONE demo,输出为3220
,或此处为the one that outputs 3220 mV
。您可以移动括号以捕获相邻文本的任何部分。
\s+
代表一个或多个空白字符。
match.Groups(1).Value
保存我们模式中第一个(也是唯一的)括号组捕获的文本。第0组是整场比赛。
如果我们将效果与http://regexhero.net进行比较,Vcc:\s+(.*?)\s+TXBias
每秒产生429,380次迭代,(?<=Vcc: ).*?(?=TXBias)
产生92,772次:
因此,仅在必要时使用环视。
答案 1 :(得分:1)
感谢@ dustmouse的评论。
嗯,你可以用这种方式做一个积极的背后隐藏:
(?<=Vcc:\s)
前一行意味着正则表达式将搜索Vcc:
,并且在没有匹配的情况下会将光标放在其后。
现在,您可以使用群组(...)
,但不保存,因此它会像(?:...)
一样。
在此论坛中,您可以使用\s*
表示尽可能多的空格,然后使用\S+
,这意味着至少一个非空格。
现在,小组成立了:
(?:\s*\S+)
你为什么用过一个小组?只是因为现在你可以说你希望它重复多少次,如{2}
(2倍),或{5}
(5倍),等等。
毕竟, tour 以这个正则表达式结束:
(?<=Vcc:\s)(?:\s*\S+){2}
奖金:我会说这是奖励,因为取决于它不会起作用的语言。
您可以使用\K
清除匹配的Vcc:
。如果它以您的语言提供,您应该更喜欢它,因为它可以提高性能:
而不是(?<=Vcc\s)
,您可以使用Vcc\s+\K
。
背后的正面看法不允许+
或*
在其中。现在看,文本Vcc:
将与所有空格匹配,而不是仅与一个空格匹配。
\K
可以解决这个问题。它清除了之前的选择并从那一点开始。
在这种情况下,最终的正则表达式将是:
Vcc:\s+\K(?:\s*\S+){2}
一个人反对另一个人。
如果你看一下regex101:
第一种选择是30步。
虽然第二步做了14步!
呀!这是半个时间!!
让我知道是否有任何混淆。