首页 > 代码库 > 用二叉查找树实现持久动态集合
用二叉查找树实现持久动态集合
a) 从根结点到待插入结点的这条路径上的所有结点都需要改变。
b)代码如下:
//13-1持久动态集合 #include <iostream> #include <time.h> using namespace std; #define LEN sizeof(struct Tree) #define m 10//栈的最大容纳空间可以调整 struct Tree { int key; struct Tree*lchild; struct Tree*rchild; }; //非递归的插入函数 struct Tree*PERSISTENT_TREE_INSERT(struct Tree*&root,struct Tree*z) {//只要是注释都是与12章插入函数不同之处。 struct Tree*y=NULL; struct Tree*x=root; struct Tree*root1=NULL,*p=NULL,*p2=NULL;//p为当前新树T’的当前结点。p2为原树T中等于当前结点p->key的值的父结点。 while (x) { y=new struct Tree[LEN]; y->key=x->key;//复制原树T的结点值。 if (root->key==x->key) { p=root1=y;//设置新的复制后的根结点。 } else if (z->key<p2->key) { p->lchild=y;//设置复制后的新树T’的当前结点的左右孩子 p->rchild=p2->rchild; p=p->lchild;//更新新树当前结点。 } else { p->rchild=y; p->lchild=p2->lchild; p=p->rchild; } p2=x; if (z->key<p2->key) x=x->lchild; else x=x->rchild; } y->lchild=y->rchild=NULL;//找到且复制待插入结点的父结点后,把复制后的新父结点左右孩子置空。 if (y==NULL) { root=z; } else if(z->key<y->key) { y->lchild=z; } else y->rchild=z; z->lchild=z->rchild=NULL; return root1; } //非递归的插入函数 void ITERATIVE_TREE_INSERT(struct Tree*&root,struct Tree*z) { struct Tree*y=NULL; struct Tree*x=root; while (x) { y=x; if (z->key<x->key) x=x->lchild; else x=x->rchild; } if (y==NULL) { root=z; } else if(z->key<y->key) { y->lchild=z; } else y->rchild=z; z->lchild=z->rchild=NULL; } //中序遍历 void InOderTraverse(struct Tree *p) { if (p) { InOderTraverse(p->lchild); cout<<p->key<<" "; InOderTraverse(p->rchild); } } void main() { int array[6]={4,3,8,2,7,10}; //int array[10]={5,3,8,2,4,7,10,6,9,11}; int i=0; struct Tree*root=NULL; struct Tree*z=new struct Tree[LEN]; z->key=array[i++];//20 ITERATIVE_TREE_INSERT(root,z); while (i!=6) { z=new struct Tree[LEN]; z->key=array[i++]; ITERATIVE_TREE_INSERT(root,z); } z=new struct Tree[LEN]; z->key=5;//12 struct Tree*root1=PERSISTENT_TREE_INSERT(root,z); InOderTraverse(root);//原树T cout<<endl; InOderTraverse(root1);//新树T’ cout<<endl;
c)时间就是a部分所说的路径上的所有结点,这个结点数量等于树高。而空间上又和新分配结点数成正比,所以时间空间都为O(h).
d)由于增加了父结点,那么需要复制整棵树,为什么呢? 比如题目中的二叉树图所给例子,结点3和4,如果在调用新插入函数时,不对结点3也就是旧结点复制,那么新树T’中的结点3的父结点就会指向旧树中结点4,而不是新树中的结点4,查看结点地址就会明白。所以需要的时间就是Ω(n),在不是必须引入父指针时,最好不要使用它,以免增加时间空间上的工作量。
e)用红黑树实现持久动态集合,又要求最坏时间为O(lgn),那么就不能有父结点,根据13,3-6题目知可以通过辅助栈来实现不带父指针的红黑树,这样就能满足题意。
声明:以上内容来自用户投稿及互联网公开渠道收集整理发布,本网站不拥有所有权,未作人工编辑处理,也不承担相关法律责任,若内容有误或涉及侵权可进行投诉: 投诉/举报 工作人员会在5个工作日内联系你,一经查实,本站将立刻删除涉嫌侵权内容。