【问题标题】:pycparser nested node visitorpycparser 嵌套节点访问者
【发布时间】:2016-02-13 14:04:39
【问题描述】:

我正在尝试使用 pycparser 解析 C 代码,并为每个 IF 语句提供访问者。根据我的观察,它只访问没有嵌套 IF 的顶级节点。是故意的,还是我的代码有问题?

【问题讨论】:

标签: python c pycparser


【解决方案1】:

查看课程评论:https://github.com/eliben/pycparser/blob/master/pycparser/c_ast.py#L107

定义了 visit_XXX 的节点的子节点不会 已访问 - 如果需要,请在节点上调用 generic_visit()。

你可以使用:

NodeVisitor.generic_visit(self, node)

我试过了,它对我有用:

if_conditions.py

from __future__ import print_function
import sys

# This is not required if you've installed pycparser into
# your site-packages/ with setup.py
sys.path.extend(['.', '..'])

from pycparser import c_parser, c_ast, parse_file

class IfVisitor(c_ast.NodeVisitor):
    def __init__(self):
        pass

    def visit_If(self, node):
        node.show()
        self.generic_visit(node);



def start(filename):
    ast = parse_file(filename, use_cpp=True)
    v = IfVisitor()
    v.visit(ast)


if __name__ == "__main__":
    if len(sys.argv) > 2:
        filename = sys.argv[1]
    else:
        filename = 'examples/c_files/test.c'

    start(filename)

test.c

main ( int arc, char **argv ) {

    int i = 1;

    if (i > 1) {
        if (i > 2) {
            printf("Yay!");
        }
    }

    // code
    return 0; // Indicates that everything vent well.     
}

【讨论】:

    【解决方案2】:

    generic_visit() 可以。或者,只需重新访问子节点。

    https://github.com/eliben/pycparser/blob/master/examples/func_calls.py#L29

    # A visitor with some state information (the funcname it's looking for)
    class FuncCallVisitor(c_ast.NodeVisitor):
        def __init__(self, funcname):
            self.funcname = funcname
    
        def visit_FuncCall(self, node):
            if node.name.name == self.funcname:
                print('%s called at %s' % (self.funcname, node.name.coord))
            # Visit args in case they contain more func calls.
            if node.args:
                self.visit(node.args)
    

    在这种情况下(IF 语句),

    if node.iftrue:
        self.visit(node.iftrue)
    
    if node.iffalse:
        self.visit(node.iffalse)
    

    【讨论】:

      猜你喜欢
      • 2021-09-04
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2019-07-10
      • 1970-01-01
      • 1970-01-01
      • 2014-10-31
      相关资源
      最近更新 更多