1. Show how a stack can be used to evaluate a postfix expression with the help of this example. 632-5*+1^7+
#include<stdio.h> #include<math.h> #include<string.h> #include<stdlib.h> #define ERRCODE 12345 #define DIVBYZERO 23456 struct node { double n1; struct node *next; }; typedef struct node *NODEPTR; NODEPTR createnode(double num) { NODEPTR newnode = (NODEPTR) malloc(sizeof(struct node)); newnode->n1 = num; newnode->next = NULL; } NODEPTR push(double num,NODEPTR top) { NODEPTR newnode = createnode(num); newnode->next = top; top = newnode; return top; } double pop(NODEPTR * top) { if(top==NULL) return ERRCODE; NODEPTR temp = *top; *top =(*top)->next; double val = temp->n1; free(temp); return val; } int is_operator(char ch) { switch(ch) { case '+': case '-': case '/': case '*': case '^': return 1; default : return 0; } } double evaluate(char *postfix) { char ch; double ans,n1,n2; NODEPTR top = NULL; while(ch =*postfix++) { if(isdigit(ch)) { double n = ch-48; top = push(n,top); } else if(is_operator(ch)) { n1 = pop(&top); if(n1==ERRCODE) return ERRCODE; n2 = pop(&top); if(n2 ==ERRCODE) return ERRCODE; switch(ch) { case '+': ans = n1+n2; break; case '-': ans = n2 - n1; break; case '*': ans = n1*n2; break; case '/': if(n1!=0) ans = n2/n1; else return DIVBYZERO; break; case '^':ans = pow(n2,n1); break; } top = push(ans,top); } } ans = pop(&top); return ans; } int main() { char postfix[30]; double ans; printf("Enter postfix expression (leave space between values):"); fgets(postfix,29,stdin); ans = evaluate(postfix); printf("The value of expression is %f",ans); return 0; }
2. Convert the following expressions into prefix and postfix. A+B*C-D/E*H (A+B^C^D)*(E+F/D)
3. What is stack data structure? Write push, pop, isEmpty and isFull functions for a stack using array implementation
#include<stdio.h> #define MAX 30 struct stack { int arr[MAX]; int top; }; void push(struct stack *s, int val) { if( is_full(s)) printf("Stack overflow"); else { (s->top)++; s->arr[s->top]=val; } } int is_empty(struct stack *s) { return s->top==-1; } int is_full(struct stack *s) { return s->top>=MAX; } int pop(struct stack *s) { int val = -1; if(is_empty(s)) printf("Stack empty"); else { int t = s->arr[s->top]; s->top--; val = t; } return val; } int main() { struct stack s1; s1.top = -1; int option; while(1) { printf("Enter 1- push 2-pop 3 - exit:"); scanf("%d",&option); if(option==3) break; else if(option==1) { int num; printf("Enter value to push:"); scanf("%d",&num); push(&s1,num); } else if(option==2) { int num; num = pop(&s1); if(num!=-1) printf("value popped is %d\n",num); } } return 0; }
4. Write an algorithm to convert an infix expression into postfix. And also write code for this.
#include<stdio.h> #include"stack.h" int is_operator(char ch) { switch(ch) { case '+': case '-': case '/': case '*': case '%': case '^': return 1; default : return 0; } } int priority(char ch) { switch(ch) { case '+': case '-':return 1; case '/': case '*': case '%':return 2; case '^':return 3; default : return 0; } } void convert(char *input, char *output) { struct stack s1; s1.top = -1; while(*input) { char ch = *input++; char ch2; if(ch=='(') push(&s1,ch); else if(ch==')') { while(!is_empty(&s1) && ( (ch=pop(&s1))!='(')) *output++ = ch; } else if(is_operator(ch)) { while(!is_empty(&s1) && priority(peek(&s1))>=priority(ch)) *output++ = pop(&s1); push(&s1,ch); } else *output++ = ch; } while(!is_empty(&s1)) *output++ = pop(&s1); *output = 0; } int main() { char infix[40],postfix[40]; printf("Enter infix expression:"); scanf("%s",infix); convert(infix,postfix); printf("the postfix expression is %s\n",postfix); return 0; } /*stack implementation not shown */
5. Explain how a stack can be implemented using a linked list. Write C functions for push, pop, isempty for this method.
#include<stdio.h> #include<stdlib.h> #define ERROR -1000 struct node { int n; struct node *next; }; typedef struct node * NODEPTR; NODEPTR create_node(int value) { NODEPTR temp = (NODEPTR) malloc(sizeof(struct node)); temp->next = NULL; temp->n = value; return temp; } NODEPTR push(NODEPTR top,int n) { NODEPTR newnode = create_node(n); newnode->next = top; top = newnode; return top; } int isempty(NODEPTR top) { return top==NULL; } int pop(NODEPTR *topPtr) { if(isempty(*topPtr)) return ERROR; int num = (*topPtr)->n; NODEPTR temp = *topPtr; *topPtr = (*topPtr)->next; free(temp); return num; } int main() { NODEPTR top = NULL; NODEPTR nd; while(1) { int option,value; printf("Enter 1- push 2- pop 3 - exit"); scanf("%d",&option); if(option==3) break; switch(option) { case 1: printf("new value to push="); scanf("%d",&value); top = push(top,value); break; case 2: value = pop(&top); if(value==ERROR) printf("Stack empty\n"); else printf("Value popped is %d\n",value); break; } } }
6. Design a method to create two stacks in a single array so that either stack overflows until the memory is completely filled and a stack is never moved to another memory location. Write push1, push2, pop1, pop2, display1 and display2 functions for this in C.
#include<stdio.h> #define MAX 5 struct two_stacks { int arr[MAX]; int top1,top2; }; void push1(struct two_stacks *s, int val) { if( is_full(s)) printf("Stack overflow"); else { (s->top1)++; s->arr[s->top1]=val; } } void push2(struct two_stacks *s, int val) { if( is_full(s)) printf("Stack overflow"); else { (s->top2)--; s->arr[s->top2]=val; } } int is_empty1(struct two_stacks *s) { return s->top1==-1; } int pop1(struct two_stacks *s) { int val = -1; if(is_empty1(s)) printf("Stack empty"); else { int t = s->arr[s->top1]; s->top1--; val = t; } return val; } int pop2(struct two_stacks *s) { int val = -1; if(is_empty2(s)) printf("Stack empty"); else { int t = s->arr[s->top2]; s->top2++; val = t; } return val; } int is_empty2(struct two_stacks *s) { return s->top2==MAX; } int is_full(struct two_stacks *s) { return (s->top2-s->top1==1)?1:0; } int main() { struct two_stacks s; s.top1 = -1; s.top2 = MAX; int option; while(1) { printf("Enter 1- push to s1, 2-pop from s1, 3- push to s2, 4-pop from s2, 5 - exit:"); scanf("%d",&option); if(option==5) break; else if(option==1||option==3) { int num; printf("Enter value to push:"); scanf("%d",&num); if(option==1) push1(&s,num); else push2(&s,num); } else if(option==2||option==4) { int num; if(option==2) num = pop1(&s); else num = pop2(&s); if(num!=-1) printf("value popped is %d\n",num); } } return 0; }
7. Write a function to convert a given postfix expression to infix expression.
#include<stdio.h> #include<string.h> #include<stdlib.h> struct node { char str[30]; struct node *next; }; struct node *createnode(char *str) { struct node *newnode = (struct node*) malloc(sizeof(struct node)); strcpy(newnode->str,str); newnode->next = NULL; } struct node * push(char *str,struct node *top) { struct node *newnode = createnode(str); newnode->next = top; top = newnode; return top; } char * pop(struct node ** top) { static char str[30]; if(*top==NULL) return NULL; struct node * temp = *top; *top =(*top)->next; strcpy(str,temp->str); free(temp); return str; } int is_operator(char ch) { switch(ch) { case '+': case '-': case '/': case '*': case '^': return 1; default : return 0; } } char *concat(char *s1,char *s2,char ch) { char *result = (char*)malloc(60); int i=1; result[0] = '('; while(*s1) result[i++]=*s1++; result[i++]=ch; while(*s2) result[i++]=*s2++; result[i++]=')';/*enclose in parantheses*/ result[i]=0; return result; } int convert(char *postfix,char *infix) { char ch; char oper1,oper2,opernew; char *expr1=(char*)malloc(30); char *expr2=(char*)malloc(30); char *expr3 = (char*)malloc(60); struct node *top = NULL; int iserr = 0; while(ch =*postfix++) { if(isdigit(ch) ||isalpha(ch)) { char str[] = {ch,0}; top = push(str,top); } else if(is_operator(ch)) { char* str = pop(&top); if(str==NULL) { printf("pop error"); iserr=1; break; } strcpy(expr1, str); str = pop(&top); if(str==NULL) { iserr = 1; printf("Error"); break; } strcpy(expr2,str); strcpy(expr3, concat(expr2,expr1,ch)); top = push(expr3,top); } } if(!iserr) strcpy(infix,pop(&top)); else return 0; } int main() { char postfix[30];char infix[30]; double ans; printf("Enter postfix expression :"); scanf("%s",postfix); if(convert(postfix,infix)) printf("The expression in infix is %s",infix); return 0; }
8. Write a function to check if a given expression is having balanced brackets.
#include<stdio.h> #include<string.h> #include<stdlib.h> #define ERRORCHAR 65 struct node { char ch; struct node *next; }; struct node *createnode(char ch) { struct node *newnode = (struct node*) malloc(sizeof(struct node)); newnode->ch = ch; newnode->next = NULL; return newnode; } int is_empty(struct node *top) { return top==NULL; } struct node * push(char ch,struct node *top) { struct node *newnode = createnode(ch); newnode->next = top; top = newnode; return top; } char pop(struct node ** top) { char ch; if(*top==NULL) return ERRORCHAR; struct node * temp = *top; *top =(*top)->next; ch = temp->ch; free(temp); return ch; } int is_opening_bracket(char ch) { switch(ch) { case '(': case '[': case '{': return 1; default : return 0; } } int is_closing_bracket(char ch) { switch(ch) { case ')': case ']': case '}': return 1; default : return 0; } } int is_matching_bracket(struct node **top,char ch) { char ch2 = pop(top); if(ch2!=ERRORCHAR) { if(ch2=='(' && ch==')' ) return 1; if(ch2=='[' && ch==']' ) return 1; if(ch2=='{' && ch=='}' ) return 1; } return 0; } int is_balanced(char *expression) { char ch; struct node *top = NULL; while(ch =*expression++) { if(is_opening_bracket(ch)) { top = push(ch,top); } else if(is_closing_bracket(ch)) { if(!is_matching_bracket(&top,ch)) { return 0; } } } return is_empty(top); } int main() { char expression[50]; printf("Enter an expression :"); scanf("%s",expression); if(is_balanced(expression)) { printf("The expression has balanced brackets"); } else { printf("The expression has unbalanced brackets"); } return 0; }
9. Given two integer sequences, one of which is the push sequence of a stack, please check whether the other sequence is a corresponding pop sequence or not.
#include<stdio.h> void read_array(int *arr,int n) { int i; printf("Enter the elements of the array:"); for (i=0;i<n;i++) scanf("%d",&arr[i]); } void write_array(int *arr,int n) { int i; printf("The array is "); for (i=0;i<n;i++) printf("%d ",arr[i]); } int is_pop_sequence(int *arr1,int *arr2,int n) { int i,j; for(i=0,j=n-1;i<n;i++,j--) if(arr1[i]!=arr2[j]) return 0; return 1; } int main() { int arr1[20], arr2[20]; int n; printf("Enter the length of sequence:"); scanf("%d",&n); read_array(arr1,n); read_array(arr2,n); if(is_pop_sequence(arr1,arr2,n)) printf("These two correspond to push and pop sequences"); else printf("These are not push and pop sequences of same stack"); }
10. Write a recursive function to reverse a stack .
#include<stdio.h> #include<stdlib.h> #define ERROR -1000 struct node { int n; struct node *next; }; typedef struct node * NODEPTR; NODEPTR create_node(int value) { NODEPTR temp = (NODEPTR) malloc(sizeof(struct node)); temp->next = NULL; temp->n = value; return temp; } void push(NODEPTR* topptr,int n) { NODEPTR newnode = create_node(n); newnode->next = *topptr; *topptr = newnode; } int isempty(NODEPTR top) { return top==NULL; } int pop(NODEPTR *topPtr) { if(isempty(*topPtr)) return ERROR; int num = (*topPtr)->n; NODEPTR temp = *topPtr; *topPtr = (*topPtr)->next; free(temp); return num; } void bottom_insert(NODEPTR *topptr,int n) { if(isempty(*topptr)) push(topptr,n); else { int a = pop(topptr); bottom_insert(topptr,n); push(topptr,a); } } void reverse(NODEPTR *topptr) { if(*topptr!=NULL) { int n= pop(topptr); reverse(topptr); bottom_insert(topptr,n); } } int main() { NODEPTR top = NULL; NODEPTR nd; while(1) { int option,value; printf("Enter 1- push 2- pop 3 - reverse stack 4 - exit"); scanf("%d",&option); if(option==4) break; switch(option) { case 1: printf("new value to push="); scanf("%d",&value); push(&top,value); break; case 2: value = pop(&top); if(value==ERROR) printf("Stack empty\n"); else printf("Value popped is %d\n",value); break; case 3: reverse(&top); break; } } }
11. Write a function to print next greater element for all elements in an array. If there is no NGE , it must print -1 for that element
#include<stdio.h> #include"stackint.h" void read_array(int *arr,int sz) { int i; for(i =0;i<sz;i++) { printf("arr[%d]=",i); scanf("%d",&arr[i]); } } void print_array(int *arr,int sz) { int i; for(i =0;i<sz;i++) { printf("arr[%d]=",i); printf("%d ",arr[i]); } printf("\n"); } void next_greater_elements(int *arr,int n) { STACK s1; int i; s1.top=-1; push(&s1,arr[0]); for(i=1;i<n;i++) { while (!is_empty(&s1) && peek(&s1) < arr[i]) { printf("Next greater element for %d =%d\n" , + pop(&s1), arr[i]); } push(&s1,arr[i]); } while(!is_empty(&s1)) printf("Next greater element for %d is -1\n",pop(&s1)); } int main() { int arr[50]; int sz; printf("Enter the size of array:"); scanf("%d",&sz); read_array(arr,sz); print_array(arr,sz); next_greater_elements(arr,sz); return 0; }
12. Implement a stack with min() function which returns the minimum value of a stack. All of push(), pop() and min() function must have time complexity of O(1)
#include<stdio.h> #include<stdlib.h> #define ERROR -1000 struct node { int value; struct node *next; }; typedef struct node * NODEPTR; NODEPTR create_node(int value) { NODEPTR temp = (NODEPTR) malloc(sizeof(struct node)); temp->next = NULL; temp->value= value; return temp; } NODEPTR push(NODEPTR top,int val) { NODEPTR newnode = create_node(val); newnode->next = top; top = newnode; return top; } int isempty(NODEPTR top) { return top==NULL; } int pop(NODEPTR *topPtr) { if(isempty(*topPtr)) return ERROR; int num = (*topPtr)->value; NODEPTR temp = *topPtr; *topPtr = (*topPtr)->next; free(temp); return num; } int peek(NODEPTR nd) { return nd->value; } void push1(NODEPTR*topptr,NODEPTR* mintopptr,int val) { int minval =val; if(*mintopptr!=NULL) { int temp = peek(*mintopptr); if (temp<minval) minval = temp; } *topptr = push(*topptr,val); *mintopptr = push(*mintopptr,minval); } int pop1(NODEPTR* topptr,NODEPTR *mintopptr) { if(!isempty(*topptr)) { pop(mintopptr); return pop(topptr); }else return ERROR; } int findmin(NODEPTR mintop) { if(mintop==NULL) return -1; return mintop->value; } int main() { NODEPTR top = NULL; NODEPTR nd; NODEPTR mintop=NULL; while(1) { int option,value; printf("Enter 1- push 2- pop 3 - exit 4- find minimum"); scanf("%d",&option); if(option==3) break; switch(option) { case 1: printf("new value to push="); scanf("%d",&value); push1(&top,&mintop,value); break; case 2: value = pop1(&top,&mintop); if(value==ERROR) printf("Stack empty\n"); else printf("Value popped is %d\n",value); break; case 4: value=findmin(mintop); if(value==-1) printf("Stack empty\n"); else printf("Minimum of stack is %d\n",value); break; } } }
13. Write a program to reverse a string using stack.
void reverseString(char *str) { struct stack s; s.top = -1; char ch; char *temp = str; while(ch=*str++)/*till '\0'*/ { push(&s,ch); } str = temp;/*go to beg address*/ while(!is_empty(&s)) *str++ = pop(&s); } int main() { char str[50]; printf("Enter a string"); fgets(str,49,stdin); reverseString(str); printf("The reversed string is %s\n",str); return 0; }
14. With the help of a stack, determine whether a given string is a palindrome.
#include<stdio.h> #include<string.h> #include<stdlib.h> #define MAX 70 struct stack { int arr[MAX]; int top; }; char pop(struct stack *s); void push(struct stack *s, char val); int is_palindrome(char *str) { char *str2=str; struct stack s; s.top = -1; while(*str) { char ch = *str++; push(&s,ch); } while(*str2 && !is_empty(s)) { char ch = pop(&s); if( *str2 !=ch) return 0; str2++; } return 1; } int is_full(struct stack *s) { return s->top>=MAX; } void push(struct stack *s, char val) { if( is_full(s)) printf("Stack overflow"); else { (s->top)++; s->arr[s->top]=val; } } int is_empty(struct stack s) { return s.top==-1; } char pop(struct stack *s) { int val = -1; if(is_empty(*s)) printf("Stack empty"); else { int t = s->arr[s->top]; s->top--; val = t; } return val; } int main() { char string[MAX]; printf("Enter the string:"); fgets(string,MAX-1,stdin); int l = strlen(string);/*fgets adds a new line char*/ string[l-1]='\0'; if(is_palindrome(string)) printf("%s is a palindrome\n",string); else printf("%s is not a palindrome\n",string); return 0; }