一行之间的字符串

时间:2015-07-17 08:02:11

标签: vbscript

通过一些谷歌资源,我可以编写一个程序来提取两个特定字符串之间的字符串。我无法使用正则表达式打印值或将值存储到变量中。这是我的代码。

prgName = InStr(vText, "Program")
sub_prgName = Mid(vText, prgName, 100)
MsgBox sub_prgName, vbInformation
Dim RegEx: Set RegEx = New RegExp
RegEx.IgnoreCase = True
RegEx.Pattern = "Program(.*)?Variant"
Set RegEx = RegEx.Execute(prgName)
MsgBox RegEx.Value, vbInformation

我想获得字符串b / w Program and Variant。当试图看到输出时说

  

运行时错误438,对象不支持此属性。

这是我想用RegEx解析的值:

Program

sqlplus $SOPS_MIPO_USER/$SOPS_MIPO_PASSWORD@$DB_SID @mipo_pruning.sql

Variant

2 个答案:

答案 0 :(得分:1)

如有疑问,请阅读documentationExecute方法返回Matches collection,因此您需要迭代该集合以获得所需的结果(在您的情况下是第一个submatch)。

For Each m In RegEx.Execute(prgName)
  MsgBox m.SubMatches(0), vbInformation
Next

演示:

>>> s = "Program sqlplus $SOPS_MIPO_USER/$SOPS_MIPO_PASSWORD@$DB_SID @mipo_pruning.sql Variant N/A"
>>> Set re = New RegExp
>>> re.Pattern = "Program(.*)?Variant"
>>> re.IgnoreCase = True
>>> For Each m In re.Execute(s) : WScript.Echo m.SubMatches(0) : Next
 sqlplus $SOPS_MIPO_USER/$SOPS_MIPO_PASSWORD@$DB_SID @mipo_pruning.sql

理论上你也可以在没有循环的情况下做到这一点:

Set m = RegEx.Execute(prgName)(0)
MsgBox m.SubMatches(0), vbInformation

但是,如果正则表达式没有找到匹配项,RegEx.Execute(prgName)(0)会引发错误,因此在循环中评估结果是更安全的方法。

我会删除正则表达式中的?,因为它会使该组成为可选组,因此您无法保证拥有SubMatches(0)项。只需使用Program(.*)Variant代替。如果“Program”和“Variant”之间没有文本,你将得到一个零长度的字符串作为第一个子匹配。或者您可以将它放在星号(Program(.*?)Variant)后面的括号内,以使匹配非贪婪(最短匹配而不是最长匹配)。

如果输入字符串包含换行符,则需要使用[\s\S]而不是.,因为正则表达式中的点匹配除了换行符之外的任何字符

演示:

>>> s = "Program" & vbNewLine & vbNewLine _
& "sqlplus $SOPS_MIPO_USER/$SOPS_MIPO_PASSWORD@$DB_SID @mipo_pruning.sql" _
& vbNewLine & vbNewLine & "Variant"
>>> WScript.Echo s
Program

sqlplus $SOPS_MIPO_USER/$SOPS_MIPO_PASSWORD@$DB_SID @mipo_pruning.sql

Variant
>>> Set re = New RegExp
>>> re.Pattern = "Program(.*)?Variant"
>>> re.IgnoreCase = True
>>> For Each m In re.Execute(s) : WScript.Echo m.SubMatches(0) : Next
>>> re.Pattern = "Program([\s\S]*)?Variant"
>>> For Each m In re.Execute(s) : WScript.Echo m.SubMatches(0) : Next


sqlplus $SOPS_MIPO_USER/$SOPS_MIPO_PASSWORD@$DB_SID @mipo_pruning.sql


作为旁注,您不应该使用Execute方法的结果替换正则表达式对象。

Set RegEx = RegEx.Execute(prgName)    '<-- NEVER do this!

重复使用变量是禁忌,所以不要这样做。

答案 1 :(得分:0)

.Execute会返回Match对象的集合。此集合具有.Count但没有.Value属性。您可以使用MsgBox RegEx(0).Value获取第一场比赛的.Value。

证据:

>> sInp = "XXXProgramYYYVariantZZZ"
>> Set r = New RegExp
>> r.Pattern = "Program(.*?)Variant"
>> WScript.Echo r.Execute(sInp)(0).Value
>> WScript.Echo r.Execute(sInp)(0).SubMatches(0)
>>
ProgramYYYVariant
YYY

您应该发布您的输入和预期结果。