树的子结构

#include <stdio.h>
#include <stdlib.h>
/* 树的子结构 */
/*先在A树中找到和B树根节点相同的节点
  接着,在依次判断*/

typedef struct TreeNode{
    int data;
    struct TreeNode *LeftNode;
    struct TreeNode *RightNode;
}TreeNode;

/*往树中插入数据(常规方法)    创建搜索树   并返回根节点*/
/*涉及到头结点的变换,用**  */
TreeNode* insertNode(TreeNode **Node,int data)
{
    TreeNode *TepNode = *Node;
    if((*Node)==NULL)   /*空树,创建树*/
    {
        (*Node) = (TreeNode *)malloc(sizeof(TreeNode));
        (*Node)->data = data;
        (*Node)->LeftNode = (*Node)->RightNode = NULL;
    }
    else    /*重点判断放在左子树还是右子树*/
    {
        while(1)
        {
            if(data > TepNode->data)  /*放右子树*/
            {
                if(TepNode->RightNode == NULL)
                {
                    TepNode->RightNode = (TreeNode *)malloc(sizeof(TreeNode));
                    TepNode->RightNode->data = data;
                    TepNode->RightNode->LeftNode = TepNode->RightNode->RightNode = NULL;
                    break;
                }
                  TepNode = TepNode->RightNode;
            }
            else
            {
                if(TepNode->LeftNode == NULL)
                {
                    TepNode->LeftNode = (TreeNode*)malloc(sizeof(TreeNode));
                    TepNode->LeftNode->data = data;
                    TepNode->LeftNode->LeftNode = TepNode->LeftNode->RightNode = NULL;
                    break;
                }
                TepNode = TepNode->LeftNode;
            }
        }
    }
    return (*Node);
}
/*往树中插入数据(递归方法)    创建搜索树   并返回根节点*/
TreeNode * insertNode1(TreeNode **Node, int data)
{
    TreeNode *TepNode = *Node;
    if((*Node)==NULL)   /*空树,创建树*/
    {
        (*Node) = (TreeNode *)malloc(sizeof(TreeNode));
        (*Node)->data = data;
        (*Node)->LeftNode = (*Node)->RightNode = NULL;
    }
    else
    {
        if(data > TepNode->data)
            insertNode1(&(*Node)->RightNode,data);
        else
            insertNode1(&(*Node)->LeftNode,data);
    }
    return (*Node);
}

/*中序遍历一棵树*/
void Mid_Travel(TreeNode *head)
{
    if(head)
    {
        Mid_Travel(head->LeftNode);
        printf("%d   ",head->data);
        Mid_Travel(head->RightNode);
    }
}

/*判断根节点的 左右节点 是否相同*/
/*
参数1:A树的根节点
参数2:B树的根节点
返回值:  1 :是
        0 : 不是*/
int FindChi(TreeNode *root1,TreeNode *root2)
{
 /* 要养成一个习惯,对任何一个树节点进行访问时,一定要提前检测该节点是否为空*/
    if(root2 == NULL)   /*终止条件1*/
        return 1;
    else if(root1 == NULL)   /*终止条件2*/
        return 0;
    else if(root1->data != root2->data)  /*终止条件3*/
        return 0;
    /*第一次执行FindChi(root1->LeftNode,root2->LeftNode),如果root1->LeftNode==root2->LeftNode,会再次执行
    FindChi(root1->LeftNode,root2->LeftNode);
    这次执行完以后,A,B树的左子树都会往下一层...中途如果有不一样,就会返回0,终止;
    如果最后能执行到root2 == NULL,说明他们的左子树一直相等
    同理,在判断他们的右子树*/
    return(FindChi(root1->LeftNode,root2->LeftNode) && FindChi(root1->RightNode,root2->RightNode));
}

/*找根节点相同的节点   找到以后,调用FindChi,判断他们的左右节点是否一样*/
int hassubtree(TreeNode *root1, TreeNode *root2)
{
    int result = 0;
    if(root1 != NULL && root2 != NULL)
    {
        if(root1 ->data == root2->data)
        /*如果返回1,说明根节点以及根节点的左右子树都一样,下面两个不会执行,退出*/
            result = FindChi(root1,root2);
        if(!result)
 /*如果上面是0,说明跟节点不一样;开始遍历A树左面的每个节点,找和B的根节点一样的节点。找到以后,调用FindChi*/
            result = hassubtree(root1->LeftNode, root2);
        if(!result)
            /*同上*/
            result = hassubtree(root1->RightNode, root2);
    }
    return result;
}


int main(void)
{
    TreeNode *Node = NULL;
    TreeNode *NodeB = NULL;
    TreeNode *root1;
    TreeNode *root2;
    int data[]={10,2,8,7,5,3,4};
    int i = 0,num =7;

    for(i=0;i<num;i++)
    {
        /*往树中插入数据(常规方法)    创建搜索树*/
      root1 = insertNode(&Node,data[i]);
        /*往树中插入数据(递归方法)    创建搜索树*/
      //  root = insertNode1(&Node,data[i]);
    }

    for(i=4;i<7;i++)
    {
        /*往树中插入数据(常规方法)    创建搜索树*/
      root2 = insertNode(&NodeB,data[i]);
    }
    printf("IS =%d   ",hassubtree(root1, root2));

    return 0;
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

One Piece&

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值