关闭

线索化二叉树C++

标签: 线索化二叉树数据结构C++
537人阅读 评论(0) 收藏 举报
分类:

线索化二叉树
1.创建二叉树
2.先序递归遍历输出二叉树
3.线索化二叉树
4.输出线索化二叉树

/*
线索化二叉树
	1.创建二叉树
	2.先序递归遍历输出二叉树
	3.线索化二叉树
	4.输出线索化二叉树
*/

#include<iostream>
#include<stack>
#include<string>
#include<fstream>
using namespace std;

class Node
{
public:
	char data;
	bool ltag, rtag;
	class Node *lchild, *rchild;
};

class Thread_Binary_Tree
{
public:

	Thread_Binary_Tree(){}
	~Thread_Binary_Tree(){}

	//创建二叉树
	void create_binary_tree(string filename)
	{
		ifstream readfile;
		string str;
		readfile.open(filename,ios::in);
		getline(readfile,str);
		cout << str << endl;
		Create_Tree(str);//创建二叉树
		readfile.close();
	}


	//先序递归输出二叉树
	void displayFront_tree()
	{
		cout << "先序递归输出" << endl;
		output_fro(t);//递归先序输出
		cout << endl;
	}

	//创建线索化二叉树
	void create_thread_Btree()
	{
		thread_root = CreateThread(t);
	}
	
	//输出线索化二叉树
	void display_thread_Btree()
	{
		cout << "中序线索化输出" << endl;
		output_thread(thread_root);
		cout << endl;
		cout << "中序线索化新根节点左右标记" << endl;
		cout << thread_root->ltag << "," << thread_root->rtag << endl;//输出中序线索化新根节点左右标记
	}
private:
	Node *t;
	Node *pre;
	Node *thread_root;
	//创建二叉树
	void Create_Tree(string str)
	{
		stack<Node *> m_stack;
		int k;
		Node *p;
		while (!str.empty())
		{
			if (str[0] == '(')
			{
				m_stack.push(p);
				k = 1;
			}
			else if (str[0] == ')')//必须使用if-else if
			{
				m_stack.pop();
			}
			else if (str[0] == ',')
			{
				k = 2;
			}
			else
			{
				p = (Node *)malloc(sizeof(Node));
				p->lchild = p->rchild = NULL;
				p->data = str[0];//将串首字符赋给data
				if (t == NULL)//处理根节点
				{
					t = p;
				}
				else
				{
					if (k == 1)
					{
						m_stack.top()->lchild = p;//左子树
					}
					if (k == 2)
					{
						m_stack.top()->rchild = p;//右子树
					}
				}
			}
			str.assign(str.substr(1, str.length() - 1));//构建新串,将串首字符除去
		}
	}

	//先序递归输出二叉树
	void output_fro(Node *t)
	{
		if (t == NULL)
		{
			return;
		}
		else
		{
			cout << t->data;
			if (t->lchild != NULL || t->rchild != NULL)
			{
				cout << "(";
				output_fro(t->lchild);//先序递归左子树
				if (t->rchild != NULL)
				{
					cout << ",";
				}
				output_fro(t->rchild);//先序递归右子树
				cout << ")";
			}
		}
	}

	//中序线索化二叉树
	void Thread(Node *&p)
	{
		if (p != NULL)
		{
			Thread(p->lchild);//向左直走
			if (p->lchild == NULL)//遍历到中序遍历输出的首节点且无左子节点
			{
				p->lchild = pre;//指向前驱节点
				p->ltag = true;
			}
			else//存在左子节点
			{
				p->ltag = false;
			}
			if (pre->rchild == NULL)//若右节点无子节点,则右指针指向后继节点
			{
				pre->rchild = p;
				pre->rtag = true;
			}
			else//存在右子节点
			{
				pre->rtag = false;
			}
			pre = p;//更新
			Thread(p->rchild);//处理右子树
		}
	}

	//创建线索化二叉树
	Node *CreateThread(Node *t)
	{
		Node *root;
		root = (Node *)malloc(sizeof(Node));//生成附加根节点
		root->ltag = false; root->rtag = true;
		root->rchild = t;
		if (t == NULL)//空树线索化
		{
			root->lchild = root;
		}
		else
		{
			root->lchild = t;
			pre = root;//pre初始化
			Thread(t);//线索化二叉树
			pre->rchild = root;//中序末节点
			pre->rtag = true;
			root->rchild = pre;//新生成根节点
			root->rtag = 1;//新生成根节点rtag=1;
		}
		return root;
	}

	//遍历输出线索化二叉树
	void output_thread(Node *t)
	{
		Node *p = t->lchild;
		while (p != t)
		{
			while (!p->ltag)
			{
				p = p->lchild;
			}
			cout << p->data << ends;
			
			while (p->rtag&&p->rchild != t)
			{
				p = p->rchild;
				cout << p->data << ends;
			}
			p = p->rchild;
		}
		
	}
};

int main()
{
	Thread_Binary_Tree m_tree;
	m_tree.create_binary_tree("data");//创建普通二叉树
	m_tree.displayFront_tree();//先序递归遍历输出
	m_tree.create_thread_Btree();//创建中序线索化二叉树
	m_tree.display_thread_Btree();//输出中序线索化二叉树
	return 0;
}
测试运行



0
0

查看评论
* 以上用户言论只代表其个人观点,不代表CSDN网站的观点或立场
    个人资料
    • 访问:93875次
    • 积分:1572
    • 等级:
    • 排名:千里之外
    • 原创:71篇
    • 转载:0篇
    • 译文:0篇
    • 评论:15条
    博客专栏
    最新评论