剑指offer21-23解题思路及代码(栈的压入、弹出序列 、从上往下打印二叉树 、二叉搜索树的后序遍历序列 )

21栈的压入、弹出序列
这题有个解题思路即仿真弹出序列,先向一个栈里面不断的插入元素,然后对比输出栈开始弹出元素,若弹出的容器中的值和popV栈中的值不同即代表不是弹出序列。
class Solution {
public:
    bool IsPopOrder(vector<int> pushV,vector<int> popV) {
        if(pushV.size()!=popV.size()&&pushV.empty()&&popV.empty())
            return false;
        stack<int> st;
        vector<int> answer;
        for(int i=0,j=0;j<popV.size();){
            while(st.empty()||st.top()!=popV[j]){
                st.push(pushV[i]);
                ++i;
            }
            if(st.top()==popV[j]){
                answer.push_back(st.top());
                st.pop();
                ++j;
            }
        }
        for(int i=0;i<answer.size();i++){
            if(answer[i]!=popV[i])
                return false;
        }
        return true;
    }
};
先编了这个,然后发现只能够通过33%的例子,其主要原因是因为,它只能够通过对的例子,当需要返回false时,由于判断条件时if(st.top()==popV[j])所以当不对的时候j永远不会增加,陷入死循环。。。所以正确判断如下:
class Solution {
public:
    bool IsPopOrder(vector<int> pushV,vector<int> popV) {
        if(pushV.size()!=popV.size()&&pushV.empty()&&popV.empty())
            return false;
        stack<int> st;
        vector<int> answer;
        int j=0;
        for(int i=0;j<popV.size();){
            while(st.empty()||st.top()!=popV[j]){
                st.push(pushV[i]);
                ++i;
            }
            if(st.top()!=popV[j])
                break;
                st.pop();
                ++j;
        }
        if(st.empty()&&j==popV.size())
            return true;
        return false;
    }
};

22 从上往下打印二叉树
通过队列存储节点来达到将各个节点输入到answer容器中的目的,原来想的是通过遍历的方法,然而还是队列从结果到过程感觉都要优越一点。代码如下:
class Solution {
public:
    vector<int> PrintFromTopToBottom(TreeNode* root) {
        vector<int> answer;
        if(!root)
            return answer;
        deque<TreeNode*> que;
        que.push_back(root);
        while(!que.empty()){
            TreeNode* rot=que.front();
            que.pop_front();
            answer.push_back(rot->val);
            if(rot->left)
                que.push_back(rot->left);
            if(rot->right)
                que.push_back(rot->right);
        }
        return answer;
    }
};

23 二叉搜索树的后序遍历序列
该题先需要知道在后序遍历中,根节点的值是最后一个,而在二叉搜索树中,其左子树的值一定小于根值,右子树一定大于根值。所以若在其右子树出现小于根值得情况即不为后序遍历得解。先通过遍历分别出其左子树和右子树,然后递归判断。代码如下:
class Solution {
public:
    bool VerifySquenceOfBST(vector<int> sequence) {
        int length=sequence.size()-1;
        if(sequence.empty())
            return false;
        int i=0;
        int root=sequence[length];
        vector<int> left;
        for(;sequence[i]<root;++i){
            left.push_back(sequence[i]);
        }
        int j=i;
        vector<int> right;
        for(;j<length;++j){
            if(sequence[j]<root)
                return false;
            right.push_back(sequence[j]);
        }
        bool left1=true;
        if(i>0)
            left1=VerifySquenceOfBST(left);
        bool right1=true;
        if(i<length)
            right1=VerifySquenceOfBST(right);
        return left1&&right1;
    }
};

猜你喜欢

转载自blog.csdn.net/u010404530/article/details/80076169
今日推荐