2-3树的实现初探

       前篇文章(2-3树的实现分析)已经分析了2-3树的遍历(traverse),检索(retrieve),插入(insert)和删除(delete)的算法,经过三天的努力,我在分析的基础上采用回溯的方式实现了2-3树,由于还在初级阶段,肯定会出现不少的问题,请多赐教。但经过测试,运行还算正确。下面是代码实现:

2-3树的异常处理类

//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
//         two_three_tree_exception.h
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
#ifndef TWO_THREE_TREE_EXCEPTION_H_
#define TWO_THREE_TREE_EXCEPTION_H_
#include<stdexcept>
#include<string>
class TTTException :public std::logic_error
{
	public:
		TTTException(const std::string &message="")
			:std::logic_error(message.c_str())
		{}
};
#endif


2-3树的item类,每个节点的数据的存储在这里,包含了一个关键字keyword和相关的值 tel。

//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
//              two_three_tree_item.h
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
#ifndef TWO_THREE_TREE_ITEM_H_
#define TWO_THREE_TREE_ITEM_H_
#include<string>
typedef std::string KeyType;
class ItemType
{
	public:
		ItemType(){}
		ItemType(const KeyType &_key,const std::string &_tel)
			:keyword(_key),tel(_tel)
		{}
		//get key word keyword;
		const KeyType & getKey()const
		{
			return keyword;
		}
		//set value tel;
		void setTel(const std::string &_tel)
		{
			tel=_tel;
		}
		//get value tel;
		std::string getTel()const
		{
			return tel;
		}
	private:
		KeyType keyword;
		std::string tel;
};
#endif

2-3树的节点类,实现树的完整连接,其中包含两个item,三个孩子:左孩子,中孩子,右孩子

//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
//             two_three_tree_node.h
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
#ifndef TWO_THREE_TREE_NODE_H_
#define TWO_THREE_TREE_NODE_H_
#include"two_three_tree_item.h"
class Node
{
	private:
		Node(ItemType &_item,Node *_leftPtr,Node*_middlePtr)
			:fItem(_item),LeftPtr(_leftPtr)
			 ,MiddlePtr(_middlePtr),RightPtr(NULL)
		{Nitems=1;}
		//当节点中的item项数为1时,调用此函数重新整合节点
		void reSet(ItemType &_item,Node *_leftPtr,
				Node*_middlePtr)
		{
			Node *tempL=_leftPtr,*tempM=_middlePtr;
			fItem=_item;
			LeftPtr=tempL;
			MiddlePtr=tempM;
			RightPtr=NULL;
			setNumb(1);
		}
		//当节点中的item项数为2时,调用此函数重新整合节点
		void reSet( ItemType &_fitem,ItemType &_litem,Node *_leftPtr,Node *_middlePtr,Node *_rightPtr)
		{
			ItemType tempfi=_fitem,templi=_litem;
			Node *tempL=_leftPtr,*tempM=_middlePtr,*tempR=_rightPtr;
			LeftPtr=tempL;
			MiddlePtr=tempM;
			RightPtr=tempR;
			fItem=tempfi;
			lItem=templi;
			setNumb(2);
			
		}
		//设置节点中item的数目
		void setNumb(int n)
		{
			Nitems=n;
		}
		//清空当前节点中的孩子和item(items)
		void clear()
		{
			LeftPtr=MiddlePtr=RightPtr=NULL;
			setNumb(0);
		}

		ItemType fItem,lItem;
		Node *LeftPtr,*MiddlePtr,*RightPtr;
		int Nitems;
		friend class ttTree;
};

#endif

2-3树实现的头文件

//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
//             two_three_tree.h
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
#ifndef TWO_THREE_TREE_H_
#define TWO_THREE_TREE_H_
#include"two_three_tree_exception.h"
#include"two_three_tree_node.h"
typedef void (*FuncT)(ItemType &_item);
class ttTree
{
	public:
		//默认构造函数
		ttTree();
              	//复制构造函数
		ttTree(ttTree &_tree);
		//析构函数
		virtual ~ttTree();
		

		virtual bool empty()const;
		
		//检索
		virtual void retrieve(const KeyType &_keyword,ItemType &_item)throw(TTTException);

		//遍历
		virtual void traverse(FuncT visit);
		
		//插入
		virtual void insert(const ItemType & newitem)
			throw(TTTException);
		
		//删除
		virtual void remove(const KeyType &keyword)
			throw(TTTException);

