Algorithm learning-Minimum stack implementation O (1) Time
Minimum Stack
The minimum stack is actually no different from the stack. The only difference is that the minimum stack can get the current stack space within the O (1) time and the minimum value is.
Minimum stack operation
The operation of the minimum stack is not much different from the operation of the normal Stack. the only method that is used is the getMin () method, which is used to obtain the minimum value in the current stack. Other methods are Push (), Pop (), Top ()..., etc.
Find the new minimum value in O (n) Time
This is amazing. Let's talk about the common O (n) method ~ Obtain the minimum value in the stack. Is it possible to maintain a Min variable? Not just! The following is an example.
First, we set a stack and a variable.
int MinSave the minimum value. Then, suppose our operations are-Push (1), Push (2), Push (3), Push (-1), Push (4) now: let's take a look at the changes in the stack and Min.
stack 1 2 3 -1 4 Min 1 1 1 -1 -1
We found that the Min value was inserted for the first time.1Is1, Insert 4th times-1Is changed-1At this time, do we think it is very simple to maintain only oneMinThat's it? No! Assume that we perform the following operations:Pop(),Pop()Operation. Let's take a look at what is left in the stack.
stack 1 2 3
SoMinWhat about it? Or-1, But actually-1Pop () has been dropped. If we find that the minimum value is Pop (), how can we update it?MinWhat about it? It can only be traversed from scratch, so it takes O (n) time.
O (1) Method
Here we will explain how O (1) can be found and the maintenance variables remain unchanged, but the elements we put in the stack memory need to be associated with the Min value.
Example:
We perform the same 5 Push operations, and the order of stack pressure is1 2 3 -1 4.
The first stack is stored for 0, and Min is 1. 2-Min = 1 for the Second stack storage, Min <2 so continue to 1. the third stack is stored for 3-Min = 2, Min <3 so it continues to be 1. the fourth stack storage-1-Min =-2, Min>-1 SO Min =-1. the fifth stack is 4-Min = 5, Min <5, so continue to be-1.
Do you understand? We store x-Min.
This is a Push operation. How can we do this when we perform Pop () and perform Pop () twice ()?
Element 5, 5> 0 at the top of the stack for the first time. In the pop-up window, 5 + Min = 4 is returned.
Element-2,-2 <0 at the top of the Second stack, pop up, return Min. and update Min = Min-(-2 ).
What about Top?
If the top element of the stack is 5, 5> 0, 5 + Min is returned.
If the top element of the stack is-2,-2 <0, Min is returned.
Did you find out? In fact, when we press the stack, the pressed element is X-Min, so as long as the pressed element is greater than Min, it stores all positive numbers, and when X is less than Min, the pressed element (X-Min) is a negative number.
So when the stack is played:
In case of positive numbers, the sum of elements (X-Min) and Min (X-Min + Min) on the top of the stack is displayed.
A negative number indicates that the Min value is updated when this element is pressed, and the Min value is updated as the newly inserted X. for example, if the value of Min is 1 and the value of-1 is inserted, the stack storage is-1 Min =-2, and the value of Min is updated to the new value of X (-1 ). then, the pop-up of Min is ready. At the same time, we will bring up the minimum value. To update Min, we will update it to the current Min-(X-Next Min) for comparison here. We will use multiple examples to understand it.
Code Implementation
I implemented four versions, the first two of which are at the O (1) level and the last two are at the O (n) level. Version 2nd May be defective. If you see any code error, please comment. Thank you.
Container 1 Implementation
Self-written struct.
/// Main. cpp // MinStack2 /// Created by Alps on 14/12/3. // Copyright (c) 2014 chen. All rights reserved. // # include
# Include
Using namespace std; class MinStack {public: vector
Stack; int min; void push (int x) {if (stack. empty () {stack. push_back (0); min = x;} else {stack. push_back (x-min); if (x <min) {min = x ;}} void pop () {if (stack. empty () {return;} else {if (stack. back () <0) {min = min-stack. back ();} stack. pop_back () ;}} int top () {if (stack. empty () {return NULL;} if (stack. back ()> 0) {return stack. back () + min;} else {return min;} int getMin () {If (stack. empty () {return NULL;} return min ;}; int main (int argc, const char * argv []) {// insert code here... std: cout <"Hello, World! \ N "; return 0 ;}
#2 STL stack implementation
During the edge test, my compiler did not go wrong, but OJ reported WA.
//// Main. cpp // MinStack4_leetcode // Created by Alps on 14/12/3. // Copyright (c) 2014 chen. All rights reserved. // # include
# Include
Using namespace std; class MinStack {public: stack
S; long min; void push (int x) {if (s. empty () {s. push (0); min = x;} else {s. push (x-min); if (x <min) {min = x ;}} void pop () {if (s. empty () {return;} else {if (s. top () <0) {min = min-s. top ();} s. pop () ;}} int top () {if (s. empty () {return NULL;} else {if (s. top ()> 0) {return (int) (min + s. top () ;}else {return (int) min ;}} int getMin () {if (s. empty () {return NULL;} else {return (int) min ;}}; int main (int argc, const char * argv []) {int a =-2147483648; MinStack M; M. push (2147483646); M. push (2147483646); M. push (2147483647); printf ("% d \ n", M. top (); M. pop (); printf ("% d \ n", M. getMin (); M. pop (); printf ("% d \ n", M. getMin (); M. pop (); M. push (2147483647); printf ("% d \ n", M. top (); printf ("% d \ n", M. getMin (); M. push (a); printf ("% d \ n", M. top (); printf ("% d \ n", M. getMin (); M. pop (); printf ("% d \ n", M. getMin (); return 0 ;}
#3 Linked List Implementation
The structure of a self-written linked list.
//// Main. cpp // MinStack3_leetcode // Created by Alps on 14/12/3. // Copyright (c) 2014 chen. All rights reserved. // # include
Using namespace std; class MinStack {public: struct StackNode {int num; StackNode * next;}; typedef StackNode * stack; stack s; MinStack () {s = (stack) malloc (sizeof (struct StackNode); s-> next = NULL;} int min; void push (int x) {if (s-> next = NULL) {stack node = (stack) malloc (sizeof (struct StackNode); node-> num = x; node-> next = s-> next; s-> next = node; min = x;} else {stack node = (stack) malloc (Sizeof (struct StackNode); node-> num = x; node-> next = s-> next; s-> next = node; if (x <min) {min = x ;}} void pop () {if (s-> next = NULL) {return;} else {stack temp = s-> next; if (min = s-> next-> num & s-> next! = NULL) {s-> next = s-> next; free (temp); min = s-> next-> num; for (stack loop = s-> next; loop! = NULL; loop = loop-> next) {if (min> loop-> num) {min = loop-> num ;}}} else {s-> next = s-> next; free (temp) ;}} int top () {if (s-> next = NULL) {return NULL;} return s-> next-> num;} int getMin () {if (s-> next = NULL) {return NULL ;} return min ;}; int main (int argc, const char * argv []) {MinStack MinS; MinS. push (-1); MinS. push (0); MinS. push (2); MinS. push (-2); printf ("% d \ n", MinS. top (); MinS. pop (); MinS. pop (); MinS. pop (); printf ("% d \ n", MinS. getMin (); return 0 ;}
Container 4 Implementation
The oldest version.
/// Main. cpp // MinStack_leetcode /// Created by Alps on 14/12/2. // Copyright (c) 2014 chen. All rights reserved. // # include
# Include "vector" using namespace std; class MinStack {public: struct StackNode {int num; int min ;}; vector
Stack; void push (int x) {if (stack. empty () {StackNode S = {x, x}; stack. push_back (S);} else {if (x <stack. back (). min) {StackNode S = {x, x}; stack. push_back (S);} else {StackNode S = {x, stack. back (). min}; stack. push_back (S) ;}}void pop () {if (stack. empty () {} else {stack. pop_back () ;}} int top () {if (stack. empty () {return NULL;} return stack. back (). num;} int getMin () {if (stack. empty () {return NULL;} return stack. back (). min ;}; int main (int argc, const char * argv []) {MinStack minstack; minstack. push (-1); minstack. push (1); printf ("% d \ n", minstack. top (), minstack. getMin (); return 0 ;}