树的基本操作

9 篇文章 0 订阅
3 篇文章 0 订阅

题目:重构二叉树

输入输入某二叉树的前序遍历和中序遍历的结果,请重构该二叉树。

假设输入的前序遍历和中序遍历的结果中都不包含重复的数字。例如,输入前序遍历序列{1,2,4,7,3,5,6,8}和中序遍历序列{4,7,2,1,5,3,8,6},重建该树。树的结点类如下:

class TreeNode{
	int value;
	TreeNode left;
	TreeNode right;
	TreeNode(int val){
		this.value = value;
	}
}

解决:

思路:

通过前序遍历获取根节点的值,然后遍历中序遍历序列,找到根节点,将中序遍历数组分成左右两个树支,然后递归调用,构成一个树。

public TreeNode reConstructBinaryTree(int [] pre,int [] in) {
         //边界条件的判断
        if(pre == null || in == null){
            return null;
        }
        if(pre.length==0 || in.length == 0){
            return null;
        }
        //前序和中序遍历的长度不一致
        if(pre.length != in.length){
            return null;
        }
        //获取树的根节点
        TreeNode root = new TreeNode(pre[0]);
        for(int i= 0;i<in.length;i++){
            //在中序遍历中找到前序遍历的值,将中序遍历分成两半
            if(in[i] == pre[0]){
                root.left = reConstructBinaryTree(Arrays.copyOfRange(pre,1,i+1),Arrays.copyOfRange(in,0,i));
                root.right = reConstructBinaryTree(Arrays.copyOfRange(pre,i+1,pre.length),Arrays.copyOfRange(in,i+1,in.length));
            }
        }
        return root;
    }

对于树的结构的打印

思路:初步思考这样实现:

......|-6-|
......|...|-8
..|-3-|
..|...|-5
1-|
..|-2-|
......|...|-7
......|-4-|

实现display方法,打印树的结构;先打印右子树的结点,然后再打印根节点,最后打印左子节点。

设置树的每一个节点的表示字符串,树的结点类表示如下:

class TreeNode{
    int value;
    TreeNode leftNode;
    TreeNode rightNode;
    String s ;//用于描述改节点的字符串描述
    TreeNode(int value) {
        this.value = value;
    }
}

通过构造树,并将每一个节点表示的字符串进行设置

/**
     * 用于设置每一个节点的字符串描述
     * @param parent  父节点
     * @param next  设置字符串的结点
     * @param flag  是否是左节点的右节点的判断
     */
    private static void setTreeStructure(TreeNode parent,TreeNode next,boolean flag){
        //如果是叶子节点的时候,直接返回
        if(next == null){
            return;
        }
        //首先是将前面的根节点的数字替换为' . ' ,为后面添加自己的数值做准备
            next.s = parent.s.replaceAll("[0-9]|-",".").substring(0,parent.s.length()-1);
        //如果不是内嵌节点,就可以直接将| 全部替换为 .
            if(flag == false) {
                int index = next.s.lastIndexOf("|");
                if (index != -1) {
                    next.s = next.s.substring(0, index) + "." +  next.s.substring(index + 1);
                }
            }
            //添加该节点的值
            next.s+="|-"+next.value+"-|";
            //进入左右节点的判断
            if(parent.leftNode == next ){
                if(next.rightNode!=null)
                    setTreeStructure(next,next.rightNode,true);
                if(next.leftNode != null){
                    setTreeStructure(next,next.leftNode,false);
                }
            }
            if(parent.rightNode == next){
                if(next.leftNode != null){
                    setTreeStructure(next,next.leftNode,true);
                }
                if(next.rightNode != null){
                    setTreeStructure(next,next.rightNode,false);
                }
            }
    }

最后将树的结构打印出来

public static void printTree(TreeNode node){
        //始终先打印右节点,然后打印本身,最后打印左节点
        if(node.rightNode!=null){
            printTree(node.rightNode);
        }
        //如果没有子节点,就不打印后面的"-|“
        if(node.leftNode==null&&node.rightNode==null){
            System.out.println(node.s.substring(0, node.s.length()-2));
        }else{
            //有子节点的直接打印该节点的描述
            System.out.println(node.s);
        }
        if(node.leftNode!=null){
            printTree(node.leftNode);
        }
    }

最后来个主方法,看看如何设置树的结构

public static void main(String [] args){
        int [] pre = {1,2,4,7,3,5,6,8};//先根遍历结果
        int [] in = {4,7,2,1,5,3,8,6};//后根遍历结果
        TreeNode root = reConstructBinaryTree(pre,in);
        //display(root);
        root.s = root.value + "-|";
        setTreeStructure(root,root.leftNode,false);//设置左节点
        setTreeStructure(root,root.rightNode,false);
        //输出
        printTree(root);
    }
二叉排序也称为二叉搜索,它是一种特殊的二叉,满足以下性质: 1. 左子中的所有节点的值均小于根节点的值; 2. 右子中的所有节点的值均大于根节点的值; 3. 左子和右子也都是二叉排序基本操作包括插入节点、删除节点和查找节点。下面是它们的实现: 1. 插入节点: 插入节点操作用于向二叉排序中插入一个新节点。从根节点开始,比较插入节点的值与当前节点的值,如果小于当前节点的值,则进入左子,否则进入右子。直到找到一个空位置,将新节点插入到该位置。 示例代码如下: ```python class TreeNode: def __init__(self, val): self.val = val self.left = None self.right = None def insert_node(root, val): if root is None: return TreeNode(val) if val < root.val: root.left = insert_node(root.left, val) else: root.right = insert_node(root.right, val) return root ``` 2. 删除节点: 删除节点操作用于从二叉排序中删除指定节点。分为三种情况: - 被删除节点没有子节点:直接删除即可; - 被删除节点只有一个子节点:将子节点替代被删除节点的位置; - 被删除节点有两个子节点:找到被删除节点的后继节点(右子中最小的节点),将后继节点的值复制到被删除节点,然后删除后继节点。 示例代码如下: ```python def find_min(node): while node.left is not None: node = node.left return node def delete_node(root, val): if root is None: return root if val < root.val: root.left = delete_node(root.left, val) elif val > root.val: root.right = delete_node(root.right, val) else: if root.left is None: return root.right elif root.right is None: return root.left else: successor = find_min(root.right) root.val = successor.val root.right = delete_node(root.right, successor.val) return root ``` 3. 查找节点: 查找节点操作用于在二叉排序中查找指定值的节点。从根节点开始,比较目标值与当前节点的值,如果小于当前节点的值,则进入左子,否则进入右子。如果找到匹配的节点,则返回该节点;如果遍历完整个仍未找到匹配的节点,则返回空。 示例代码如下: ```python def search_node(root, val): if root is None or root.val == val: return root if val < root.val: return search_node(root.left, val) else: return search_node(root.right, val) ``` 以上是二叉排序基本操作的实现。你可以根据需要调用这些函数来操作二叉排序
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值