树深度算法用作函数定义,但不作为方法定义

时间:2015-04-16 00:27:31

标签: python oop recursion tree depth

我写了一个递归获取树深度的算法。作为函数定义,它可以工作:

def tree_depth_f(tree):
    """Counts the maximum depth of a tree."""        
    def recursive_count(node):
        """Recursive count function."""
        childs = tree[node]
        if childs == None:
            return 0
        else:
            maxh = 0
            for i in xrange(len(childs)):
                h = recursive_count(childs[i])
                if maxh < h:
                    maxh = h                
            return int(1 + maxh)

    root = tree['root']
    depth = recursive_count(root)
    return depth

但是与方法定义相同的算法不起作用:

class MyClass:
    def __init__():
        pass

    def tree_depth(self, tree):
        """Counts the maximum depth of a tree."""        
        def recursive_count(node):
            """Recursive count function."""
            self.childs = tree[node]
            if self.childs == None:
                return 0
            else:
                self.maxh = 0
                for i in xrange(len(self.childs)):
                    self.h = recursive_count(self.childs[i])
                    if self.maxh < self.h:
                        self.maxh = self.h                
                return int(1 + self.maxh)

        self.root = tree['root']
        self.depth = recursive_count(self.root)
        return self.depth

tree是列表字典。这就是我测试这些代码的方式:

tree = {0: [1], 1: [2], 2: [3, 4], 3: None, 4: None, 'root': 0}
m = MyClass()
print "As a function:", tree_depth_f(tree)
print "As a method:", m.tree_depth(tree)

以下是此示例中tree的图形表示:

enter image description here

函数定义工作正常,但是当我使用方法定义时,我收到以下错误:

TypeError: 'NoneType' object has no attribute '__getitem__'
    at Answer.py. in recursive_count on line 102
    at Answer.py. in recursive_count on line 102
    at Answer.py. in recursive_count on line 102
    at Answer.py. in tree_depth on line 108
    at Answer.py. in <module> on line 157

原始代码中的第102,108和157行指向:

102: self.h = recursive_count(self.childs[i])
108: self.depth = recursive_count(self.root)
157: print "As a method:", m.tree_depth(tree)

经过大量调试后,我发现当方法定义找到一个叶子(self.childsNone的一个节点)并开始从递归返回时,self.childs父节点也是None。我不知道为什么。功能定义工作正常。你能帮助我吗?

1 个答案:

答案 0 :(得分:1)

您正在修改self.childs,它在这里有效地充当全局变量(因为它记录在对象上,它通过对递归函数的不同调用持续存在)。每个节点没有一个对象,你有一个对象,句点。因此,在self.childs上没有“{1}}父母节点”,您只有一个self.childs。当递归从self分支退出时,变量return 0self.childs

在您的功能代码中,您的None是一个局部变量,因此每个函数调用都会获得一个单独的副本;无论是在方法还是在函数上,你真的需要它。

只需删除childsself.就不需要成为实例变量。实际上,由于您没有使用任何面向对象的功能,因此不需要任何变量作为实例变量。