繁体   English   中英

将计数参数传递给递归 python function

[英]passing counting argument into a recursive python function

我成功地解决了一个算法问题来序列化和反序列化二叉树。

class Codec:
    def __init__(self):
        self.i=0
    def serialize(self, root):
        store=[]
        def preorder(node):
            if not node:
                store.append("N")
                return
            store.append(str(node.val))
            preorder(node.left)
            preorder(node.right)
        preorder(root)
        return ",".join(store)

    # serialized data is passed here as "data" argument             
    def deserialize(self, data):
        values=data.split(",")
        def helper():
            if values[self.i]=="N":
                self.i+=1
                return
            root=TreeNode(int(values[self.i]))
            self.i+=1
            root.left=helper()
            root.right=helper()
            return root
        return helper()

为了解决deserialize化 function,我创建了一个顶级 state 变量self.i 相反,我想将i传递给helper function 但我无法弄清楚。 我尝试使用局部变量进行这样的编码:

    def deserialize(self, data):
        values=data.split(",")
        def helper(i):
            if values[i]=="N":       
                i+=1
                return
            root=TreeNode(int(values[i]))    
            i+=1
            root.left=helper(i)
            # i think issue is here.
            # Because i is modified inside root.left=helper(i)
            # so somehow I need to keep track of this modification
            root.right=helper(i)
            return root
        return helper(0)

除了使用实例属性( i ),您可以使用i尝试过的局部变量,但随后将其作为参数传递给helper ,而是将其作为nonlocal名称引用。 但我不建议这样做。 而是在给定值上创建一个迭代器。 然后你可以调用next来获取下一个值。

一旦你摆脱了丑陋的实例属性,你就不再需要实例了,我想知道你为什么需要 class Codec 如果您真的想保留它,然后将这两个函数创建为static方法,因为创建Codec的实例是没有意义的:

这是在示例树上运行的完整代码:

class TreeNode:
    def __init__(self, val):
        self.val = val
        self.left = self.right = None

    def add(self, val):
        if val < self.val:
            if self.left:
                self.left.add(val)
            else:
                self.left = TreeNode(val)
        else:
            if self.right:
                self.right.add(val)
            else:
                self.right = TreeNode(val)

    def print(self, tab=""):
        if self.right:
            self.right.print(tab +  "  ")
        print(tab, self.val)
        if self.left:
            self.left.print(tab +  "  ")

    @staticmethod
    def of(*values):
        if values:
            root = TreeNode(values[0])
            for val in values[1:]:
                root.add(val)
            return root

class Codec:
    @staticmethod
    def serialize(root):
        store=[]
        def preorder(node):
            if not node:
                store.append("N")
                return
            store.append(str(node.val))
            preorder(node.left)
            preorder(node.right)
        preorder(root)
        return ",".join(store)
    
    @staticmethod
    def deserialize(data):
        values = iter(data.split(","))
        
        def helper():
            val = next(values)
            if val=="N":
                return
            root = TreeNode(int(val))
            root.left = helper()
            root.right = helper()
            return root
        return helper()

tree = TreeNode.of(4,2,6,1,3,5,7)
tree.print()
s = Codec.serialize(tree)
print(s)
root = Codec.deserialize(s)
root.print()

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM