How to implement a queue using two stacks
Hello, I need to implement a queue using two stacks, i.e. I need to insert an integer into Stack 1, and when I am removing an element all items from Stack 1 must be transferred to stack 2, then making it look like a queue.
Items from Stack 1 can only be transferred if stack 2 is empty, while it is not elements must be removed from Stack 2.
The code for insertion and removal in stack 1 is as follows way:
#include<stdio.h>
#include<stdlib.h>
typedef struct noLista{
int info;
struct noLista *prox;
} Elemento;
Elemento* criarNovo(int Caractere);
Elemento* Push(Elemento *Topo, int Caractere);
Elemento* Pop(Elemento *Topo);
Elemento* Top(Elemento *Topo);
main () {
int Dados, i, op;
Elemento *Pilha = NULL, *aux;
do{
system("cls");
printf("1 - Adicionar elemento\n");
printf("2 - Remover elemento\n");
printf("0 - Encerrar\n\n");
printf("Opcao: ");
scanf("%d", &op);
switch(op){
case 1:
printf("Digite um inteiro: ");
scanf("%d", &Dados);
Pilha = Push(Pilha, Dados);
printf("Elemento adicionado\n\n");
system("pause");
break;
case 2:
aux = Top(Pilha);
if(aux != NULL){
Pilha = Pop(Pilha);
printf("Elemento removido\n\n");
system("pause");
} else{
printf("A pilha esta vazia\n\n");
system("pause");
}
break;
case 3:
break;
}
} while(op!=0);
}
Elemento* criarNovo(int Caractere){
Elemento *novo;
novo = (Elemento*) malloc(sizeof(Elemento));
novo->info = Caractere;
novo->prox = NULL;
return novo;
}
Elemento* Push(Elemento *Topo, int Caractere){
Elemento *novo;
novo = criarNovo(Caractere);
novo->prox = Topo;
Topo = novo;
return Topo;
}
Elemento* Pop(Elemento *Topo){
Elemento *aux;
aux = Topo;
if(Topo != NULL) {
Topo = Topo->prox;
free(aux);
}
return Topo;
}
Elemento* Top(Elemento *Topo){
return Topo;
}
What should I do?
2 answers
typedef struct item_p
{
int elemento;
struct item_p *proximo;
} pilhaItem;
typedef struct
{
pilhaItem *raiz;
int tamanho;
} pilha;
pilha* pilha_nova()
{
/* cria pilha */
pilha *p = (pilha*) malloc(sizeof(pilha));
if(p == NULL)
return NULL;
/* pilha esta' vazia */
p->raiz = NULL;
p->tamanho = 0;
return p;
}
int pilha_tamanho(pilha *p)
{
if (p == NULL)
return -1;
return p->tamanho;
}
int pilha_top(pilha *p)
{
pilhaItem *aux;
if (p == NULL || p->tamanho == 0)
return NULL;
aux = p->raiz;
return aux->elemento;
}
pilhaItem* pilha_novo_elemento(int valor)
{
/* aloca memoria para a estrutura pilhaItem */
pilhaItem *item = (pilhaItem *) malloc(sizeof(pilhaItem));
if(item == NULL)
return NULL;
item->elemento=valor;
/* item ainda nao tem proximo */
item->proximo = NULL;
return item;
}
void pilha_push(pilha *p, int valor)
{
pilhaItem *novo = NULL;
if (p == NULL || valor == NULL)
return;
/* cria novo item */
novo = pilha_novo_elemento(valor);
if (novo == NULL)
return;
p->tamanho++;
/* inserir no topo da pilha */
/* se a pilha esta vazia */
if (p->raiz == NULL)
{
p->raiz = novo;
return;
}
/* primeiro elemento */
novo->proximo = p->raiz;
p->raiz = novo;
}
void pilha_pop(pilha *p)
{
pilhaItem *curr;
if (p == NULL || p->tamanho == 0)
return;
curr = p->raiz;
p->raiz = curr->proximo;
p->tamanho--;
/* liberta memoria associada ao item removido */
free(curr);
}
Test these functions in the ideone (example of how to use)
Main file
main () {
int Dados, i, op;
pilha *Pilha1=pilha_nova();
do{
system("cls");
printf("1 - Adicionar elemento\n");
printf("2 - Remover elemento\n");
printf("0 - Encerrar\n\n");
printf("Opcao: ");
scanf("%d", &op);
switch(op){
case 1:
printf("Digite um inteiro: ");
scanf("%d", &Dados);
pilha_push(Pilha1, Dados);
printf("Elemento adicionado\n\n");
system("pause");
break;
case 2:
if(Pilha1 != NULL){
pilha_pop(Pilha1);
printf("Elemento removido\n\n");
system("pause");
} else{
printf("A pilha esta vazia\n\n");
system("pause");
}
break;
case 3:
break;
}
} while(op!=0);
pilha *Pilha2=pilha_nova();
while(pilha_tamanho(Pilha1)>0){
pilha_push(Pilha2, pilha_top(Pilha1));
pilha_pop(Pilha1);
}
}
The final part of the code I put all the data from Stack 1 into Stack 2 as I wanted.
pilha *Pilha2=pilha_nova();
while(pilha_tamanho(Pilha1)>0){
pilha_push(Pilha2, pilha_top(Pilha1)); //inserir na pilha 2 o valor de pilha 1
pilha_pop(Pilha1); // remover o topo da pilha 1
}
The method of moving from one stack to another stack is:
LOOP: {
- return the value from the top of Stack 1 and put in the stack 2
- remove value from top of Stack 1
}
Since @FabioMorais has already responded with a possible alternative implementation for the problem, I take the opportunity to show an implementation starting from the code it has and changing as little as possible.
I cannot help but make an aside for the nomenclature you are using that is more important than it seems. Let's look at these lines of code:
Elemento* criarNovo(int Caractere);
Elemento* Push(Elemento *Topo, int Caractere);
int Dados, i, op;
Here you are using camelCase and PascalCase, in addition to setting the parameters of the capitalized functions and variables. The most important thing is to be consistent and always use the same naming style, and the most adopted pattern in C is snake_case. In this pattern these instructions would be:
Elemento* criar_novo(int caractere);
Elemento* push(Elemento *topo, int caractere);
int dados, i, op;
Names of structures and classes are often capitalized.
Leaving now for the solution. First you have to create the second stack:
Elemento *Pilha = NULL, *aux, *Pilha2 = NULL;
// ^---
Which will be the stack that will have the items to be removed. The idea now is:
- if
Pilha2
has elements then remove removes the top of that directly. - if it is empty you must first pass all the elements to from
Pilha
toPilha2
and then remove the top ofPilha2
Implementation:
case 2:
if (Top(Pilha2) == NULL){ // se a pilha 2 está vazia
while (Top(Pilha) != NULL){ //passa tudo da pilha1 para a pilha2
int removido = Top(Pilha)->info;
Pilha = Pop(Pilha);
Pilha2 = Push(Pilha2, removido);
}
}
if(Top(Pilha2) != NULL) { //se existem elementos
int removido = Top(Pilha2)->info; //remove o primeiro da pilha2
Pilha2 = Pop(Pilha2);
printf("Elemento %d removido\n\n", removido);
} else {
printf("A pilha esta vazia\n\n");
}
break;
See how it works in Ideone by adding elements 5, 10 and 12 and then removing all
Visually what happens first is that first is everything added to the Pilha1
Pilha1:
12 -> 10 -> 5 -> NULL
Pilha2:
NULL
Then on the first removal does Pop
to everything from Pilha1
and does Push
to Pilha2
.
Step 1:
Pilha1:
10 -> 5 -> NULL
Pilha2:
12 -> NULL
Step 2:
Pilha1:
5 -> NULL
Pilha2:
10 -> 12 -> NULL
Step 3:
Pilha1:
NULL
Pilha2:
5 -> 10 -> 12 -> NULL
After these steps all removals are done by Pilha2
and so start by removing on 5, giving the Order 5, 10, 12 which works as a queue and not a stack.