		//赋值操作符重载
		virtual ttTree &operator=(ttTree &oldtree)throw(TTTException);

	protected:

		bool insertTree(Node *&treePtr,Node *&tempPtr,ItemType &tempItem)throw(TTTException);
		bool removeTree(Node *&treePtr,Node *&tempPtr,const KeyType &_key)
			throw(TTTException);
		void retrieveTree(Node * &treePtr,const KeyType &_key,ItemType &_item)throw(TTTException);
		void traverseTree(Node *&treePtr,FuncT visit);

		//复制构造函数
		void copyTree(Node *&newtree, Node* &oldtree)throw(TTTException);

		void destroy(Node *&treePtr);

		//在插入的情况下,当当前的item数大于2时,调用此函数维护2-3的原有属性
		bool insertMaintain(Node *&treePtr,Node *&tempPtr,ItemType &tempItem,char ch)throw(TTTException);
		//在删除的情况下,当当前的item数小于1时,调用此函数维护2-3的原有属性
		bool removeMaintain(Node *&treePtr,Node *&tempPtr,char ch);
		
		//寻找当前节点treeptr中项目的中序后继,
		int processLeft(Node *&treePtr,Node*&tempPtr,ItemType &replace);

		//当前的节点treePtr中item数目为2时返回true,否侧返回false
		bool twoItem(Node *&treePtr)const;

		//当前的节点treePtr中的item数目为1时返回true,否则返回false
		bool oneItem(Node *&treePtr)const;

		//判断当前节点treePtr是否为根节点,如是则返回true,否则返回false
		bool isRoot(Node *&treePtr)const;

		//判断当前节点treePtr是否为叶节点,若是则返回true,否则返回false
		bool isLeaf(Node *&treePtr)const;

		//判断当前节点treePtr中是否存在与关键字_key相等的项
		//若存在则返回true,否则返回false
		bool equal(Node*&treePtr,const KeyType & _key)const;


		//按项中关键字的大小重新排序first,middle,last,使其满足
		//first.getkey()<=middle.getKey()<=last.getkey()
		void sort(ItemType &first,ItemType &middle,ItemType &last);

	private:
		Node *root;
};
#endif


2-3树的现实文件

#include<cstddef>
#include<cassert>
#include"two_three_tree.h"
using namespace std;
ttTree::ttTree():root(NULL)
{
}
ttTree::ttTree(ttTree &_tree)
{
	copyTree(root,_tree.root);
}
ttTree::~ttTree()
{
	destroy(root);
}
bool ttTree::empty()const
{
	return root==NULL;
}
void ttTree::retrieve(const KeyType &_keyword,ItemType &_item)
		throw(TTTException)
{
	try{
		retrieveTree(root,_keyword,_item);
	}catch(TTTException &e)
	{
		throw;
	}
}
void ttTree::traverse(FuncT visit)
{
	traverseTree(root,visit);
}
void ttTree::insert(const ItemType &newitem)
	throw(TTTException)
{
	Node *inPtr=NULL;
	//point to a new creating Node, and deliver new node to
	//last time insertTree function called
	ItemType inItem=newitem;
	// contain the "internal" item value that canot be cotained in this 
	// node 
	try{
		bool ok=insertTree(root,inPtr,inItem);
		if(!ok)
			throw TTTException("TTTException :insert newitem failed !");
	
	}catch(TTTException &e)
	{
		throw;
	}
}
void ttTree::remove(const KeyType &keyword)
	throw(TTTException)
{
	Node *rePtr=NULL;
	//point to the empty node's child
	try{
		bool ok=removeTree(root,rePtr,keyword);
		if(!ok)
			throw TTTException("TTTException :remove item failed !");
	}catch(TTTException &e)
	{
		throw;
	}
}
ttTree &ttTree::operator=(ttTree &oldtree)throw(TTTException)
{
	try{
		if(this==&oldtree)
			return *this;
		else
		{
			destroy(root);
			copyTree(root,oldtree.root);
		}
	}catch(TTTException &e)
	{
		throw;
	}
}
bool ttTree::insertTree(Node *&treePtr,Node *&tempPtr,
		ItemType &tempItem)throw(TTTException)
{
	if(empty())
	{
		treePtr=new Node(tempItem,NULL,NULL);
		if(treePtr==NULL)
			throw TTTException("TTTException :allocate memory failed !");
		return true;
	}
	else if(isLeaf(treePtr))
	{
		try{
			return insertMaintain(treePtr,tempPtr,tempItem,'F');
		}catch(TTTException &e)
		{
			throw;
		}
	}
	else if((tempItem.getKey())<(treePtr->fItem.getKey()))
	{
		bool success=insertTree(treePtr->LeftPtr,tempPtr,tempItem);
		if(success)
			return true;
		else
		{	try{
				return insertMaintain(treePtr,tempPtr,tempItem,'L');
			}catch(TTTException &e)
			{
				throw;
			}
		}

	}
	else if(twoItem(treePtr)&&(tempItem.getKey()>=treePtr->lItem.getKey()))
	{
		bool success=insertTree(treePtr->RightPtr,tempPtr,tempItem);
		if(success)
			return true;
		else
		{
			try{
				return insertMaintain(treePtr,tempPtr,tempItem,'R');
			}catch(TTTException &e)
			{
				throw;
			}
		}
	}
	else
	{
		bool success=insertTree(treePtr->MiddlePtr,tempPtr,tempItem);
		if(success)
			return true;
		else
		{
			try{
				return insertMaintain(treePtr,tempPtr,tempItem,'M');
			}catch(TTTException &e)
			{
				throw;
			}
		}
	}
}

