Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/149.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 有没有一种优雅的方式来遍历叮当作响的AST语句?_C++_Clang_Abstract Syntax Tree_Clang++ - Fatal编程技术网

C++ 有没有一种优雅的方式来遍历叮当作响的AST语句?

C++ 有没有一种优雅的方式来遍历叮当作响的AST语句?,c++,clang,abstract-syntax-tree,clang++,C++,Clang,Abstract Syntax Tree,Clang++,我试图遍历所有函数定义并从中提取信息。我必须迭代函数体中的所有语句,并根据类型执行特定函数 目前我有一个丑陋的if else块。有没有更优雅的方法 void FunctionMatcher::processStatement(const clang::Stmt *statement) { string type = statement->getStmtClassName(); if (type == "ReturnStmt") { auto rs = dyn

我试图遍历所有函数定义并从中提取信息。我必须迭代函数体中的所有语句,并根据类型执行特定函数

目前我有一个丑陋的if else块。有没有更优雅的方法

void FunctionMatcher::processStatement(const clang::Stmt *statement) {
    string type = statement->getStmtClassName();
    if (type == "ReturnStmt") {
        auto rs = dyn_cast<const ReturnStmt *>(statement);
        processReturnStmt(rs);
    } else if (type == "WhileStmt") {
        auto ws = dyn_cast<WhileStmt>(statement);
        processWhileStmt(ws);
    } else if (type == "ForStmt") {
        auto fs = dyn_cast<const ForStmt *>(statement);
        processForStmt(fs);
    } else if (type == "IfStmt") {
        auto is = dyn_cast<const IfStmt *>(statement);
        processIfStmt(is);
    } else if (type == "SwitchStmt") {
        auto ss = dyn_cast<const SwitchStmt *>(statement);
        processSwitchStmt(ss);
    } else if (type == "CompoundStmt") {
        auto cs = dyn_cast<const CompoundStmt *>(statement);
        for (auto child : cs->children())
            processStatement(child);
    } else {
      // ...
    }
void FunctionMatcher::processStatement(const clang::Stmt*语句){
字符串类型=语句->getStmtClassName();
如果(类型==“返回stmt”){
自动rs=动态铸造(声明);
过程返回stmt(rs);
}else if(类型==“whilestm”){
自动ws=dyn_cast(语句);
处理时间(ws);
}else if(类型==“ForStmt”){
自动fs=动态转换(语句);
tmt过程(fs);
}else if(类型==“IfStmt”){
自动转换=动态转换(语句);
processIfStmt(is);
}else if(类型==“开关stmt”){
自动ss=动态铸造(声明);
进程切换stmt(ss);
}else if(类型==“CompoundStmt”){
自动cs=动态铸造(声明);
对于(自动子项:cs->children())
处理声明(儿童);
}否则{
// ...
}

通过浏览clang::TextNodeDumper的代码,我找到了一个解决方案。 显然,Clang有自己的访客来发表声明、声明等。。。 简单的例子:

class StatementVisitor : public ConstStmtVisitor<StatementVisitor> {

public:
    StatementVisitor();

    void Visit(const Stmt *Node) {
        ConstStmtVisitor<StatementVisitor>::Visit(Node);
    }

    void VisitIfStmt(const IfStmt *Node) {
        llvm::outs() << " An if statement yay!\n";
    }

    void VisitWhileStmt(const WhileStmt *Node) {
        llvm::outs() << " A While statement yay!\n";
    }
};
class语句访问者:public constmtvisitor{
公众:
StatementVisitor();
无效访问(const Stmt*节点){
constmtvisitor::访问(节点);
}
void visitifsmt(常量IfStmt*节点){
llvm::outs()您可以使用

它递归地遍历给定代码中的所有语句

class MyASTVisitor : public RecursiveASTVisitor<MyASTVisitor>
{
    public:
    bool VisitFunctionDecl(FunctionDecl* f)
    {
        ...
    }

    bool VisitIfStmt(IfStmt* IF)
    {
        ...
    }

    bool VisitForStmt(ForStmt* FS)
    {
        ...
    }

    bool VisitWhileStmt(WhileStmt* WS)
    {
        ...
    }
}
类MyASTVisitor:公共递归AstVisitor
{
公众:
bool VisitFunctionDecl(FunctionDecl*f)
{
...
}
bool visitifsmt(IfStmt*IF)
{
...
}
bool VisitForStmt(ForStmt*FS)
{
...
}
bool访问时长(同时长*宽)
{
...
}
}

您是否尝试过:@KostasRim这就是我用来提取函数的方法。现在我想迭代正文中的语句并处理它们。看起来像是a,no?@G.M的经典用例。我需要用accept方法扩展Stmt类,不是吗?这些是库类。