二叉查找树的典型面试题目汇总

#include <iostream>
#include <vector>
#include <stack>
#include <queue>

using namespace std;

typedef struct BSTreeNode{
    int num;
    BSTreeNode* leftChild;
    BSTreeNode* rightChild;

}*TreeNode;


TreeNode search(TreeNode root,int key)
{
    if (!root)
    {
        return NULL;
    }
    if (key==root->num)
    {
        return root;
    }
    if (key<root->num)
    {
        search(root->leftChild,key);
    }
    return search(root->rightChild,key);
}
//利用指针的指针进行改变树结构。
void insert_node(TreeNode* node,int num)
{
    if ((*node)==NULL)
    {
        (*node)=new BSTreeNode;
        (*node)->num=num;
        (*node)->leftChild=(*node)->rightChild=NULL;
    }
    else
    {
        if (num<(*node)->num)
        {
            insert_node(&(*node)->leftChild,num);
        }
        else if (num>(*node)->num)
        {
            insert_node(&(*node)->rightChild,num);
        }
        else
            cout<<" insert duplicated elements \n";
    }
}
//利用引用去改变整个树结构。
void insert_node2(TreeNode &root,int num)
{
    if (root==NULL)
    {
        root=new BSTreeNode;
        root->num=num;
        root->leftChild=root->rightChild=NULL;
    }
    else
    {
        if (num<root->num)
        {
            insert_node2(root->leftChild,num);
        }
        else if (num>root->num)
        {
            insert_node2(root->rightChild,num);
        }
        else
            cout<<" insert duplicated elements \n";
    }
}
//中序遍历输出树结果。
void inorder(TreeNode root)
{
    if (root!=NULL)
    {
        inorder(root->leftChild);
        cout<<root->num<<" ";
        inorder(root->rightChild);
    }
}
//非递归的中序遍历。
void inorderTraverse(TreeNode root)
{
    stack<TreeNode>sta;
    TreeNode p=root;
    while (p||sta.size())
    {
        if (p)
        {
            sta.push(p);
            p=p->leftChild;
        }
        else
        {
            p=sta.top();
            cout<<p->num<<" ";
            sta.pop();
            p=p->rightChild;
        }
    }
}
/*
题目:输入一个整数和棵二元树。
从树的根结点开始往下访问一直到叶所经过有形成条路径。打印出和与输入整数相等的所有路径。
*/
void findPath(TreeNode root,vector<int>&path,int current_sum,int expected_sum)
{
    //这个路径必须包括根节点,而且必须是连接的的线路。
    if (root==NULL||current_sum>expected_sum)//剪枝条件
    {
        return;
    }
    current_sum+=root->num;
    //path 存下数字路径
    path.push_back(root->num);
    bool is_leaf=(!root->leftChild)&&(!root->rightChild);
    if (is_leaf&&(expected_sum==current_sum))
    {
        //符合条件输出该情况树节点。
        vector<int>::iterator it;
        for (it=path.begin();it!=path.end();it++)
        {
            cout<<*it<<" ";
        }
        cout<<endl;
    }
    //类似于全排列算法的实现。先加入某个节点递归,然后在删除递归。
    if (root->leftChild)
    {
        findPath(root->leftChild,path,current_sum,expected_sum);
    }
    if (root->rightChild)
    {
        findPath(root->rightChild,path,current_sum,expected_sum);
    }
    current_sum-=root->num;
    path.pop_back();
}
//输入一颗二元查找树,将该转换为它的镜像即在转换后的二元查找树中,左子结点都大于右。递归方法简单实现
TreeNode traverseTree(TreeNode& root)
{
    if (root)
    {
        //递归逻辑一定清楚!!
        TreeNode left=root->leftChild;
        TreeNode right=root->rightChild;
        root->leftChild=traverseTree(right);
        root->rightChild=traverseTree(left);
    }
    return root;
}
/*
使用循环方式实现镜像的转换。
解法一:用递归。假设当前结点为root,只需交换该结点的左右子女,然后分别递归求解左子树和右子树即可。
解法二:用循环,需要一个辅助栈完成,每次取栈顶元素交换左右子女,然后将左右子女分别压入辅助栈,当栈中元素为空时,结束循环。
其实不论是递归也好,循环也好,都是利用栈的特性完成。
*/

TreeNode traverseTreeType2(TreeNode &root)
{
    if (root)
    {
        stack<TreeNode>sta;
        sta.push(root);
        while (sta.size())
        {
            TreeNode pNode=sta.top();
            TreeNode leftChild=pNode->leftChild;
            TreeNode rightChild=pNode->rightChild;
            sta.pop();
            if (leftChild)
            {
                sta.push(leftChild);
            }
            if (rightChild)
            {
                sta.push(rightChild);
            }
            pNode->leftChild=rightChild;
            pNode->rightChild=leftChild;
        }
    }
    return root;
}
//求树的深度递归实现。
int deepth(TreeNode root)
{
    int leftDeep=0,RightDeep=0;
    if (root==NULL)
    {
        return 0;
    }
    RightDeep= deepth(root->rightChild)+1;
    leftDeep=deepth(root->leftChild)+1;	
    return leftDeep>RightDeep? leftDeep:RightDeep;
}
/*
层次遍历树过程
创建一个队列q;
将根放入队列;
while(队列非空)
{
从队列取出一个元素并访问;
如果该元素有左子树就将它放入队列;
如果该元素有右子树就将它放入队列;
}
*/
void levelTravese(TreeNode root)
{
    queue<TreeNode>que;
    que.push(root);
    while (que.size())
    {
        TreeNode pNode=que.front();
        que.pop();
        cout<<pNode->num<<" ";
        if (pNode->leftChild)
        {
            que.push(pNode->leftChild);
        }
        if (pNode->rightChild)
        {
            que.push(pNode->rightChild);
        }
    }
}

int main()
{
    int a[]={10,5,12,4,7,6,11};
    TreeNode root=NULL;
    for (int i=0;i<7;i++)
    {
        //insert_node(&root,a[i]);
        insert_node2(root,a[i]);
    }
    cout<<"insert ending 中序遍历输出"<<endl;
    //inorder(root);
    inorderTraverse(root);
    cout<<endl;
    levelTravese(root);
    cout<<endl;
    vector<int>path;
    int current_sum=0;
    int expected_sum=28;
    findPath(root,path,current_sum,expected_sum);
    //traverseTree(root);
    traverseTreeType2(root);
    inorder(root);
    return 0;
}

    原文作者:二叉查找树
    原文地址: https://blog.csdn.net/huruzun/article/details/21799441
    本文转自网络文章,转载此文章仅为分享知识,如有侵权,请联系博主进行删除。
点赞