zoukankan      html  css  js  c++  java
  • Tree的遍历与node定义学习

    
    /*
     * 二叉树节点
     */
    public class Node {
    	//数据项
    	public long data;
    
    	//左子节点
    	public Node leftChild;
    	//右子节点
    	public Node rightChild;
    	
    	/**
    	 * 构造方法
    	 * @param data
    	 */
    	public Node(long data) {
    		this.data = data;
    	}
    	
    }
    
    /*
     * 二叉树
     */
    public class Tree {
    	//根节点
    	public Node root;
    	
    	/**
    	 * 插入节点
    	 * @param value
    	 */
    	public void insert(long value,String sValue) {
    		//封装节点
    		Node newNode = new Node(value);
    		//引用当前节点
    		Node current = root;
    		//引用父节点
    		Node parent;
    		//如果root为null,也就是第一插入的时候
    		if(root == null) {
    			root = newNode;
    			return;
    		} else {
    			while(true) {
    				//父节点指向当前节点
    				parent = current;
    				//如果当前指向的节点数据比插入的要大,则向左走
    				if(current.data > value) {
    					current = current.leftChild;
    					if(current == null) {
    						parent.leftChild = newNode;
    						return;
    					}
    				} else {
    					current = current.rightChild;
    					if(current == null) {
    						parent.rightChild = newNode;
    						return;
    					}
    				}
    			}
    		}
    	}
    	
    	/**
    	 * 查找节点
    	 * @param value
    	 */
    	public Node find(long value) {
    		//引用当前节点,从根节点开始
    		Node current = root;
    		//循环,只要查找值不等于当前节点的数据项
    		while(current.data != value) {
    			//进行比较,比较查找值和当前节点的大小
    			if(current.data > value) {
    				current = current.leftChild;
    			} else {
    				current = current.rightChild;
    			}
    			//如果查找不到
    			if(current == null) {
    				return null;
    			}
    		}
    		return current;
    	}
    
    /**
    	 * 删除节点  删除节点需要父子两层指针
    	 * @param value
    	 */
    	public boolean delete(long value) {
    		//引用当前节点,从根节点开始
    		Node current = root;
    		
    		//应用当前节点的父节点
    		Node parent = root;
    		//是否为左节点
    		boolean isLeftChild = true;
    		
    		while(current.data != value) {
    			parent = current;
    			//进行比较,比较查找值和当前节点的大小
    			if(current.data > value) {
    				current = current.leftChild;
    				isLeftChild = true;
    			} else {
    				current = current.rightChild;
    				isLeftChild = false;
    			}
    			//如果查找不到
    			if(current == null) {
    				return false;
    			}
    		}
    		
    		//删除叶子节点,也就是该节点没有子节点
    		if(current.leftChild == null && current.rightChild == null) {
    			if(current == root) {
    				root = null;
    			} else if(isLeftChild) {
    				parent.leftChild = null;
    			} else {
    				parent.rightChild = null;
    			}
    		//current的右节点空,判断current是parrent的左孩子?右孩子?决定current的leftchild插入位置
    		} else if(current.rightChild == null) {
    			if(current == root) {
    				root = current.leftChild;
    			}else if(isLeftChild) {
    				parent.leftChild = current.leftChild;
    			} else {
    				//是右节点,比parent节点要大
    				parent.rightChild = current.leftChild;
    			}
    			//current只有右孩子的情况,其次判断current是parent的左右孩子,判断插入parent的位置
    		} else if(current.leftChild == null) {
    			if(current == root) {
    				root = current.rightChild;
    			} else if(isLeftChild) {//current是parent的左孩子
    				parent.leftChild = current.rightChild;
    			} else {//current是parent的右孩子
    				parent.rightChild = current.rightChild;
    			}
    		} else {//current既有左孩子,也有右孩子
    			Node successor = getSuccessor(current);
    			// 先处理删除节点的父
    			if(current == root) {
    				root = successor;
    			} else if(isLeftChild) {
    				parent.leftChild = successor;
    			} else{
    				parent.rightChild = successor;
    			}
    			// 处理删除节点的左节点
    			successor.leftChild = current.leftChild;
    		}
    		
    		return true;
    		
    		
    	}
    	
    	public Node getSuccessor(Node delNode) {
    		Node successor = delNode;
    		Node successorParent = delNode;
    		Node current = delNode.rightChild;
    		//寻找右子树的最左侧节点,比被删除节点稍微大一点
    		while(current != null) {
    			successorParent = successor;
    			successor = current;
    			current = current.leftChild; // 删除节点的右子树的最左侧孩子节点
    		}
    		//被删除的右孩子,不等于找到的最左侧节点,successor就是右子树的最左侧孩子,successorParent是父节点
    		//不等于就是找到了,
    		if(successor != delNode.rightChild) {
    			//将最左节点的右节点给父节点是左,比较小,所以放再left
    			successorParent.leftChild = successor.rightChild;
    			// 直接放到位置了
    			successor.rightChild = delNode.rightChild;
    		}
    		return successor;
    	}
    	
    
    
    
    
    	
    	/**
    	 * 前序遍历
    	 */
    	public void frontOrder(Node localNode) {
    		if(localNode != null) {
    			//访问根节点
    			System.out.println(localNode.data + " ");
    			//前序遍历左子树
    			frontOrder(localNode.leftChild);
    			//前序遍历右子树
    			frontOrder(localNode.rightChild);
    		}
    	}
    	
    	/**
    	 * 中序遍历
    	 */
    	public void inOrder(Node localNode) {
    		if(localNode != null) {
    			//中序遍历左子树
    			inOrder(localNode.leftChild);
    			//访问根节点
    			System.out.println(localNode.data + " ");
    			//中旬遍历右子树
    			inOrder(localNode.rightChild);
    		}
    	}
    	
    	/**
    	 * 后序遍历
    	 */
    	public void afterOrder(Node localNode) {
    		if(localNode != null) {
    			//后序遍历左子树
    			afterOrder(localNode.leftChild);
    			//后序遍历右子树
    			afterOrder(localNode.rightChild);
    			//访问根节点
    			System.out.println(localNode.data + " " );
    		}
    	}
    }
    
    
  • 相关阅读:
    聊一聊-JAVA 泛型中的通配符 T,E,K,V,?
    leetcode刷到的大牛思路记录
    leetcode树有关题目随笔
    SpringMVC Controller介绍及常见注解
    一个方法团灭 6 道股票问题
    IDEA中Update resources和Update classes and resources、Redeploy、Restart server的区别
    动态规划规律总结
    mapPartitions
    RDD的依赖关系
    foreachPartition来写数据库
  • 原文地址:https://www.cnblogs.com/hbym/p/15570945.html
Copyright © 2011-2022 走看看