一种树的实现,在Qt界面的一个例子上看到的,把在VC++6.0上实现并写成模板
#include <vector> #include <iostream> #include <stack> #include <queue> #include <string> using namespace std; template<typename T> class TreeItem { public: TreeItem(T data, TreeItem<T> *parent = 0); ~TreeItem(); TreeItem<T> *child(int number); int childCount() const;//孩子的个数 int childNumber() const;//当前节点是第几个孩子 bool insertChildren(int position, T data);//插入孩子 bool insertChildren(int position, TreeItem<T> *p);//重载 TreeItem<T> *parent();//获取父亲 bool removeChildren(int position);//删除一个孩子 TreeItem<T>* rihghtbrother();//获取右兄弟 bool swapchildren(int first, int second);//交换孩子的顺序 T data(); private: T Data; vector<TreeItem<T>*> childItems; TreeItem<T> *parentItem; }; template<typename T> TreeItem<T>::TreeItem(T data, TreeItem<T> *parent) { parentItem = parent; Data = data; } template<typename T> TreeItem<T>::~TreeItem() { for(int i=0; i<childItems.size(); i++) delete childItems[i]; } template<typename T> TreeItem<T>* TreeItem<T>::child(int number) { if(number<0 || number>=childItems.size()) return NULL; return childItems[number]; } template<typename T> int TreeItem<T>::childCount() const { return childItems.size(); } template<typename T> int TreeItem<T>::childNumber() const { if (parentItem) for(int i=0;i<parentItem->childItems.size();i++) if(this == parentItem->childItems[i]) return i; return 0; } template<typename T> bool TreeItem<T>::insertChildren(int position, T data) { if(position<0 || position>childItems.size()) return false; TreeItem<T> *item = new TreeItem<T>(data,this); vector<TreeItem<T>*>::iterator iter = childItems.begin(); childItems.insert(iter+position, item); return true; } template<typename T> bool TreeItem<T>::insertChildren(int position, TreeItem<T> *p) { if(position<0 || position>childItems.size()) return false; vector<TreeItem<T>*>::iterator iter = childItems.begin(); childItems.insert(iter+position, p); return true; } template<typename T> TreeItem<T>* TreeItem<T>::parent() { return parentItem; } template<typename T> bool TreeItem<T>::removeChildren(int position) { if (position < 0 || position>=childItems.size()) return false; delete childItems[position]; return true; } template<typename T> TreeItem<T>* TreeItem<T>::rihghtbrother() { TreeItem *p = this->parentItem; if(p && p->childCount()>(this->childNumber()+1)) return p->child(childNumber()+1); return NULL; } template<typename T> bool TreeItem<T>::swapchildren(int first, int second) { if(first==second)return true; int count = childItems.size(); if (first < 0 || first >= count) return false; if (second < 0 || second >= count) return false; TreeItem<T> *p = childItems[first]; childItems[first] = childItems[second]; childItems[second] = p; } template<typename T> T TreeItem<T>::data() { return Data; } /////////////////////////////////////////////////////////////////// /// \brief The Tree class template<typename T> class Tree { public: Tree(TreeItem<T> *root){rootItem=root;} void Previsit(); void Postvisit();//和前序遍历一样,只是"操作"在出栈时进行 void Levelvisit(); ////operations else........... private: TreeItem<T> *rootItem; }; template<typename T> void Tree<T>::Previsit() { stack<TreeItem<T>*> st; TreeItem<T>* q= rootItem; st.push(q); cout<<q->data()<<" "; while(q->childCount()) { q = q->child(0); st.push(q); cout<<q->data()<<" "; } while(!st.empty()) { q = st.top(); st.pop(); // cout<<q->data()<<" "; if(q->rihghtbrother()) { q = q->rihghtbrother(); st.push(q); cout<<q->data()<<" "; while(q->childCount()) { q = q->child(0); st.push(q); cout<<q->data()<<" "; } } } } template<typename T> void Tree<T>::Levelvisit() { queue<TreeItem<T>*> que; TreeItem<T>* q= rootItem; que.push(q); while(!que.empty()) { q = que.front(); que.pop(); cout<<q->data()<<" "; for(int i=0; i<q->childCount(); i++) que.push(q->child(i)); } } int main() { TreeItem<string> *rootItem = new TreeItem<string>("root",NULL);// 实际使用时用第二个重载的insertChildren更实用。。。。。。。。。。。。 rootItem->insertChildren(0,"A"); rootItem->insertChildren(1,"B"); rootItem->insertChildren(2,"C"); rootItem->insertChildren(3,"D"); rootItem->child(0)->insertChildren(0,"A1"); rootItem->child(0)->insertChildren(1,"A2"); rootItem->child(1)->insertChildren(0,"B1"); rootItem->child(1)->insertChildren(1,"B2"); rootItem->child(1)->insertChildren(2,"B3"); rootItem->child(3)->insertChildren(0,"D1"); // rootItem->swapchildren(0,2); Tree<string> tree(rootItem); // tree.Previsit(); tree.Levelvisit(); return 0; }
在TreeItem中应该用链表来管理孩子的指针会好点,代码编译通过,但不知道还有没有Bug。共同学习
时间: 2024-10-31 14:02:57