我需要解析并将C和C ++函数拆分为主要组件(返回类型,函数名称/类和方法,参数等)。
我正在使用标题或列表中的签名:
public:void __thiscall myClass :: method(int,class myOtherClass *)
我有以下正则表达式,适用于大多数功能:
(?<expo>public\:|protected\:|private\:) (?<ret>(const )*(void|int|unsigned int|long|unsigned long|float|double|(class .*)|(enum .*))) (?<decl>__thiscall|__cdecl|__stdcall|__fastcall|__clrcall) (?<ns>.*)\:\:(?<class>(.*)((<.*>)*))\:\:(?<method>(.*)((<.*>)*))\((?<params>((.*(<.*>)?)(,)?)*)\)
有一些函数不喜欢解析,但似乎与模式匹配。我并不担心匹配目前不是类成员的函数(以后可以处理)。该表达式用于C#程序,因此<label>
用于轻松检索组。
我想知道是否有一个标准的正则表达式来解析所有函数,或者如何改进我的处理奇怪的异常?
答案 0 :(得分:4)
众所周知,C ++难以解析;写一个捕捉所有案例的正则表达式是不可能的。例如,可以有无限数量的嵌套括号,这表明即使是C ++语言的这个子集也不规则。
但似乎你要追求实用性,而不是理论上的正确性。只是不断提高你的正则表达式,直到它抓住它需要抓住的案例,并尽量使它尽可能严格,这样你就不会得到任何错误的匹配。
如果不知道它没有捕捉到的“奇怪异常”,就很难说如何改进正则表达式。
答案 1 :(得分:2)
看看Boost.Spirit,它是一个boost库,允许仅使用C ++代码而不使用预处理器来实现递归下降解析器。您必须指定BNF Grammar,然后传递一个字符串以进行解析。您甚至可以生成抽象语法树(AST),它可用于处理已分析的数据。
BNF规范看起来像是一个整数列表或分隔的单词可能如下所示:
using spirit::alpha_p;
using spirit::digit_p;
using spirit::anychar_p;
using spirit::end_p;
using spirit::space_p;
// Inside the definition...
integer = +digit_p; // One or more digits.
word = +alpha_p; // One or more letters.
token = integer | word; // An integer or a word.
token_list = token >> *(+space_p >> token) // A token, followed by 0 or more tokens.
有关更多信息,请参阅文档,该库在开始时有点复杂,但随后它变得更容易使用(并且更强大)。
答案 2 :(得分:0)
没有。即使函数原型也可以具有任意级别的嵌套,因此无法用单个正则表达式表示。
如果你真的把自己局限于与你的例子非常接近的事情(正好是两个论点等),那么你能提供一些不匹配的例子吗?