3.1Describe how you could use a single array to implement three stacks.
1)solution 1
divide the array to 3 part, so each part can be one stack, but for each stack is limited to n/3 size
[stk1][stk2][stk3]
2)solution 1 improvement
stk2 and stk3 share same size, this can increase stk2 or stk3 use n*2/3 size, stk1 still only use n/3 size
[ stk1][stk2 stk3]
3)solution 2,
link array as free link list, so each stack can be regard as link list based. so each stack may use whole size n if possible
for each stack, push is to get the free item from free list, and link it to its own list
for pop, remove the item from its list and return to free list
see below sample code
struct element{
int val;
int next;
};
class stack3{
private:
const maxSize=1000;
element data[maxSize];
int top[3];
int free;//point to free list
stack3(){
top[0]=top[1]=top[2]=-1;
//create free list
for(int i = 0;i < maxSize;i++){
data[i].next = i+1;
}
free = 0;//point to first
}
void push(int num,int val){
if(free==maxSize){
return; //no space
}
//get free slot
int index = free;
free = data[free].next;
data[index].val = val;
data[index].next = top[num];//link to stack
top[num] = index; //point to new top
}
int top(int num){
assert(!empty(num));
return data[top[num]].val;
}
void pop(int num){
if(top[num] == -1){
return; //no element
}
int index = top[num];
top[num] = data[index].next;//update top pointer
data[index].next = free; //link to free list
free = index;
}
bool empty(int num){
return top[num] == -1;
}
};
3.2How would you design a stack which, in addition to push and pop, also has a functionmin which returns the minimum element? Push, pop and min should all operate inO(1) time.
basic idea
1)use two stack, one is for element, another is for min element
when push number, push current min number, current min Numbr = min(number, minStk.top())
pros: easy implement
cons: min stack needs to occupy same space as normal stack
2)improvement
actually minStack doens't need to grow with normal stack same time, only push new min when necessary
class MinStack {
private:
stack<int>stk,minStk;
public:
MinStack() {
}
/*optimize memory usage of minStack
only push min elements when minStk.top() <= number
*/
void push(int number) {
stk.push(number);
if(minStk.empty() || number <= minStk.top()){
minStk.push(number);
}
}
int pop() {
int ret = stk.top();
if(stk.top()==minStk.top()){
minStk.pop();
}
stk.pop();
return ret;
}
int min() {
return minStk.top();
}
};