bool ttTree::removeTree(Node *&treePtr,Node *&tempPtr,const KeyType &_key)
	throw(TTTException)
{
	if(empty())
		throw TTTException("TTTException :two three tree is empty !");
	else if(isLeaf(treePtr)&&(!equal(treePtr,_key)))
		throw TTTException("TTTException :item contian keyword not exist !");
	else if(equal(treePtr,_key))
	{
		ItemType replace;
		 if(treePtr->fItem.getKey()==_key)
		 {

			 int placeok=processLeft(treePtr->MiddlePtr,tempPtr,replace);
			 treePtr->fItem=replace;
			 if(placeok==0)
				 return true;
			 else if(placeok==1)
			 {
				 return removeMaintain(treePtr,tempPtr,'M');

			 }
			 else
			 {
				 if(twoItem(treePtr))
				 {
					 treePtr->reSet(treePtr->lItem,NULL,NULL);
					 return true;
				 }
				 return false;
			 }
		 }
		 else 
		 {
			 int placeok=processLeft(treePtr->RightPtr,tempPtr,replace);
			 //must deal with solution that treePtr is a leaf
			 treePtr->lItem=replace;
			 if(placeok==0)
				 return true;
			 else if(placeok==1)
			 {
				 return removeMaintain(treePtr,tempPtr,'R');
			 }
			 else
			 {
				 treePtr->reSet(treePtr->fItem,NULL,NULL);
				 return true;
			 }
		 }
	}
	else if(_key<(treePtr->fItem.getKey()))
	{
		bool success=removeTree(treePtr->LeftPtr,tempPtr,_key);
		if(success)
			return true;
		else
		{
			return removeMaintain(treePtr,tempPtr,'L');
		}
	}
	else if(twoItem(treePtr)&&(_key>=(treePtr->lItem.getKey())))
	{
		bool success=removeTree(treePtr->RightPtr,tempPtr,_key);
		if(success)
			return true;
		else
			return removeMaintain(treePtr,tempPtr,'R');
	}
	else
	{
		bool success=removeTree(treePtr->MiddlePtr,tempPtr,_key);
		if(success)
			return true;
		else
			return removeMaintain(treePtr,tempPtr,'R');
	}
}

