二叉树的一些笔试面试常见题目

来源:互联网 发布:mac可以玩守望先锋吗 编辑:程序博客网 时间:2024/05/22 11:50
//树的一些常见编程题目#include<iostream>    #include<queue>    #include<stack>    using namespace std;        //二叉树结点的描述    typedef struct BiTNode  {        char data;        struct BiTNode *lchild, *rchild;      //左右孩子    }BiTNode,*BiTree;        //按先序遍历创建二叉树    //BiTree *CreateBiTree()     //返回结点指针类型    //void CreateBiTree(BiTree &root)      //引用类型的参数    void CreateBiTree(BiTNode **root)    //二级指针作为函数参数    {        char ch; //要插入的数据        scanf("\n%c", &ch);      //cin>>ch;        if(ch=='#')          *root = NULL;      else      {          *root = (BiTNode *)malloc(sizeof(BiTNode));          (*root)->data = ch;          printf("请输入%c的左孩子:",ch);          CreateBiTree(&((*root)->lchild));          printf("请输入%c的右孩子:",ch);          CreateBiTree(&((*root)->rchild));      }  }      //前序遍历的算法程序    void PreOrder(BiTNode *root)  {        if(root==NULL)            return ;        printf("%c ", root->data); //输出数据        PreOrder(root->lchild); //递归调用,前序遍历左子树        PreOrder(root->rchild); //递归调用,前序遍历右子树    }        //中序遍历的算法程序    void InOrder(BiTNode *root)    {        if(root==NULL)          return ;      InOrder(root->lchild); //递归调用,前序遍历左子树        printf("%c ", root->data); //输出数据        InOrder(root->rchild); //递归调用,前序遍历右子树    }        //后序遍历的算法程序    void PostOrder(BiTNode *root)  {      if(root==NULL)          return ;      PostOrder(root->lchild);      //递归调用,前序遍历左子树        PostOrder(root->rchild);      //递归调用,前序遍历右子树        printf("%c ", root->data);    //输出数据      }        /*  二叉树的非递归前序遍历,前序遍历思想:先让根进栈,只要栈不为空,就可以做弹出操作,  每次弹出一个结点,记得把它的左右结点都进栈,记得右子树先进栈,这样可以保证右子树在栈中总处于左子树的下面。  */ #if 1void PreOrder_Nonrecursive(BiTree T)     //先序遍历的非递归      {        if(!T)              return ;                stack<BiTree> s;        s.push(T);            while(!s.empty())        {            BiTree temp = s.top();            cout<<temp->data<<" ";            s.pop();            if(temp->rchild)                s.push(temp->rchild);            if(temp->lchild)                s.push(temp->lchild);        }    }      #endif/*  二叉树的非递归中序遍历*/void InOrder_Nonrecursive1(BiTree T){if(T == NULL)return;stack<BiTree> s;BiTree curr = T;while(curr != NULL){s.push(curr);curr = curr->lchild;}while(!s.empty()){curr = s.top();s.pop();cout<<curr->data<<" ";if(curr->rchild){curr = curr->rchild;while(curr != NULL){s.push(curr);curr = curr->lchild;}}}}void PostOrder_Nonrecursive1(BiTree T)  // 后序遍历的非递归      {      if(T == NULL)return;    stack<BiTree> s;          BiTree curr = T ;           // 指向当前要检查的节点        BiTree previsited = NULL;    // 指向前一个被访问的节点    while(curr != NULL){s.push(curr);curr = curr->lchild;}while(!s.empty()){curr = s.top();//如果右子树为空或者已经被访问过,则输出当前结点if(curr->rchild == NULL || curr->rchild == previsited){cout<<curr->data<<" ";previsited = curr;s.pop();} else if(curr->lchild == previsited) //如果左子树已经被访问,则访问右子树{curr = curr->rchild;while(curr != NULL){s.push(curr);curr = curr->lchild;}}}}         void PostOrder_Nonrecursive(BiTree T)  // 后序遍历的非递归     双栈法    {          stack<BiTree> s1 , s2;          BiTree curr ;           // 指向当前要检查的节点        s1.push(T);      while(!s1.empty())  // 栈空时结束          {            curr = s1.top();            s1.pop();            s2.push(curr);            if(curr->lchild)                s1.push(curr->lchild);            if(curr->rchild)                s1.push(curr->rchild);        }        while(!s2.empty())        {            printf("%c ", s2.top()->data);            s2.pop();        }    }      int visit(BiTree T)    {        if(T)        {            printf("%c ",T->data);            return 1;        }        else            return 0;    }        // 使用递归求二叉树的深度int getDepth(BiTree T){if(T == NULL)return 0;int d1 = getDepth(T->lchild);int d2 = getDepth(T->rchild);return (d1 > d2 ? d1 : d2) + 1;}// 使用非递归算法求二叉树的深度,根据层次遍历来求解#define MARK ((BiTree) -1)int visit2(BiTree T,int &depth){ if(T == NULL)return -1;if(T == MARK)++depth;return 1;}int getDepth_Nonrecursive(BiTree T){if(T == NULL)return 0;queue<BiTree> Q;Q.push(T);Q.push(MARK);int depth = 0;while(!Q.empty()){int flag = 0;BiTree curr = Q.front();Q.pop();visit2(curr,depth);if(curr != MARK && curr->lchild){Q.push(curr->lchild);flag = 1;}if(curr != MARK && curr->rchild){Q.push(curr->rchild);flag = 1;}if(flag)Q.push(MARK);}return depth;}//使用递归求出二叉树的结点个数int getNodeCount(BiTree T){if(T == NULL)return 0;return 1 + getNodeCount(T->lchild) + getNodeCount(T->rchild);}//递归判断二叉树是否相等bool cmpTree(BiTree T1,BiTree T2){if(T1 == NULL && T2 == NULL)return true;if(T1 == NULL || T2 == NULL)return false;if(T1 && T2){if(T1->data == T2->data){if(cmpTree(T1->lchild,T2->lchild))return cmpTree(T1->rchild,T2->rchild);else if(cmpTree(T1->lchild,T2->rchild))return cmpTree(T1->rchild,T2->lchild);}}}//使用队列层次遍历二叉树void LeverTraverse(BiTree T) {queue<BiTree> Q;BiTree p = T;if(p != NULL)Q.push(p);while(!Q.empty()){BiTree curr = Q.front();Q.pop();visit(curr);if(curr->lchild){Q.push(curr->lchild);}if(curr->rchild){Q.push(curr->rchild);}}}//如何判断二叉树是否是平衡二叉树void IsBalance(){}//判断B是否是A的子树bool DoesTree1HaveTree2(BiTree T1,BiTree T2){if(T1 == NULL)return false;if(T2 == NULL)return true;if(T1->data != T2->data)return false;if(DoesTree1HaveTree2(T1->lchild,T2->lchild))return DoesTree1HaveTree2(T1->rchild,T2->rchild);elsereturn false;}bool HasSubtree(BiTree T1,BiTree T2){bool result = false;if(T1 != NULL && T2 != NULL){if(T1->data == T2->data)result = DoesTree1HaveTree2(T1,T2);if(!result)result = HasSubtree(T1->lchild,T2);if(!result)result = HasSubtree(T2->rchild,T2);}return result;}#if 0int main(void)    {        BiTNode *root = NULL; //定义一个根结点        int flag=1,k;        printf("                     本程序实现二叉树的基本操作。\n");        printf("可以进行建立二叉树,递归先序、中序、后序遍历,非递归先序、中序遍历及非递归层序遍历等操作。\n");            while(flag)        {            printf("\n");            printf("|--------------------------------------------------------------|\n");            printf("|                    二叉树的基本操作如下:                     |\n");            printf("|                        0.创建二叉树                          |\n");            printf("|                        1.递归先序遍历                        |\n");            printf("|                        2.递归中序遍历                        |\n");            printf("|                        3.递归后序遍历                        |\n");            printf("|                        4.非递归先序遍历                      |\n");            printf("|                        5.非递归中序遍历                      |\n");            printf("|                        6.非递归后序遍历                      |\n");            printf("|                        7.非递归层序遍历                      |\n");            printf("|                        8.二叉树的深度                        |\n");            printf("|                        9.二叉树的结点个数                    |\n");            printf("|                        10.退出程序                            |\n");            printf("|--------------------------------------------------------------|\n");            printf("                        请选择功能:");            scanf("%d",&k);            switch(k)            {            case 0:                printf("请建立二叉树并输入二叉树的根节点:");                CreateBiTree(&root);                break;            case 1:                if(root)                {                    printf("递归先序遍历二叉树的结果为:");                    PreOrder(root);                    printf("\n");                }                else                    printf("          二叉树为空!\n");                break;            case 2:                if(root)                {                    printf("递归中序遍历二叉树的结果为:");                    InOrder(root);                    printf("\n");                }                else                    printf("          二叉树为空!\n");                break;            case 3:                if(root)                {                    printf("递归后序遍历二叉树的结果为:");                    PostOrder(root);                    printf("\n");                }                else                    printf("          二叉树为空!\n");                break;            case 4:                if(root)                {                    printf("非递归先序遍历二叉树:");                    PreOrder_Nonrecursive(root);                    printf("\n");                }                else                    printf("          二叉树为空!\n");                break;            case 5:                if(root)                {                    printf("非递归中序遍历二叉树:");                    //InOrderTraverse1(root);    InOrder_Nonrecursive1(root);                printf("\n");                }                else                    printf("          二叉树为空!\n");                break;            case 6:                if(root)                {                    printf("非递归后序遍历二叉树:");                    PostOrder_Nonrecursive(root);   //PostOrder_Nonrecursive1(root);                printf("\n");                }                else                    printf("          二叉树为空!\n");                break;            case 7:                if(root)                {                    printf("非递归层序遍历二叉树:");                    //LeverTraverse(root);                    LevelOrder(root);                    printf("\n");                }                else                    printf("          二叉树为空!\n");                break;            case 8:                if(root)                    printf("这棵二叉树的深度为:%d\n",depth(root));                else                    printf("          二叉树为空!\n");                break;            case 9:                if(root)                    printf("这棵二叉树的结点个数为:%d\n",CountNode(root));                else                    printf("          二叉树为空!\n");                break;            default:                flag=0;                printf("程序运行结束,按任意键退出!\n");            }        }        system("pause");        return 0;    }#endif//根据前序和中序遍历来构建二叉树int CreateBiTreeWithPreAndIn(char *pPre,char *pIn,int num,BiTNode *T){if(pPre == NULL || pIn == NULL || T == NULL)return -1;if(num == 0)return 0;T->data = pPre[0];int i = 0;for(i = 0;i < num;++i){if(pIn[i] == T->data)break;}if(i == num){printf("--\n");return -2;}if(i > 0) // 有左子树{T->lchild = new BiTNode();CreateBiTreeWithPreAndIn(pPre+1,pIn,i,T->lchild);}if(num - i - 1 > 0) // 有右子树{T->rchild = new BiTNode();CreateBiTreeWithPreAndIn(pPre+i+1,pIn+i+1,num - i - 1,T->rchild);}}//输入一个数组,判断是否是一个二叉搜索树的后序遍历bool IsBiTreePostOrder(int a[],int n){if(a == NULL)return false;if(n == 1)return true;   if(n > 1){int root = a[n-1];int leftLen = 0;for(int i = 0;i < n-1;++i){if(a[i] < root)leftLen = i+1;elsebreak;}for(int i = leftLen + 1;i<n-1;++i){if(a[i] < root)return false;}if(IsBiTreePostOrder(a,leftLen))return IsBiTreePostOrder(a+leftLen,n-leftLen-1);}}//计算出从根节点到叶节点路径和等于expectedSum的路径void printPath(vector<char> &path){for(auto it = path.cbegin();it != path.cend();++it){printf("%d ",*it);}printf("\n");}void FindPath(BiTree T,char expectedSum,char currSum,vector<char> &path){path.push_back(T->data);currSum += T->data;bool isLeaf = (T->lchild == NULL && T->rchild == NULL);if(isLeaf && currSum == expectedSum)printPath(path);if(T->lchild)FindPath(T->lchild,expectedSum,currSum,path);if(T->rchild)FindPath(T->rchild,expectedSum,currSum,path);path.pop_back();}void  FindPath(BiTree T,char expectedSum){if(T == NULL)return ;char currSum = 0 ;vector<char> path;FindPath(T,expectedSum,currSum,path);}

1 0
原创粉丝点击