3

我正在尝试按命名空间分隔符拆分以下(Delphi RTTI 输出).

System.Generics.Collections.TEnumerator<Utils.TPair<System.string,System.string>>

正确的拆分应该是[System, Generics, Collections, TEnumerator<Utils.TPair<System.string,System.string>>].

首先我尝试了一个否定的前瞻\.(?!\<*[a-zA-Z0-9_.,]*\>),但它与Utils.TPair最左边的句点相匹配System.string。我可能会补充一点,我有点惊讶,它(正确地)匹配Collections.TEnumerator. 我想这证明了我对正则表达式语言的掌握。

因此,我尝试通过这样说来使其“更贪婪”:\.(?!\<*[a-zA-Z0-9_.,<>]*\>),但没有找到匹配项。(我知道这不是正则表达式通常所说的“贪婪”的意思,但我想不出更合适的描述。)

所以我决定重新开始。据我了解,我应该能够使用消极的环视来解决我的问题。特别是:任何匹配跟随<都可以有效地被忽略。所以我决定(?<!\<[a-zA-Z0-9_]*)\.应该解决我的问题。它没有。这可能是由于(许多)否定后向实现不支持可变长度字符串这一事实。(具体来说,PCRE - 这基本上是 Delphi 使用的,显然支持可变长度的替代品。不过,每个替代品都必须在执行时固定。)

因此我转向你,社区。

谁能解释一下这个问题,实际上应该很简单?会很好!

4

1 回答 1

4

试试这个正则表达式:

\.(?![^.]*[\w_.,]*>)

它的基本意思是:匹配所有.没有在 a und.之前的 a之后的,因此在 a 内。它实际上非常仅限于您的示例。><>

红字

消极的lookbehind可以更好地解决这个任务:

(?<!<.{0,1000})\.

这意味着匹配任何前面.没有的<

我在java中试过这个并且它有效。Java 不允许有无限的后视,这就是为什么我使用 1000 的限制{0,1000}而不是*. 我不知道PCRE是否支持它。

于 2012-09-17T14:50:42.800 回答