int ttTree::processLeft(Node *&treePtr,Node *&tempPtr,ItemType &replace)
{
	if(treePtr==NULL)
		return 2;
	else if(isLeaf(treePtr))
	{
		replace=treePtr->fItem;
		if(twoItem(treePtr))
		{
			treePtr->reSet(treePtr->lItem,NULL,NULL);
			return 0;
		}
		tempPtr=NULL;
		return 1;
	}
	else
	{
		int result=processLeft(treePtr->LeftPtr,tempPtr,replace);
		if(result==0)
			return 0;
		else if(result==1)
		{
			bool placeok=removeMaintain(treePtr,tempPtr,'L');
			if(placeok)
				return 0;
			else
				return 1;
		}
	}
}
void ttTree::retrieveTree(Node * &treePtr,const KeyType &_key,
		ItemType &_item) throw(TTTException)
{
	if(empty())
		throw TTTException("TTTException:empty two three tree !");
	else if(isLeaf(treePtr)&&(!equal(treePtr,_key)))
		throw TTTException("TTTException :the item whose key word equal to _key not exist !");
	else if(equal(treePtr,_key))
	{
		if(treePtr->fItem.getKey()==_key)
			_item=treePtr->fItem;
		else
			_item=treePtr->lItem;
	}
	else if(_key<(treePtr->fItem.getKey()))
		retrieveTree(treePtr->LeftPtr,_key,_item);
	else if(twoItem(treePtr)&&(_key>=treePtr->lItem.getKey()))
		retrieveTree(treePtr->RightPtr,_key,_item);
	else
		retrieveTree(treePtr->MiddlePtr,_key,_item);
}
void ttTree::traverseTree(Node *&treePtr,FuncT visit)
{
	if(treePtr!=NULL)
	{
		traverseTree(treePtr->LeftPtr,visit);
		visit(treePtr->fItem);
		traverseTree(treePtr->MiddlePtr,visit);
		if(twoItem(treePtr))
		{
			visit(treePtr->lItem);
			traverseTree(treePtr->RightPtr,visit);
		}
	}

}
void ttTree::copyTree(Node *&newtree,Node * &oldtree)
	throw(TTTException)
{
	if(oldtree!=NULL)
	{
		newtree= new Node(oldtree->fItem,NULL,NULL);
		if(newtree==NULL)
			throw TTTException("TTTException :allocate memory failed !");
	
		if(twoItem(oldtree))
		{
			newtree->reSet(oldtree->fItem,oldtree->lItem,
					NULL,NULL,NULL);

		}
		copyTree(newtree->LeftPtr,oldtree->LeftPtr);
		copyTree(newtree->MiddlePtr,oldtree->MiddlePtr);
		if(twoItem(oldtree))
			copyTree(newtree->RightPtr,oldtree->RightPtr);
	}
}

void ttTree::destroy(Node *&treePtr)
{
	if(treePtr!=NULL)
	{
		destroy(treePtr->LeftPtr);
		destroy(treePtr->MiddlePtr);
		if(twoItem(treePtr))//may be left out
			destroy(treePtr->RightPtr);
		delete treePtr;
		treePtr=NULL;
	}
}

bool ttTree::twoItem(Node *&treePtr)const
{
	if(treePtr->Nitems==2)
		return true;
	else
		return false;
}

bool ttTree::oneItem(Node *&treePtr)const
{
	if(treePtr->Nitems==1)
		return true;
	else
		return false;
}
bool ttTree::isRoot(Node *&treePtr)const
{
	if((root!=NULL)&&(root==treePtr))
		return true;
	else 
		return false;
}
bool ttTree::isLeaf(Node *&treePtr)const
{
	if((treePtr->LeftPtr==NULL)&&(treePtr->MiddlePtr==NULL)
			&&(treePtr->RightPtr==NULL))
		return true;
	else
		return false;
}
bool ttTree::equal(Node *&treePtr,const KeyType &_key)const
{
	if(treePtr->fItem.getKey()==_key)
		return true;
	else if(twoItem(treePtr)&&(treePtr->lItem.getKey()==_key))
		return true;
	else
		return false;

}

void ttTree::sort(ItemType &first,ItemType &middle,ItemType &last)
{
	ItemType temp;
	if(first.getKey()<middle.getKey())
	{
		if(first.getKey()<last.getKey())
		{
			if(middle.getKey()>=last.getKey())
			{
				temp=middle;
				middle=last;
				last=temp;
			}
		}
		else
		{
			temp=last;
			last=middle;
			middle=first;
			first=temp;
		}

	}
	else
	{
		if(middle.getKey()<last.getKey())
		{
			if(first.getKey()<last.getKey())
			{
				temp=middle;
				middle=first;
				first=temp;
			}
			else
			{
				temp=middle;
				middle=last;
				last=first;
				first=temp;
			}
		}
		else
		{
			temp=last;
			last=first;
			first=temp;
		}
	}
}

