Skip to content

Instantly share code, notes, and snippets.

@signalpillar
Created November 26, 2014 17:33
Show Gist options
  • Select an option

  • Save signalpillar/08fb2917a1adfdeaffa5 to your computer and use it in GitHub Desktop.

Select an option

Save signalpillar/08fb2917a1adfdeaffa5 to your computer and use it in GitHub Desktop.
"""
Script with :func:`build_hierarchy` function as an entry point.
Specify the class and get its inheritance hierarchy.
See also :mod:`inspect.getclasstree` as an alternative implementation.
There is also a way to convert hierarchy to the dot-language graph - :func:`node_to_dot_graph`
"""
import itertools
from collections import namedtuple
class Node(namedtuple('Node', 'value children')):
"""Node in the hierarchy"""
def __repr__(self):
if not self.children:
return self.value
return super(Node, self).__repr__()
def build_hierarchy(cls):
"""Build inheritance hierarchy of the specified class
types.ClassType -> Node
"""
return Node(
value=cls.__name__,
children=[
build_hierarchy(sub_cls)
for sub_cls in cls.__subclasses__()
]
)
def node_to_dot(node):
"""Convert node to the statement in the dot-language.
Node -> str
"""
return "\n".join(
itertools.chain(
(
'{} -> {};'.format(node.value, child.value)
for child in node.children
),
(node_to_dot(child) for child in node.children)
))
def node_to_dot_graph(node):
"""Convert recursively node to the graph in the dot-language.
Node -> str
"""
return """
digraph {name} {{
{nodes}
}}
""".format(
name=node.value,
nodes=node_to_dot(node)
)
if __name__ == '__main__':
hierarchy = build_hierarchy(Exception)
with open('~/Temp/exception.dot', 'w+') as fd:
fd.write(node_to_dot_graph(hierarchy))
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment