二叉树遍历 及 创建

每次老师讲这个二叉树都是先讲的遍历再将的创建,因为你不会遍历就不会创建二叉树。

因为是二叉树所以这个树的每个结点都要有  1个数据域,2个指针域

所以我们需要定义一个结构体

typedef struct BiTNode
{
    char data;
    struct BiTNode *lchild;//左孩子
    struct BiTNode *rchild;//右孩子
}BiTNode, *BiTree;

1、前序遍历

基本思想:根结点 ---> 左子树 ---> 右子树     (总的来说就是中左右

前序遍历 :1  2  4  5  7  8  3  6

前序遍历递归写法

void PerOrderTraverse(BiTree T)//递归前序遍历
{
    if(T != NULL)    //跳出递归条件
    {
        cout << T->data <<" ";
        PerOrderTraverse(T->lchild);
        PerOrderTraverse(T->rchild);
    }
}

2、中序遍历

中序遍历:左子树---> 根结点 ---> 右子树  (左中右)

中序遍历结果: 4  2  7  8  5  1  3  6

中序遍历递归写法

void InOrderTraverse(BiTree T)//递归中序遍历
{
    if( T != NULL )
    {
        InOrderTraverse(T->lchild);
        cout << p->data << " ";
        InOrderTraverse(T->rchild);
    }
}

3、后序遍历

后序遍历:左子树 ---> 右子树 ---> 根结点  (左右中)

后序遍历结果:4  8  7  5  2  6  3  1

后续遍历递归写法

void PostOrderTraverse(BiTree T)//递归后序遍历
{
    if(T != NULL)	//跳出递归条件 
    {
        PostOrderTraverse(T->lchild);
        PostOrderTraverse(T->rchild);
        cout << T->data << " ";
    }
}

4、层序遍历

遍历思想就是一层一层往下,然后从左往右(这个要看你先压入队列的是左孩子还是右孩子了)

层序遍历: A B E C D F

void LevelOrderTraverse(BiTree T)//层序遍历 
{
	queue<BiTree> Q;			//创建一个队列
    Q.push(T);					//先压入第一个节点
    while(!Q.empty())			// 队列不为空
    {
        T = Q.front();		 	//T指向队首元素
        cout << T->data << " "; //输出队首元素
        Q.pop();				//弹出队首元素 
       	if(T->lchild)			//T的左孩子不为空(有左子树) 
           Q.push(T->lchild);	//T的左孩子压入队列 
       	if(T->rchild)			//T的右孩子不为空(有右子树) 
           Q.push(T->rchild);	//T的右孩子压入队列 
    }
}

5、创建二叉

用#代替空区域,因为一个节点有2个指针域

void CreatBiTree(BiTree &T)//前序输入创建二叉树
{
    char ch;
    cin >> ch;
    if(ch == '#')
        T = NULL;
    else
    {
        T = new BiTNode;
        T->data = ch;
        CreatBiTree(T->lchild);
        CreatBiTree(T->rchild);
    }
}

6、求树深

int GetDepth(BiTree T)//求树深度
{
    int LD = 0,RD = 0;
    if(T == NULL)
        return 0;
    else
    {
        LD = GetDepth(T->lchild);
        RD = GetDepth(T->rchild);
        if(LD >= RD)
        return LD + 1;
        else
        return RD + 1;
    }
}

7、求叶子节点,及个数


void CountLeaf(BiTree root, int &number)//叶子节点 
{

    if(root != NULL)
    {
        if(!root->lchild && !root->rchild)
        {
            number++;
            cout << root->data << " ";
        }
        if(root->lchild)
            CountLeaf(root->lchild, number);
        if(root->rchild)
            CountLeaf(root->rchild, number);
    }
}

总结

细心的我们发现 诶呀??? 怎么这三种写法这么相似阿??好像只有一点不一样,这就是二叉树递归写法的妙处所在。

并且我们人为的去进行脑力遍历二叉树时跟这个递归的思路是一样的。

不会遍历???  不要紧 找几棵树练一下就会了。

大家练习一下,写出这棵树的  前  中  后  遍历结果。

前: A  B  D  Y  E  C  F  X  Z

中: D  Y  B  E  A  F  C  Z  X 

后: Y  D  E  B  F  Z  X  C  A

层: A  B  C  D  E  F  X  Y  Z

我认为只有我们自己发现的规律才是我们自己的   所以多找点题练练,你就能发现规律了。

猜你喜欢

转载自blog.csdn.net/Harington/article/details/83896290