双标记位先根次序构建树
来源:互联网 发布:c语言中rand函数 编辑:程序博客网 时间:2024/05/18 13:29
利用带双标记的先根次序信息,来构造左孩子右兄弟方式表示的树。
#include <iostream>#include <stack>//#include "TreeNode.h"using namespace std;const int N = 10; //结点数量template <class T> class Tree; //声明树类// 带“双标记”的先根次序 结点类template <class T>class DualTagTreeNode {public: T info; //树结点信息 int ltag; //左标记 int rtag; //右标记 DualTagTreeNode() {}; //构造函数 virtual ~DualTagTreeNode() {}; //析构函数};// 树结点类的ADTtemplate <class T>class TreeNode {friend class Tree<T>;private: T m_Value; //树结点的值 TreeNode<T>* pChild; //左子结点 TreeNode<T>* pSibling; //右兄弟结点public: TreeNode() {}; TreeNode(const T &value) {m_Value = value; pChild = NULL; pSibling = NULL;}; T Value() {return m_Value;}; // 获得结点的信息 TreeNode<T> *LeftMostChild() {return pChild;}; // 返回第一个左子树 TreeNode<T> *RightSibling() {return pSibling;}; // 返回第一个右兄弟 void setValue(T &value) {m_Value = value;}; //设置结点的值 void setChild(TreeNode<T> *pointer) {pChild = pointer;}; //设置左孩子 void setSibling(TreeNode<T> *pointer) {pSibling = pointer;}; //设置右孩子};// 树类ADT,只写出了相关的变量及函数template <class T>class Tree {private: TreeNode<T> *root; TreeNode<T> *getParent(TreeNode<T> *root, TreeNode<T> *current);public: Tree() {root = NULL;}; Tree(DualTagTreeNode<T> *nodeArray, int count); //带双标记先根次序构造算法 TreeNode<T> *getRoot() {return root;}; //返回树中的根结点 void Visit(T Value) {cout << Value;}; //访问 void RootFirstTraverse(TreeNode<T> *root); //先根次序周游,作为测试使用};// 函数功能:带双标记先根次序构造算法template <class T>Tree<T>::Tree(DualTagTreeNode<T>* nodeArray, int count) {//利用带双标记位的先根次序表示的树构造左孩子右兄弟方式表示的树 //使用STL中的stack using std::stack; stack<TreeNode<T>* > aStack; //准备建立根结点 TreeNode<T>* pointer = new TreeNode<T>; root=pointer; //处理一个结点 for(int i = 0;i < count-1;i++) { pointer->setValue(nodeArray[i].info); if(nodeArray[i].rtag == 0) aStack.push(pointer); //将结点压栈 else pointer->setSibling(NULL); //右兄弟设为空 TreeNode<T>* temppointer = new TreeNode<T>; if(nodeArray[i].ltag == 0) pointer->setChild(temppointer); else { pointer->setChild(NULL); //左孩子设为空 pointer = aStack.top(); aStack.pop(); pointer->setSibling(temppointer); } pointer = temppointer; } //处理最后一个结点 pointer->setValue(nodeArray[count-1].info); pointer->setChild(NULL); pointer->setSibling(NULL);}// 函数功能:先根深度遍历template <class T>void Tree<T>::RootFirstTraverse(TreeNode<T> *root) { while (root != NULL) { Visit(root->Value()); RootFirstTraverse(root->LeftMostChild()); root = root->RightSibling(); }}// 函数功能:显示森林结构.图6.5(a)所示的森林void DisplayTree() { cout << " A G \n"; cout << " / | \\ / \\ \n"; cout << " B C D H I \n"; cout << " / \\ | \n"; cout << " E F J \n"; cout << endl; cout << "rtag = 0 , there is a right sibling" << endl; cout << "rtag = 1 , there isn't a right sibling" << endl; cout << "ltag = 0 , there is a left child" << endl; cout << "ltag = 1 , there isn't a left child" << endl << endl;}// 函数功能:显示森林结构的带双标记先根次序表示void DisplayNode(char *Info, int *nRtag, int *nLtag) { if (Info != NULL) { cout << "info "; for (int i = 0; i < N; i ++) cout << Info[i] << " "; cout << endl; } if (nRtag != NULL) { cout << "rtag "; for (int i = 0; i < N; i ++) cout << nRtag[i] << " "; cout << endl; } if (nLtag != NULL) { cout << "ltag "; for (int i = 0; i < N; i ++) cout << nLtag[i] << " "; cout << endl; }}// 函数功能:周游树,在这里只列举一种(先根次序)void Traverse(Tree<char> *tree) { cout << "FirstRoot traverse: "; tree->RootFirstTraverse(tree->getRoot()); // 先根深度优先周游 cout << endl;}int main() { // 显示森林结构 DisplayTree(); // 带双标记先根次序构造算法,图6.5(a)所示的森林的带双标记位的先根次序表示为例 char strInfo[N] = {'A', 'B', 'C', 'E', 'F', 'D', 'G', 'H', 'J', 'I'}; int nRtag[N] = {0, 0, 0, 0, 1, 1, 1, 0, 1, 1}; int nLtag[N] = {0, 1, 0, 1, 1, 1, 0, 0, 1, 1}; cout << "Dualtag_FirstRoot create tree." << endl; //打印带双标记位的先根次序表示 DisplayNode(strInfo, nRtag, nLtag); DualTagTreeNode<char> *nodeArray = new DualTagTreeNode<char>[N]; for (int i = 0; i < N; i ++) { //设置带双标记位的先根次序结点类 nodeArray[i].info = strInfo[i]; nodeArray[i].rtag = nRtag[i]; nodeArray[i].ltag = nLtag[i]; } Tree<char> aTree(nodeArray, N); // 建树 Traverse(&aTree); // 周游树,结果:ABCEFDGHJI return 0;}
0 0
- 双标记位先根次序构建树
- 双标记层次次序构建树
- 线段树单标记,双标记
- 二叉树层次序遍历
- 使用整洁的HTML标记构建页面
- 使用整洁的HTML标记构建页面
- HDU 4902 双标记线段树
- bzoj 1798 线段树 双lazy标记
- HDU3397 线段树 区间合并 双标记
- hdu 3397 线段树双标记
- hdu 3397 线段树双标记
- 线段树区间修改之双标记 【lazy两重标记并且分类讨论】
- JSP:include 用于构建动态网站的简单 JSP 标记
- 为自己的ASP网站系统构建一套标记语言
- html单双标记
- EZW算法的过程详解和Matlab代码(1)构建扫描次序表(修正小波树结构)
- “次序”很重要
- 初始化次序
- 复习————强制类型的转换
- wikioi-天梯-普及一等-区间dp-1048:石子归并
- 玩转Java对象和XML相互转换
- 补遗篇之static
- Html:小技巧:自动提交表单的实现方法
- 双标记位先根次序构建树
- Android 点击AlertDialog中的EditText显示输入框
- 原子操作 Interlocked系列函数
- 简单使用set/unordered_set (备忘)
- JAVA 正则表达式、汉字正则、 java正则代码
- struts2 生成并下载 excel 文件 (jxl)
- .NET中文乱码的解决方法分享
- poj2418
- 线程锁EnterCriticalSection和LeaveCriticalSection的用法