bool ttTree::removeMaintain(Node *&treePtr,Node *&tempPtr,char ch)
{
	if(ch=='R')//R for ptr1 relative to ptr2's position is right
	{	
		if(twoItem(treePtr->MiddlePtr))
		{
			treePtr->RightPtr->reSet(treePtr->lItem,treePtr->MiddlePtr->RightPtr,tempPtr);
			treePtr->reSet(treePtr->fItem,treePtr->MiddlePtr->lItem,treePtr->LeftPtr,treePtr->MiddlePtr,treePtr->RightPtr);
			treePtr->MiddlePtr->reSet(treePtr->MiddlePtr->fItem,treePtr->MiddlePtr->LeftPtr,treePtr->MiddlePtr->MiddlePtr);
			return true;
		}
		else
		{
			treePtr->MiddlePtr->reSet(treePtr->MiddlePtr->fItem,treePtr->lItem,treePtr->MiddlePtr->LeftPtr,treePtr->MiddlePtr->MiddlePtr,tempPtr);
			treePtr->RightPtr->clear();//clear function ----
			delete treePtr->RightPtr;
			treePtr->RightPtr=NULL;
			treePtr->reSet(treePtr->fItem,treePtr->LeftPtr,treePtr->MiddlePtr);
			return true;

		}

	}
	else if(ch=='M')
	{
		if(twoItem(treePtr->LeftPtr))// function ---------------
		{
			treePtr->MiddlePtr->reSet(treePtr->fItem,treePtr->LeftPtr->RightPtr,tempPtr);
			treePtr->reSet(treePtr->LeftPtr->lItem,treePtr->lItem,treePtr->LeftPtr,treePtr->MiddlePtr,treePtr->RightPtr);
			treePtr->LeftPtr->reSet(treePtr->LeftPtr->fItem,treePtr->LeftPtr->LeftPtr,treePtr->LeftPtr->MiddlePtr);
			return true;
		}
		else
		{
			treePtr->LeftPtr->reSet(treePtr->LeftPtr->fItem,treePtr->fItem,treePtr->LeftPtr->LeftPtr,treePtr->LeftPtr->MiddlePtr,tempPtr);
			treePtr->MiddlePtr->clear();
			delete treePtr->MiddlePtr;
			treePtr->MiddlePtr=NULL;
			if(oneItem(treePtr))
			{
				treePtr->setNumb(0);
				tempPtr=treePtr->LeftPtr;
				if(isRoot(treePtr))
				{
					treePtr->clear();
					delete treePtr;
					treePtr=tempPtr;
					return true;
				}
				return false;
			}
			else
			{
				treePtr->reSet(treePtr->lItem,treePtr->LeftPtr,treePtr->RightPtr);
				return true;
			}
		}
	}
	else if(ch=='L')//L for ptr1 relative to ptr2's position is left
	{
		if(twoItem(treePtr->MiddlePtr))
		{
			treePtr->LeftPtr->reSet(treePtr->fItem,tempPtr,treePtr->MiddlePtr->LeftPtr);
			treePtr->reSet(treePtr->MiddlePtr->fItem,treePtr->lItem,treePtr->LeftPtr,treePtr->MiddlePtr,treePtr->RightPtr);
			treePtr->MiddlePtr->reSet(treePtr->MiddlePtr->lItem,treePtr->MiddlePtr->MiddlePtr,treePtr->MiddlePtr->RightPtr);
			return true;
		}
		else
		{
			treePtr->MiddlePtr->reSet(treePtr->fItem,treePtr->MiddlePtr->lItem,tempPtr,treePtr->MiddlePtr->LeftPtr,treePtr->MiddlePtr->MiddlePtr);
			treePtr->LeftPtr->clear();
			delete treePtr->LeftPtr;
			treePtr->LeftPtr=NULL;
			if(oneItem(treePtr))
			{
				treePtr->setNumb(0);
				tempPtr=treePtr->MiddlePtr;
				if(isRoot(treePtr))
				{
					treePtr->clear();
					delete treePtr;
					treePtr=tempPtr;
					return true;
				}
				return false;
			}
			else
			{
				treePtr->reSet(treePtr->lItem,treePtr->MiddlePtr,treePtr->RightPtr);
				return true;
			}
		}
	}

}


