在 python 中构建一个调用图,包括模块和函数? [关闭]
Posted
技术标签:
【中文标题】在 python 中构建一个调用图,包括模块和函数? [关闭]【英文标题】:Build a Call graph in python including modules and functions? [closed] 【发布时间】:2012-12-07 10:49:05 【问题描述】:我有一堆脚本来执行一项任务。而且我真的需要知道项目的调用图,因为它非常令人困惑。我无法执行代码,因为它需要额外的硬件和软件来执行此操作。但是,我需要了解其背后的逻辑。所以,我需要知道是否有一个工具(不需要任何 python 文件执行)可以使用模块而不是跟踪或 python 解析器来构建调用图。我有这样的 C 工具,但没有 python。 谢谢。
【问题讨论】:
【参考方案1】:简而言之,不存在这样的工具。 Python 是一种过于动态的语言,无法在不执行代码的情况下生成调用图。
这里有一些代码清楚地展示了python的一些非常动态的特性:
class my_obj(object):
def __init__(self, item):
self.item = item
def item_to_power(self, power):
return self.item ** power
def strange_power_call(obj):
to_call = "item_to_power"
return getattr(obj, to_call)(4)
a = eval("my" + "_obj" + "(12)")
b = strange_power_call(a)
请注意,我们使用eval
创建my_obj
的实例,还使用getattr
调用其中一个方法。这两种方法都使得为 python 创建静态调用图变得极其困难。此外,还有各种难以分析的模块导入方式。
我认为最好的办法是坐下来拿着代码库和一张纸,然后开始手写笔记。这将有双重好处,让您更熟悉代码库,并且不会轻易被难以解析的场景所欺骗。
【讨论】:
我知道。最多可以在模块中搜索import、def 和func() 语句。我想我会写一个程序来做到这一点。当然,它只适用于简单源代码。 只有非常简单的。您还需要解析 cmets、strings 和 docstrings,以免被它们愚弄。我已经编辑了我的答案,以包括我认为你应该做的事情。 是的,我是手动做的...有 14 个引用的脚本...祝我好运:) @Wilduck 静态分析器可能很有用,但并不完整。任何语言都可以混淆它的调用图。例如,我可以使用 C++ 中的字典来查找函数指针并调用它们。静态调用图是在深入研究新代码库之前获得高级概述的快速方法。 Questions 说 OP 有这样一个 C.Gee 的工具,这怎么可能? C 有函数指针 ...【参考方案2】:您可能想查看 pycallgraph:
pycallgraph
此链接中还描述了一种更手动的方法:
generating-call-graphs-for-understanding-and-refactoring-python-code
【讨论】:
是的,我在研究过程中看到了这个页面,但我正在寻找一个“专业”的解决方案。恐怕这种东西不存在……新的创业想法?呵呵 不幸的是,Pycallgraph 不能很好地消化软件包 pycallgraph 正在运行代码,这是他要求不要做的。 pyan 进行静态分析(请参阅下面的答案) 第二个链接失效pycallgraph
现已无人维护【参考方案3】:
我发现的最好的工具是pyan
,是Edmund Horner 的originally written,improved by him,然后是given colorization 和Juha Jeronen 的其他功能。该版本具有有用的命令行选项:
Usage: pyan.py FILENAME... [--dot|--tgf]
Analyse one or more Python source files and generate an approximate call graph
of the modules, classes and functions within them.
Options:
-h, --help show this help message and exit
--dot output in GraphViz dot format
--tgf output in Trivial Graph Format
-v, --verbose verbose output
-d, --defines add edges for 'defines' relationships [default]
-n, --no-defines do not add edges for 'defines' relationships
-u, --uses add edges for 'uses' relationships [default]
-N, --no-uses do not add edges for 'uses' relationships
-c, --colored color nodes according to namespace [dot only]
-g, --grouped group nodes (create subgraphs) according to namespace
[dot only]
-e, --nested-groups create nested groups (subgraphs) for nested namespaces
(implies -g) [dot only]
这是运行pyan.py --dot -c -e pyan.py | fdp -Tpng
的结果:
Edmund Horner 的原始代码现在最好找到 in his github repository,并且有人还制作了 repository with both versions,您可以从那里 download Juha Jeronen's version。我制作了一个干净的版本,将他们的贡献合并到my own repository just for pyan,因为两个存储库都有很多其他软件。
【讨论】:
@DavidFraser 是否与 Python 3.x 兼容? @AlexanderReshytko 不幸的是没有。我已经将一个名为py3-compat
的分支推送到我的 github 存储库,它进行了最小的更改。但这使用了 compiler
模块,该模块在 Python 3 中被删除。代码需要重新构造以使用 ast.NodeVisitor
子类;这应该不会太难,但我现在没有时间去做。 (它仍然与 Python 2.6+ 兼容)
给关注此的任何人的说明;包括 Technologicat
在内的各种用户现在都贡献了 Python 3 支持
这很好用。我在 Windows 上,我发现它有助于创建一个执行 python "C:\path\to\pyan.py" %1 --uses --defines --colored --grouped --annotated --dot >pyan_output.dot && clip < pyan_output.dot
的 bash 命令,这样我就可以粘贴到 webgraphviz.com 并查看输出。感谢您帮助创建并保持更新!
截至现在,似乎维护得最好的fork是github.com/Technologicat/pyan,虽然相关的PyPI包pypi.org/project/pyan3已经有一段时间没有更新了。跨度>
【参考方案4】:
SourceTrail 将在这方面为您提供帮助。 https://www.sourcetrail.com/
Sourcetrail 是一个免费的开源跨平台源代码浏览器,可帮助您在不熟悉的源代码上高效工作。支持 C、C++、Java 和 Python
https://github.com/CoatiSoftware/Sourcetrail
这是文档的链接
https://www.sourcetrail.com/documentation/
请注意,Python 支持相对较新,所以请不要期望它能够完美运行。
【讨论】:
【参考方案5】:我还在https://github.com/zw-normal/pycallgraph 写了一个小工具。 代码的概念很容易理解和使用,但它只提供了有限的信息,还需要另一个 IDE 才能更好地理解。
【讨论】:
【参考方案6】:您应该查看PyCG,这是我们创建的peer reviewed Python 调用图生成器,它可以处理 Python 的大部分功能,包括高阶函数、类、生成器等。
【讨论】:
【参考方案7】:我找到的 pyan3 的工作版本是 1.1.1 (pip install pyan3==1.1.1
),它的文档是 here
【讨论】:
【参考方案8】:我最近(2021 年)在寻找这样的工具,发现 code2flow 似乎正在积极维护。
【讨论】:
以上是关于在 python 中构建一个调用图,包括模块和函数? [关闭]的主要内容,如果未能解决你的问题,请参考以下文章