递归计数器

时间:2016-08-27 20:13:58

标签: java recursion

我有以下代码来序列化和反序列化二叉树。序列化工作正常,但反序列化不正确。我正在努力理解我的数组索引计数器“i”应该如何设置用于反序列化。如果你能帮助我理解这一点,我将非常感激。

public class TreeNode {
    int val;
    TreeNode left;
    TreeNode right;

    TreeNode(int x) {
        val = x;
    }
}

public String serialize(TreeNode root) {
    StringBuffer serial = new StringBuffer();
    helperSerialize(root, serial);
    return serial.toString();
}


public void helperSerialize(TreeNode node, StringBuffer serial) {
    if (node == null) {
        serial.append("null ");
        return;
    }
    serial.append(new Integer(node.val).toString() + " ");
    helperSerialize(node.left, serial);
    helperSerialize(node.right, serial);
}

public TreeNode deSerialize(TreeNode root, String s) {
    String[] split = s.split("\\s+");
    root = deSerialize( split, 0);
    return root;
}

public TreeNode deSerialize( String[] s, int i) {
    if(i >= s.length || s[i].equals("null"))
        return null;
    else {
        int v = (int) s[i].charAt(0) - '0';
       TreeNode root = new TreeNode(v);
        root.left = deSerialize( s, ++i);
        i = i +1; // i should be incremented for next recursion
        root.right = deSerialize( s, ++i);
        return root;
    }
}

2 个答案:

答案 0 :(得分:0)

试试这个:(作为使索引有效的示例实现)

public TreeNode deSerialize(TreeNode root, String s) {
    String[] split = s.split("\\s+");
    root = deSerialize( split, new int[1]{0});
    return root;
}

public TreeNode deSerialize( String[] s, int[] i) {
    if(i[0] >= s.length || s[i[0]].equals("null"))
        return null;
    else {
        int v = (int) s[i[0]].charAt(0) - '0';
       TreeNode root = new TreeNode(v);
        root.left = deSerialize( s, ++i[0]);
        root.right = deSerialize( s, ++i[0]);
        return root;
    }
}

这允许通过引用传递索引,因此不会克隆分支。

编辑:

你的algorythm如下:

    A
   / \
  B   C
 / \ / \
D  E F  G

你序列化了一个:
A B D null null E null null C F null null G null null
你反序列化a:
A B D null null null D null null
使用基于数组的迭代器:
A B D null null E null null C F null null G null null

但你的         int v =(int)s [i] .charAt(0) - '0'; 是错误的,因为它只允许一个字符数,而是使用Integer.parse()。

因为你没有提供你的输入/输出,我看不出哪个是错误,但是如果你通过引用和解析来进行修改,你应该没问题。

答案 1 :(得分:0)

我建议使用Scanner而不是预解析整个字符串。那么你根本不需要担心索引。

这里有一些似乎有用的代码。 (对不起,我重命名并重新安排了一些内容,以便更容易构建正在运行的样本。)

import java.util.Scanner;

public class TreeNode {
    int val;
    TreeNode left;
    TreeNode right;

    TreeNode(int x) {
        val = x;
    }

    TreeNode(int x, TreeNode left, TreeNode right) {
        val = x;
        this.left = left;
        this.right = right;
    }

    public String serialize() {
        StringBuffer serial = new StringBuffer();
        serializeHelper(this, serial);
        return serial.toString();
    }

    private static void serializeHelper(TreeNode node, StringBuffer serial) {
        if (node == null) {
            serial.append("null ");
            return;
        }
        serial.append(new Integer(node.val).toString() + " ");
        serializeHelper(node.left, serial);
        serializeHelper(node.right, serial);
    }

    public static TreeNode deserialize(String serialized) {
        Scanner scanner = new Scanner(serialized);
        return deserializeHelper(scanner);
    }

    private static TreeNode deserializeHelper(Scanner scanner) {
        String value = null;

        if (scanner.hasNext()) {
            value = scanner.next();
        }
        if (value == null || value.equals("null")) {
            return null;
        }

        return new TreeNode(Integer.parseInt(value),
                            deserializeHelper(scanner),
                            deserializeHelper(scanner));
    }

    public static void main(String[] args) {
        TreeNode root = new TreeNode(1,
            new TreeNode(2,
                new TreeNode(3),
                new TreeNode(4)),
            null);

        String serialized = root.serialize();
        System.out.println(serialized);

        TreeNode deserialized = deserialize(serialized);
        // 1 2 3 null null 4 null null null
        System.out.println(deserialized.left.right.val);
        // 4
        System.out.println(deserialized.serialize());
        // 1 2 3 null null 4 null null null 
    }
}