二叉树、 树的遍历操作、 二叉查找树 、 Trie 树(字典树)

目录

二叉树

树的遍历操作

二叉查找树

Trie 树(字典树)

总结

LetCode真题

230. 二叉搜索树中第K小的元素


二叉树

在二叉树中,有下面两个特殊的类型,如下图所示:

  • 满二叉树,定义为除了叶子结点外,所有结点都有 2 个子结点。

  • 完全二叉树,定义为除了最后一层以外,其他层的结点个数都达到最大,并且最后一层的叶子结点都靠左排列。

存储二叉树有两种办法,一种是基于指针的链式存储法,另一种是基于数组的顺序存储法。

  • 链式存储法,也就是像链表一样,每个结点有三个字段,一个存储数据,另外两个分别存放指向左右子结点的指针,如下图所示:

 

  • 顺序存储法,就是按照规律把结点存放在数组里,如下图所示,为了方便计算,我们会约定把根结点放在下标为 1 的位置。随后,B 结点存放在下标为 2 的位置,C 结点存放在下标为 3 的位置,依次类推。

我们可以发现如果结点 X 的下标为 i,那么 X 的左子结点总是存放在 2 * i 的位置,X 的右子结点总是存放在 2 * i + 1 的位置。

树的遍历操作

// 先序遍历
public static void preOrderTraverse(Node node) {
    if (node == null)
        return;
    System.out.print(node.data + " ");
    preOrderTraverse(node.left);
    preOrderTraverse(node.right);
}
// 中序遍历
public static void inOrderTraverse(Node node) {
    if (node == null)
        return;
    inOrderTraverse(node.left);
    System.out.print(node.data + " ");
    inOrderTraverse(node.right);
}
// 后序遍历
public static void postOrderTraverse(Node node) {
    if (node == null)
        return;
    postOrderTraverse(node.left);
    postOrderTraverse(node.right);
    System.out.print(node.data + " ");
}

二叉查找树

二叉查找树(也称作二叉搜索树)具备以下几个的特性:

  • 在二叉查找树中的任意一个结点,其左子树中的每个结点的值,都要小于这个结点的值。
  • 在二叉查找树中的任意一个结点,其右子树中每个结点的值,都要大于这个结点的值。
  • 在二叉查找树中,会尽可能规避两个结点数值相等的情况。
  • 对二叉查找树进行中序遍历,就可以输出一个从小到大的有序数据队列。如下图所示,中序遍历的结果就是 10、13、15、16、20、21、22、26。

二叉查找树的查找操作:二分查找

二叉树的插入操作

二叉查找树的删除

情况一,如果要删除的结点是某个叶子结点,则直接删除,将其父结点指针指向 null 即可。

情况二,如果要删除的结点只有一个子结点,只需要将其父结点指向的子结点的指针换成其子结点的指针即可。

情况三,如果要删除的结点有两个子结点,则有两种可行的操作方式。

   第一种,找到这个结点的左子树中最大的结点,替换要删除的结点。左的最大替换

第二种,找到这个结点的右子树中最小的结点,替换要删除的结点。右的最小

 

Trie 树(字典树)

范例:输入一个字符串,判断它在已有的字符串集合中是否出现过?(假设集合中没有某个字符串与另一个字符串拥有共同前缀且完全包含的特殊情况,例如 deep 和 dee。)如,已有字符串集合包含 6 个字符串分别为,cat, car, city, dog,door, deep。输入 cat,输出 true;输入 home,输出 false。

我们对字符串建立一个的树结构,如下图所示,它将字符串集合的前缀进行合并,每个根结点到叶子结点的链条就是一个字符串。

这个树结构也称作 Trie 树,或字典树。它具有三个特点:

第一,根结点不包含字符;

第二,除根结点外每一个结点都只包含一个字符;

第三,从根结点到某一叶子结点,路径上经过的字符连接起来,即为集合中的某个字符串。

这个问题的解法可以拆解为以下两个步骤:

第一步,根据候选字符串集合,建立字典树。这需要使用数据插入的动作。

第二步,对于一个输入字符串,判断它能否在这个树结构中走到叶子结点。如果能,则出现过。

总结

要想利用二叉树实现增删查操作,你需要熟练掌握二叉树的三种遍历方式。遍历的时间复杂度是 O(n)。有了遍历方式之后,你可以完成在指定位置的数据增删操作。增删操作的时间复杂度都是 O(1)。

对于查找操作,如果是普通二叉树,则查找的时间复杂度和遍历一样,都是 O(n)。如果是二叉查找树,则可以在 O(logn) 的时间复杂度内完成查找动作。树结构在存在“一对多”的数据关系中,可被高频使用,这也是它区别于链表系列数据结构的关键点。

LetCode真题

230. 二叉搜索树中第K小的元素

class Solution {
	public  void inorder(TreeNode root, List<Integer> list) {
		if(root == null) {
			return ;
		}
		inorder(root.left, list);
		list.add(root.val) ;
		inorder(root.right, list) ;
	}

	public  int kthSmallest(TreeNode root, int k) {
		List<Integer> list = new ArrayList<Integer>() ;
		inorder(root, list) ;
		return list.get(k-1) ;
	}
}

 

 

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值