本片博客转自:https://blog.csdn.net/hello_world_lvlcoder/article/details/72615092
定义:
本片博客前面部分截取自算法(第4版
查找:
要判断一个键是否存在树中,先将它和根节点中的键比较,如果它和其中任意一个相等,查找命中;否则就根据比较的结果找到指向相应区间的连接,并在其指向的子树中递归地继续查找,如果找到了空连接上,查找未命中。
插入:
插入之前,先要对2-3树进行一次未命中的查找:
1、 向2-节点中插入新键
如果未命中查找结束于一个2-节点,直接将2-节点替换为一个3-节点,并将要插入的键保存在其中
2、 向一颗只含3-节点的树中插入新键
先临时将新键存入唯一的3-节点中,使其成为一个4-节点,再将它转化为一颗由3个2-节点组成的2-3树,分解后树高会增加1
3、 向一个双亲节点为2-节点的3-节点中插入新键
先构造一个临时的4-节点并将其分解,分解时将中键移动到双亲节点中(中键移动后,其双亲节点中的位置由键的大小确定)
4、 向一个双亲节点为3-节点的3-节点中插入新键
一直向上分解构造的临时4-节点并将中键移动到更高层双亲节点,直到遇到一个-2节点并将其替换为一个不需要继续分解的3-节点,或是到达树根(3-节点)。
5、 分解根节点
如果从插入节点到根节点的路径上全是3-节点,根将最终被替换为一个临时的4-节点,将临时的4-节点分解为3个2-节点,分解后树高会增加1
变换:
1、局部变换
将对一个4-节点的分解叫做变换,对一个4-节点的变换方式可能有6种:
这些变换都是局部的,除了相关的节点和链接之外不必修改或检查树的其他部分
2、全局性质:
变换不会影响树的全局有序性和平衡性,任意空链接到根节点的路径长度依旧是相等的
生长:
后面部分参考自大话数据结构
删除:
插入之前,先要对2-3树进行一次命中的查找:
1、删除非叶子节点key:
使用中序遍历下的直接后继节点key来覆盖当前节点key,再删除用来覆盖的后继节点key
2、删除叶子节点key:
a) 当前节点不是2-节点,直接删除key
b) 当前节点是2-节点,删除节点,并作一些判断:
a) 当前节点的双亲节点是2-节点、兄弟节点是3-节点,将双亲节点移动到当前位置,再将兄弟节点中最接近当前位置的key移动到双亲节点中
b) 当前节点的双亲节点是2-节点、兄弟节点也是2-节点,先通过移动兄弟节点的中序遍历直接后驱到兄弟节点,以使兄弟节点变为3-节点;再进行a)的操作
c) 当前节点的双亲节点是3-节点,拆分双亲节点使其成为2-节点,再将再将双亲节点中最接近的一个拆分key与中孩子合并,将合并后的节点作为当前节点
d) 2-3树是一颗满二叉树,将2-3树层树减少,并将兄弟节点合并到双亲节点中,同时将双亲节点的所有兄弟节点合并到双亲节点的双亲节点中,如果生成了-4节点,再分解4-节点即可