我有这个 [讨厌的] 正则表达式来捕获一个 VBA 过程签名,其中包含一个桶中的所有部分:
public static string ProcedureSyntax
{
get
{
return
@"(?:(?<accessibility>Friend|Private|Public)\s)?(?:(?<kind>Sub|Function|Property\s(Get|Let|Set)))\s(?<identifier>(?:[a-zA-Z][a-zA-Z0-9_]*)|(?:\[[a-zA-Z0-9_]*\]))\((?<parameters>.*)?\)(?:\sAs\s(?<reference>(((?<library>[a-zA-Z][a-zA-Z0-9_]*))\.)?(?<identifier>([a-zA-Z][a-zA-Z0-9_]*)|\[[a-zA-Z0-9_]*\]))(?<array>\((?<size>(([0-9]+)\,?\s?)*|([0-9]+\sTo\s[0-9]+\,?\s?)+)\))?)?";
}
}
它的一部分是矫枉过正,会匹配非法的数组语法(在过程签名的上下文中),但这不是我现在关心的问题。
问题是这部分:
\((?<parameters>.*)?\)
当一个函数(或属性 getter )返回一个数组时中断,因为那时签名看起来像这样:
Public Function GetSomeArray() As Variant()
或者像这样:
Public Function GetSomeArray(ByVal foo As Integer) As Variant()
这使得函数的返回类型完全变味了,因为 parameters
捕获组会选择这个:
ByVal foo As Integer) As Variant(
我知道为什么它会发生 - 因为我的正则表达式假设最后一个右大括号是分隔参数
捕获组的那个。 p>
有没有办法修复我的正则表达式来改变它,而不会对性能产生太大影响?
要注意的是这是一个有效的签名:
Public Function DoSomething(foo As Integer, ParamArray bar()) As Variant()
我有另一个单独的正则表达式来处理各个参数,它会很好用......如果这个不与数组返回类型混淆的话。
这是我得到的:
我需要的是一个不包含 ) As Variant(
部分的 parameters
组,就像返回类型不是数组时那样:
最佳答案
给你....
(?:(?<accessibility>Friend|Private|Public)\s)?(?:(?<kind>Sub|Function|Property\s(Get|Let|Set)))\s(?<identifier>(?:[a-zA-Z][a-zA-Z0-9_]*)|(?:\[[a-zA-Z0-9_]*\]))\((?<parameters>(?:\(\)|[^()])*)?\)(?:\sAs\s(?<reference>(((?<library>[a-zA-Z][a-zA-Z0-9_]*))\.)?(?<identifier1>([a-zA-Z][a-zA-Z0-9_]*)|\[[a-zA-Z0-9_]*\]))(?<array>\((?<size>(([0-9]+)\,?\s?)*|([0-9]+\sTo\s[0-9]+\,?\s?)+)\))?)?
您对原始正则表达式做了哪些更改?
我刚刚更改了这个 \((?<parameters>.*)?\)
将原始正则表达式的一部分添加到 \((?<parameters>(?:\(\)|[^()])*)?\)
.即 .*
在你的模式中会做一个贪婪的匹配直到最后)
符号,但是这个 (?:\(\)|[^()])*
火柴()
不属于 (
的部分或任何字符或 )
零次或多次。所以这匹配像 foo
这样的字符串或 foo()bar
..
关于c# - 使用正则表达式解析签名,具有 "fun"和数组返回值,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/27477824/