python - 计算Python程序的数据依赖图

标签 python

我有一段Python代码:

a0 = 1
a1 = 2
a2 = add(a0, a1)
a3 = [i + 1 for i in range(a2)]

我想得到以下data-dependency graph :

{ "a0": [], "a1": [], "a2": ["a0", "a1"], "a3": ["a2"]}

我可以使用locals()获取局部变量的列表,但这就是我现在所拥有的。我可以尝试解析 AST,但这似乎是一个兔子洞,因为我需要处理 AST 的每个怪癖。 有什么想法吗?

用例:我正在尝试编写一种小型 DSL 语言,其中变量是任务,代表需要运行的长时间运行的命令。我正在使用doit但我发现在代码中已经可见的情况下必须显式声明依赖项既麻烦又难以阅读。

最佳答案

最终ast模块已经有了非常方便的“walk”方法。

import ast


def get_deps(code):
    body = ast.parse(code)
    _, statements = next(ast.iter_fields(body))

    full_graph = {
        assign.targets[0].id: [
            d.id for d in ast.walk(assign) if isinstance(d, ast.Name)
        ]
        for assign in statements
    }
    # full_graph also contains `range` and `i`. Keep only top levels var
    restricted = {}
    for var in full_graph:
        restricted[var] = [d for d in full_graph[var] if d in full_graph and d != var]
    return restricted


if __name__ == "__main__":
    d = get_deps(
        """
a0 = 1
a1 = 2
a2 = add(a0, a1)
a3 = [i + 1 for i in range(a2)]
"""
    )

    assert d == {"a0": [], "a1": [], "a2": ["a0", "a1"], "a3": ["a2"]}, d

关于python - 计算Python程序的数据依赖图,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/55712076/

相关文章:

python - 如何按特定规则统计子串?

Python - 匹配

python - PySpark。读取 Parquet 时通过转换为字符串来合并模式?

python - Beautiful Soup 找到具有隐藏样式的元素

python - 使用 `waitress` 在多个端口上提供 Django 应用程序

python - 使用 Python 获取每个 CSV 列中的字符串计数

python - pysftp.Connection.walktree() 参数说明

python - 获得整数数组汉明距离的最快方法

python - 迭代列表元素的所有可能组合并在 Python 中用作索引

python - 在两种不同颜色之间更改像素颜色