Python 3 解析文件以查找代码块

问题描述 投票:0回答:1

好的,如果我有以下代码:

a = 1
b = 2
count_one = 0
count_two = 0
ex_array = [a,b]

for i in ex_array:
    print(i)
    if i == 2:
        print("Two")
    elif i == 1:
         print("One")

我的目标是将代码分类为代码块(和子块)。

我的意思是:

一个块就是整个代码,我们称之为“一级”。 在“一级”块内还有:

for i in ex_array:
    print(i)
    if i == 2:
        print("Two")
    elif i == 1:
         print("One")

我们称之为“二级”块。 在二级区块内还有:

if i == 2:
    print("Two")

if i == 1:
    print("One")

此级别为“三级”:

因此,“第一级”中有 1 个代码块(完整代码),“第二级”中有 1 个代码块(包含

for
if
语句的
elif
循环)和第三级中有 2 个代码块(
if
elif
陈述)。

一旦我对代码块和级别进行了分类,我想将它们添加到字典中,如下所示:

code_block_dictionary = {0:(0,"Entire code"), 1:(1,"The for loop block"), 2:(2,"The if statement"), 3:(2,"The `elif` statement")}

第一个数字是索引/键,第二个数字是级别,第三个数字是该级别的代码。

最后,我希望能够做这样的事情:

输入级别以选择块:

我输入“3”

此级别有 2 个代码块

输入要打印的块号:

我输入“1”,打印到终端的结果字符串是:

if i == 2:
    print("Two")

我希望这一切都是有道理的。 如果需要更多信息,请询问,我会尽力而为。 谢谢

python python-3.x parsing dictionary classification
1个回答
0
投票

您可以使用 ast 模块 通过自定义 AST 解析来完成此操作。 我可能会稍微迟到,但如果其他人有兴趣解决这个问题:

import ast


def visit(node: ast.AST, depth: int = 0):
    """Visit a node to look for child blocks."""
    # Fields that indicate this is a block.
    FIELDS = {"body", "orelse", "finalbody"}
    if any((key in FIELDS) for key, _ in ast.iter_fields(node)):
        yield (depth, ast.unparse(node))

    # Iterate over the fields for the current node.
    for key, value in ast.iter_fields(node):
        if key in FIELDS:
            if isinstance(value, list):
                for item in value:
                    if isinstance(item, ast.AST):
                        yield from visit(item, depth + 1)
            elif isinstance(value, ast.AST):
                yield from visit(node, depth + 1)


if __name__ == "__main__":
    path = ...

    with open(path) as f:
        source = f.read()

    tree = ast.parse(source)
    for block in visit(tree):
        print(block)

此代码为您提供了一个具有深度的生成器和源代码。
注意:它不会为您提供原始源代码(请参阅 ast.unparse),但您可以使用

lineno
end_lineno
字段来获取它。

© www.soinside.com 2019 - 2024. All rights reserved.