bool ttTree::insertMaintain(Node *&treePtr,Node *&tempPtr,
		ItemType &tempItem,char ch)
		throw(TTTException)
{
	if(ch=='L')
	{
		if(twoItem(treePtr))
		{
			ItemType tranItem=treePtr->fItem;
			Node *tranPtr=new Node(tempItem,tempPtr,treePtr->LeftPtr);
			if(tranPtr==NULL)
				throw TTTException("TTTException :allocate memory failed !");
			treePtr->reSet(treePtr->lItem,treePtr->MiddlePtr,treePtr->RightPtr);
			tempItem=tranItem;
			tempPtr=tranPtr;
			if(isRoot(treePtr))
			{
				Node *tempRoot=new Node(tempItem,tempPtr,treePtr);
				if(tempRoot==NULL)
					throw TTTException("TTTException :allocate memory failed !");
				root=tempRoot;
				return true;
			}
			return false;
		}
		else
		{
			treePtr->reSet(tempItem,treePtr->fItem,tempPtr,treePtr->LeftPtr,treePtr->MiddlePtr);
			return true;
		}
	}
	else if(ch=='M')
	{
		if(twoItem(treePtr))
		{
			Node *tranPtr=new Node(treePtr->fItem,treePtr->LeftPtr,tempPtr);
			if(tranPtr==NULL)
				throw TTTException("TTTEexception :allocate memory failed !");
			treePtr->reSet(treePtr->lItem,treePtr->MiddlePtr,treePtr->RightPtr);
			tempPtr=tranPtr;
			if(isRoot(treePtr))
			{
				Node *tempRoot=new Node(tempItem,tempPtr,treePtr);
				if(tempRoot==NULL)
					throw TTTException("TTTException :allocate memory failed !");
				root=tempRoot;
				return true;
			}
			return false;
		}
		else
		{
			treePtr->reSet(treePtr->fItem,tempItem,treePtr->LeftPtr,
					tempPtr,treePtr->MiddlePtr);
			return true;
		}
	}
	else if(ch=='R')
	{
		ItemType tranItem=treePtr->lItem;
		Node *tranPtr=new Node(treePtr->fItem,treePtr->LeftPtr,treePtr->MiddlePtr);
		if(tranPtr==NULL)
			throw TTTException("TTTException :allocate memory failed !");
		treePtr->reSet(tempItem,tempPtr,treePtr->RightPtr);
		tempItem=tranItem;
		tempPtr=tranPtr;
		if(isRoot(treePtr))
		{
			Node *tempRoot=new Node(tempItem,tempPtr,treePtr);
			if(tempRoot==NULL)
				throw TTTException("TTTException :allocate memory failed !");
			root=tempRoot;
			return true;
		}
		return false;

	}
	else
	{
		if(twoItem(treePtr))
		{
			sort(treePtr->fItem,tempItem,treePtr->lItem);
			Node *tranPtr=new Node(treePtr->fItem,NULL,NULL);
			if(tranPtr==NULL)
				throw TTTException("TTTException :allocate memory failed !");
			treePtr->reSet(treePtr->lItem,NULL,NULL);
			tempPtr=tranPtr;
			if(isRoot(treePtr))
			{
				Node *tempRoot=new Node(tempItem,tempPtr,treePtr);
				if(tempRoot==NULL)
					throw TTTException("TTTException :allocate memory failed !");
				root=tempRoot;
				return true;
			}
			return false;
		}
		else
		{
			ItemType tranItem;
			if(treePtr->fItem.getKey()>tempItem.getKey())
			{
				tranItem=treePtr->fItem;
				treePtr->fItem=tempItem;
				tempItem=tranItem;
			}
			treePtr->reSet(treePtr->fItem,tempItem,NULL,NULL,NULL);
			return true;
		}
	}
}

2-3树的简单的测试程序

#include<iostream>
#include<cstdlib>
#include<string>
#include<ctime>
#include"two_three_tree.h"
using namespace std;
void display(ItemType &_item);
int main()
{
	srand(time(0));
	ttTree atree,btree;
	ItemType aitem;
	string thekey,thetel;
 	try{
		for(int i=0;i<20;i++)
		{
			for(int j=0;j<7;j++)
			{
				thekey=thekey+char(rand()%26+'a');
				thetel=thetel+char(rand()%10+'0');
			}
			atree.insert(ItemType(thekey,thetel));
			thekey.clear();
			thetel.clear();
		}
		cout<<"the item in atree :"<<endl;
		atree.traverse(display);
		cout<<"traverse over !"<<endl;
		cout<<"calling operator= function :"<<endl;
		btree=atree;
		cout<<"the item in btree :"<<endl;
		btree.traverse(display);
		cout<<"traverse over !"<<endl;
	}catch(TTTException &e)
	{
		cout<<e.what()<<endl;
	}
	return 0;
}
void display(ItemType &_item)
{
	cout<<"the information :"<<_item.getKey()<<'\t'<<_item.getTel()<<endl;
}

有兴趣的可以自己测试一下。


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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值