Skip to content

Commit

Permalink
feat: update #232 and #53 (#259)
Browse files Browse the repository at this point in the history
  • Loading branch information
StoneLyu authored and azl397985856 committed Jan 3, 2020
1 parent b71a73d commit 97fe63d
Show file tree
Hide file tree
Showing 2 changed files with 67 additions and 3 deletions.
68 changes: 66 additions & 2 deletions problems/232.implement-queue-using-stacks.md
Original file line number Diff line number Diff line change
Expand Up @@ -29,7 +29,7 @@ You may assume that all operations are valid (for example, no pop or peek operat

## 思路

这道题目是让我们用栈来模拟实现队列。 我们直到栈和队列都是一种受限的数据结构
这道题目是让我们用栈来模拟实现队列。 我们知道栈和队列都是一种受限的数据结构
栈的特点是只能在一端进行所有操作,队列的特点是只能在一端入队,另一端出队。

在这里我们可以借助另外一个栈,也就是说用两个栈来实现队列的效果。这种做法的时间复杂度和空间复杂度都是O(n)。
Expand Down Expand Up @@ -64,7 +64,7 @@ push之前是这样的:

## 代码

* 语言支持:JS, Python
* 语言支持:JS, Python, Java

Javascript Code:

Expand Down Expand Up @@ -183,6 +183,70 @@ class MyQueue:
# param_4 = obj.empty()
```

Java Code

```java
class MyQueue {
Stack<Integer> pushStack = new Stack<> ();
Stack<Integer> popStack = new Stack<> ();

/** Initialize your data structure here. */
public MyQueue() {

}

/** Push element x to the back of queue. */
public void push(int x) {
while (!popStack.isEmpty()) {
pushStack.push(popStack.pop());
}
pushStack.push(x);
}

/** Removes the element from in front of queue and returns that element. */
public int pop() {
while (!pushStack.isEmpty()) {
popStack.push(pushStack.pop());
}
return popStack.pop();
}

/** Get the front element. */
public int peek() {
while (!pushStack.isEmpty()) {
popStack.push(pushStack.pop());
}
return popStack.peek();
}

/** Returns whether the queue is empty. */
public boolean empty() {
return pushStack.isEmpty() && popStack.isEmpty();
}
}

/**
* 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();
* boolean param_4 = obj.empty();
*/
````

## 扩展
- 类似的题目有用队列实现栈,思路是完全一样的,大家有兴趣可以试一下。
- 栈混洗也是借助另外一个栈来完成的,从这点来看,两者有相似之处。

## 延伸阅读

实际上现实中也有使用两个栈来实现队列的情况,那么为什么我们要用两个stack来实现一个queue?

其实使用两个栈来替代一个队列的实现是为了在多进程中分开对同一个队列对读写操作。一个栈是用来读的,另一个是用来写的。当且仅当读栈满时或者写栈为空时,读写操作才会发生冲突。

当只有一个线程对栈进行读写操作的时候,总有一个栈是空的。在多线程应用中,如果我们只有一个队列,为了线程安全,我们在读或者写队列的时候都需要锁住整个队列。而在两个栈的实现中,只要写入栈不为空,那么`push`操作的锁就不会影响到`pop`

- [reference](https://leetcode.com/problems/implement-queue-using-stacks/discuss/64284/Do-you-know-when-we-should-use-two-stacks-to-implement-a-queue)

- [further reading](https://stackoverflow.com/questions/2050120/why-use-two-stacks-to-make-a-queue/2050402#2050402)
2 changes: 1 addition & 1 deletion problems/53.maximum-sum-subarray-cn.md
Original file line number Diff line number Diff line change
Expand Up @@ -80,7 +80,7 @@ If you have figured out the O(n) solution, try coding another solution using the

#### 复杂度分析
- *时间复杂度:* `O(nlogn) - n 是数组长度`
- *空间复杂度:* `Ologn)` - 因为调用栈的深度最多是logn。
- *空间复杂度:* `O(logn)` - 因为调用栈的深度最多是logn。

#### 解法五 - [动态规划](https://www.wikiwand.com/zh-hans/%E5%8A%A8%E6%80%81%E8%A7%84%E5%88%92)
动态规划的难点在于找到状态转移方程,
Expand Down

0 comments on commit 97fe63d

Please sign in to comment.