C#栈与队列力扣详解 初学者必看(题目会更新)

在这里插入图片描述
分析:队列有先进先出的特点,所以我们使用两个栈,st1用来存放元素,st2用来实际返回
(1)假设有元素1和2进入st1,在需要Pop()时,我们将st1中的元素全部弹出放入st2中,此时就是2为栈底,1为栈顶(借用卡哥的图)有一个要点:先判断st2中是否没有元素了,才能将st1中的元素弹出加入到st2中。
在这里插入图片描述
(2)Peek()返回头部节点,和Pop()写法类似,将返回值改为Peek即可,本质没区别

public class MyQueue {
    Stack<int> st1;
    Stack<int> st2;
    public MyQueue() {
        st1 = new Stack<int>();
        st2 = new Stack<int>();
    }
    
    public void Push(int x) {
        st1.Push(x);
    }
    
    public int Pop() {
        if(st2.Count != 0)
        {
           return st2.Pop(); 
        }
        else
        {
            while(st1.Count != 0)
            {
                st2.Push(st1.Pop());
            }
            return st2.Pop();
        }
    }
    
    public int Peek() {
        if(st2.Count != 0)
        {
            return st2.Peek();
        }
        else
        {
            while(st1.Count != 0)
            {
                st2.Push(st1.Pop());
            }
            return st2.Peek();
        }
    }
    
    public bool Empty() {
        return st1.Count == 0 && st2.Count == 0;
    }
}

/**
 * Your MyQueue object will be instantiated and called as such:
 * MyQueue obj = new MyQueue();
 * obj.Push(x);
 * int param_2 = obj.Pop();
 * int param_3 = obj.Peek();
 * bool param_4 = obj.Empty();
 */

在这里插入图片描述
分析:和上个题目类似,也是一个容器用来存放元素,另一个容器用来返回最终值。
(1)设定q1输出元素,q2存放元素,假如q1已有元素1,现在需要加入元素2,那么就先把q1中的元素都弹出来放入q2中,再把元素2加入q1,再将q2中的元素全部加入到q1,遵循队列原则,这些元素(也就是元素1)都会放到q1的尾部,也就是第一个元素是2,第二个元素是1。
(2)实现了Push功能,我们的队列的顺序就已经是遵循栈的原则了(先进后出)其余直接返回头部,或者弹出即在这里插入图片描述

public class MyStack {
    Queue<int> q1;
    Queue<int> q2;
    public MyStack() {
        q1 = new Queue<int>();
        q2 = new Queue<int>();
    }
    
    public void Push(int x) {
        while(q1.Count > 0)
        {
            q2.Enqueue(q1.Dequeue());
        }
        q1.Enqueue(x);
        while(q2.Count > 0)
        {
            q1.Enqueue(q2.Dequeue());
        }
    }
    
    public int Pop() {
        return q1.Dequeue();
    }
    
    public int Top() {
       return q1.Peek();
    }
    
    public bool Empty() {
        return q1.Count == 0 && q2.Count == 0;
    }
}

/**
 * Your MyStack object will be instantiated and called as such:
 * MyStack obj = new MyStack();
 * obj.Push(x);
 * int param_2 = obj.Pop();
 * int param_3 = obj.Top();
 * bool param_4 = obj.Empty();
 */

在这里插入图片描述
分析:本题想到栈作为解题,当遇到左括号的时候就添加右括号,直到遇到右括号就开始弹出看是否相等。
(1)首先是要记得写else if,因为最后的判断语句要弹出元素
(2)其次就是写判断条件 st1.Count == 0,因为输入元素s也可能是"(()“,这样栈中会有两个右括号,那么第二个右括号完全没有就会出现报错,所以记得return false
(3)最后也要判断一下栈中的元素是否为空,因为也可能是s只输入”)",那么for循环中也没有地方处理该元素
说句题外话:看到新题肯定考虑不到这么多情况,都是一边做一边报错一边去想,最后总结一下,至少保证下次看见思路更多一点就行

public class Solution {
    public bool IsValid(string s) {
       Stack<char> st1 = new Stack<char>();
       for(int i = 0; i < s.Length; i++)
       {
            if(s[i] =='{')
            {
                st1.Push('}');
            }
            else if(s[i] =='[')
            {
                st1.Push(']');
            }
            else if(s[i] =='(')
            {
                st1.Push(')');
            }
            else if(st1.Count == 0 || st1.Pop() != s[i])
            {
                return false;
            }
       }
       if(st1.Count != 0)
       {
          return false;
       }
       return true;
    }
}

在这里插入图片描述
分析:还是使用栈,把字符串中的所有元素都加入到栈,如果有一样的那就弹出该元素。假设栈中有ab,而字符串下一个元素是b,那就直接弹出b,此时栈中只有a,继续下一个元素的判断

public class Solution {
    public string RemoveDuplicates(string s) {
        Stack<char> st1 = new Stack<char>();
        for(int i = 0; i < s.Length; i++)
        {
            if(st1.Count != 0 && st1.Peek() == s[i])
            {
                st1.Pop();
            }
            else
            {
                st1.Push(s[i]);
            }
        }
        //新的字符串方法Concat:将指定的字符串参数连接到字符串上
        //直接将栈中的字符连接成字符串
        // st1.Reverse:栈是先进后出,需要翻转元素
        return string.Concat(st1.Reverse());
        //还有一种写法 就是将栈中的元素拼接成字符串即可
        /*
        string str = "";
        while(st1.Count > 0)
        {
        	str += st1.Pop();
        }
        return str;
        */
    }
}
  • 14
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值