How to create mergable stack?

Design a stack with following operations.

a) push(Stack s, x): Adds an item x to stack s
b) pop(Stack s): Removes the top item from stack s
c) merge(Stack s1, Stack s2): Merge contents of s2 into s1.

Time Complexity of all above operations should be O(1).

If we use array implementation of stack, then merge is not possible to do in O(1) time as we have to do following steps.
a) Delete old arrays
b) Create a new array for s1 with size equal to size of old array for s1 plus size of s2.
c) Copy old contents of s1 and s2 to new array for s1
The above operations take O(n) time.

We can use a linked list with two pointers, one pointer to first node (also used as top when elements are added and removed from beginning). The other pointer is needed for last node so that we can quickly link the linked list of s2 at the end of s1. Following are all operations.
a) push(): Adds the new item at the beginning of linked list using first pointer.
b) pop(): Removes an item from beginning using first pointer.
c) merge(): Links the first pointer second stack as next of last pointer of first list.



Can we do it if we are not allowed to use extra pointer?
We can do it with circular linked list. The idea is to keep track of last node in linked list. The next of last node indicates top of stack.
a) push(): Adds the new item as next of last node.
b) pop(): Removes next of last node.
c) merge(): Links the top (next of last) of second list to the top (next of last) of first list. And makes last of second list as last of whole list.

This article is contributed by Rahul Gupta. Please write comments if you find anything incorrect, or you want to share more information about the topic discussed above

The code for the above is given below:

C++

filter_none

edit
close

play_arrow

link
brightness_4
code

#include <iostream>
using namespace std;
  
class node {
public:
    int data;
    node* next;
};
  
class mystack {
public:
    node* head;
    node* tail;
  
    mystack()
    {
        head = NULL;
        tail = NULL;
    }
};
  
mystack* create()
{
    mystack* ms = new mystack(); // creating a new stack
    return ms;
}
  
void push(int data, mystack* ms)
{
    node* temp = new node();
    temp->data = data;
    temp->next = ms->head;
  
    // when pushing first element in the stack the tail 
    // must be pointed by that first element
    if (ms->head == NULL)  
        ms->tail = temp; 
      
    ms->head = temp;
}
  
int pop(mystack* ms)
{
    if (ms->head == NULL) {
        cout << "stack underflow" << endl;
        return 0;
    }
    else {
        node* temp = ms->head;
        ms->head = ms->head->next;
        int popped = temp->data;
        delete temp;
        return popped;
    }
}
  
// making the next pointer of tail of 
// one stack point to other stack
void merge(mystack* ms1, mystack* ms2)
{
   if (ms1->head == NULL)
   {
       ms1->head = ms2->head;
       ms1->tail = ms2->tail; 
       return;
   }
     
   ms1->tail->next = ms2->head;
   ms1->tail = ms2->tail; 
}
  
void display(mystack* ms)
{
    node* temp = ms->head;
    while (temp != NULL) {
        cout << temp->data << " ";
        temp = temp->next;
    
}
  
int main()
{
    mystack* ms1 = create();
    mystack* ms2 = create();
  
    push(6, ms1);
    push(5, ms1);
    push(4, ms1);
    push(9, ms2);
    push(8, ms2);
    push(7, ms2);
    merge(ms1, ms2);
    display(ms1);
} // This code is contributed by jayshmi

chevron_right


Output:

4 5 6 7 8 9

Attention reader! Don’t stop learning now. Get hold of all the important DSA concepts with the DSA Self Paced Course at a student-friendly price and become industry ready.




My Personal Notes arrow_drop_up

Improved By : jayshmi

Article Tags :
Practice Tags :


4


Please write to us at contribute@geeksforgeeks.org to report any issue with the above content.