Complete Stack implementation in C - c

I have been asked to do a stack implementation. I need to the following functions;
Push
Pop
isFull
isEmpty
peek
Display the whole array
This is what I wrote.
#include <stdio.h>
#include <stdlib.h>
#define SIZE 5
/* Stack Structure */
struct stack
{
int s[SIZE];
int top;
}st;
int main()
{
int option;
printf("+-------------------------------------+\n");
printf("1.Push\n2.Pop\n3.Check whether the stack is full\n4.Check whether the stack is empty\n5.Check the Top Element\n6.Display the Stack\n7.Exit\n");
printf("+-------------------------------------+\n");
printf("Enter Choice:\t");
scanf("%d", &option);
while(option == -99)
{
switch(option)
{
case 1:
push();
break;
case 2:
pop();
break;
case 3:
isFull();
break;
case 4:
isEmpty();
break;
case 5:
peek();
break;
case 6:
display();
break;
case 7:
printf("You Exited from the program");
break;
}
}
return 0;
}
/*Function to add an element to the stack*/
void push ()
{
int num;
if (st.top == (SIZE - 1))
{
printf ("Stack is Full\n");
}
else
{
printf ("Enter the element to be pushed\n");
scanf ("%d", &num);
st.top ++;
st.s[st.top] = num;
}
}
/*Function to delete an element to the stack*/
int pop()
{
int num;
if (st.top == -1)
{
printf ("Stack is Empty\n");
return st.top;
}
else
{
num = st.s[st.top];
printf ("Popped element is = %d", st.s[st.top]);
st.top --;
}
return (num);
}
/*Function to Check whether the stack is full*/
void isFull()
{
if(st.top == SIZE - 1)
printf("Stack is Full");
else
printf("Stack has %d elements", st.top - 1);
}
/*Function to Check whether the stack is Empty*/
void isEmpty()
{
if(st.top == -1)
printf("Stack is Empty");
else
printf("Stack has %d elements", st.top - 1);
}
/* Function to display the top element*/
void peek()
{
printf("Top most element: \t%d", st.s[st.top]);
}
/* Function to display the stack*/
void display ()
{
int i;
if (st.top == -1)
{
printf ("Stack is empty\n");
}
else
{
printf ("\n The status of the stack is \n");
for (i = st.top; i >= 0; i--)
{
printf ("%d\n", st.s[i]);
}
}
printf ("\n");
}
0 errors, 11 warnings are shown.
But when I run the programme it ends after asking the choice.
output:
+-------------------------------------+
1.Push
2.Pop
3.Check whether the stack is full
4.Check whether the stack is empty
5.Check the Top Element
6.Display the Stack
7.Exit
+-------------------------------------+
Enter Choice: 1
Process returned 0 (0x0) execution time : 6.304 s
Press any key to continue.
I really need to have it done. It is one of my assignments. Please help me and thank you very much for your time. :-)

You're exiting because you are entering an option that's between 1 and 7, but your while loop is checking for -99. So the while loop gets skipped and you exit.
I'm guessing what you actually want to do is keep prompting the user for actions until they exit. Try considering what functionality you actually want looped over in your program.
Also don't be afraid to put print statements in your code and trace the flow line by line. That will help you a lot with debugging.
Best of luck on the assignment!

Of course process stops working when you choose number. The program works while variable option is equal to -99, which never happens, because your choice is always between numbers 1-7.
The problem may be solved by writing option >= 1 && option <=7 in while loop.

Related

My static stack code is not running properly

#include <stdio.h>
#include <stdlib.h>
#define N 5
int stack[N];
int top = -1;
void push()
{
int x;
printf("Enter data");
scanf("%d", &x);
if (top == N - 1)
{
printf("Overflow");
}
else
{
top++;
stack[top] = x;
}
}
void pop()
{
int item;
if (top == -1)
{
printf("Underlfow");
}
else
{
item = stack[top];
top--;
printf("%d", item);
}
}
void peek()
{
if (top == -1)
{
printf("Underflow");
}
else
{
printf("%d", stack[top]);
}
}
void display()
{
int i;
for (i = top; i >= 0; i--)
{
printf("%d\n", stack[top]);
}
}
int main()
{
int ch;
do
{
printf("\n1.push\n2.pop\n3.peek\n4.display");
scanf("%d", &ch);
switch (ch)
{
case 1:
push();
break;
case 2:
pop();
break;
case 3:
peek();
break;
case 4:
display();
break;
case 5:
exit(0);
break;
default:
printf("invalid key pressed");
break;
}
} while (ch != 0);
return 0;
}
So it is the code which i wrote following a tutorial on youtube
In push function if i excced the array size which is 5 it will still take values instead of printing overflow and when i try to display it, it will display all values same
before i was geting a error at getch(); while using void main() so i change it to int main() and used return 0; it is still not working.
So it is the code which i wrote following a tutorial on youtube In push function if i excced the array size which is 5 it will still take values instead of printing overflow and when i try to display it, it will display all values same
Your logic is to always allow you to enter values. But they are not inserted in the stack (and instead "Overflow" is printed). This is because you ask for the value before checking if the stack is full. Just make the test before, and put the scan inside the else part of the if statement.
void push()
{
int x;
if (top == N - 1) {
/* put \n chars at end of lines in output statements
* like this ---vv */
printf("Overflow\n");
} else {
printf("Enter data ");
fflush(stdout);
scanf("%d", &x);
top++;
stack[top] = x;
}
}
The problem of printing always the top of the stack is basically that you print stack[top], instead of stack[i], in the display() function loop. You should use this code instead.
void display()
{
int i;
for (i = top; i >= 0; i--)
{
/* use i here --------------v */
printf("%d: %d\n", i, stack[i]);
}
}
This is not an error, but will save you trouble in the future. Get used to put the \n char at the end of the printing format, instead of at the beginning, if you are going to print a complete line. I understand that you want to avoid it when prompting the user, so you avoid it. But the stdio library uses buffering, so it doesn't print things when you ask it for, so it delays the printing of strings (on an interactive session) until you do printf a '\n' char (if the output device is a terminal), or before reading from stdin (also, if the input device is a terminal). This can make a mess if you print your strings without the trailing '\n'. And more, if you redirect your output, this means using a pipe (so, it is not a terminal). Then, no output is done until the buffer fills completely (meaning over 10kb of data, usually 16kb on modern unix/linux systems) You will see your program doing things while no output has been output, and you won't know why.
You don't use getch() in your code, so i think you have posted a different version of the code you are talking about.
My code, after edition, leads to:
#include <stdio.h>
#include <stdlib.h>
#define N 5
int stack[N];
int top = -1;
void push()
{
if (top == N - 1) {
/* no overflow yet, not if we check beforehand :) */
printf("Stack full, cannot push()\n");
} else {
int x;
printf("Enter data ");
fflush(stdout); /* to flush the output (no \n at end) */
scanf("%d", &x);
top++;
stack[top] = x;
printf("Push: %d to position %d\n", x, top);
}
}
void pop()
{
if (top == -1) {
/* the appropiate message is stack empty, no underflow has
* occured yet. We are preventing it */
printf("Stack empty, cannot pop()\n");
} else {
int item = stack[top];
printf("Pop: %d from pos %d\n", item, top);
top--;
}
}
void peek()
{
if (top == -1) {
/* no underflow yet, we are preventing it */
printf("Stack empty, cannot peek()\n");
} else {
printf("Peek: %d on pos %d\n", stack[top], top);
}
}
void display()
{
int i;
printf("Stack contents:\n");
for (i = top; i >= 0; i--) {
printf("> %d: %d\n", i, stack[i]);
}
}
int main()
{
int ch = 5; /* so we exit if no valid input is made in scanf() */
do {
printf("1.push\n"
"2.pop\n"
"3.peek\n"
"4.display\n"
"5.exit\n");
scanf("%d", &ch);
switch (ch) {
case 1:
push();
break;
case 2:
pop();
break;
case 3:
peek();
break;
case 4:
display();
break;
case 5:
break;
default:
printf("Input invalid option\n");
break;
}
} while (ch != 5); /* option 5 is to exit */
return 0;
}

How Can I Pass a Menu Function Int Value Back To Main To Access Other Menu Functions Using Switch Statement?

I'm doing this for part of a school project and I am so lost and this is only the beginning of it. Our professor wants us to have 4 menu functions. Each menu has options to access other functions within the program. First, we are asked to have the program state if we would like to start or quit. That's no problem. My problem is when I run the main menu function and select an option I cannot get my choice to return to main to run the switch case to access the other menus. Right now I have all the other menus saying "coming soon..." just so I know I am getting it right. I'll add more once I get past this part. This is my first post here so I apologize if this is a lot of code to post. I greatly appreciate any help. Thank you.
#include <stdio.h>
#include <stdlib.h>
int main()
{
//declare all working variables: mOption, FManOption, COption...etc...
int MOption = 0;
int FManOption = 0;
int FOption = 0;
int COption = 0;
int userChoice = 0;
int n = mainMenu();
switch(n)
{
case 1: while(FManOption != 3)
{
FManOption = FishermanMenu();
switch(FManOption)
{
case 1: //get a fisherman
//count fisherman
break;
case 2: //prompt for a ssn, validate, search
//if found display everything about this fisherman
break;
case 3: //hit any key to go back to main menu
//reset FManOption
break;
default: "error!";
}//end switch(FManOption)
}//end while(FManOption != 3)
break;
default: printf("error");
}
return 0;
}
int mainMenu()
{
int option = 0;
printf("-------Welcome to the Fishing Tournament Main Menu!-------\n\n");
do
{
printf("1 - Fisherman menu\n");
printf("2 - Fish menu\n");
printf("3 - Tournament(Catch) menu\n");
printf("4 - Close Tournament (determine winner)\n");
printf("5 - Quit Program\n\n");
printf("Please select a menu option: ");
if (scanf("%d", &option) != 1) /* check scanf() return value for input errors */
{
/* handle input error */
return -1;
}
} while (option < 1 || option > 5); /* check the range of option ( 1 - 5) */
return option; /* finally return the final correct option */
}
int FishermanMenu()
{
printf("Coming soon...");
/*
-1-Register fisherman
-2-Search fisherman
-3-Go back to main menu
*/
//FManOption
}//end Fisherman Menu
Your mainMenu() function doesn't return anything other than 0, in addition you ignore the return value in main, when you call mainMenu(); (this shouldn't even compile btw), this is probably what you are looking for,
int mainMenu(void)
{
int option = 0;
printf("-------Welcome to the Fishing Tournament Main Menu!-------\n\n");
do
{
printf("1 - Fisherman menu\n");
printf("2 - Fish menu\n");
printf("3 - Tournament(Catch) menu\n");
printf("4 - Close Tournament (determine winner)\n");
printf("5 - Quit Program\n\n");
printf("Please select a menu option: ");
if (scanf("%d", &option) != 1) /* check scanf() return value for input errors */
{
/* handle input error */
return -1;
}
} while (option < 1 || option > 5); /* check the range of option ( 1 - 5) */
return option; /* finally return the final correct option */
}
int main(void)
{
int n = mainMenu(); /* save the result to n */
/* your code */
return 0;
}

switch case not working with character value if i input char value the switch doesn't encounter default and starts linfinite loop

---------- > ## Heading ## > when i input a character as an input default case of switch doesn't encounter and loop started > infinite times > > > enter code here
#include <stdio.h>
#include <stdlib.h>
#include <conio.h>
void create();
void display();
void search();
struct node {
int data;
struct node* link;
};
struct node* head;
int main()
{
int value;
while (1) {
printf("Enter Correct Choice :- \n");
printf("Enter 1 to Create Linklist :- \n");
printf("Enter 2 to Display Linklist :- \n");
printf("Enter 3 to Search Linklist :- \n");
printf("Enter Your Choice Here _________ ");
scanf(" %d", &value);
switch (value) {
case 1:
create();
break;
case 2:
display();
break;
case 3:
search();
break;
default:
printf("Error !! Wrong Choice :- \n");
break;
}
}
return 0;
}
TL;DR- Always check the return value of scanf() for success.
In case of a non-numeric character input, the format specifier %d does not find a match, and no input is consumed (i.e., the invalid input remains in the input buffer). Thus, the switch body executes, most likely it does not find a match with any existing case statement, so the default case statement(s) get executed, and control goes back to while loop.
Then, due to the presence of the invalid input in the buffer (and not getting consumed), the above phenomena keeps on repeating.
The major problem is, in case of scanf() failure, the value of variable value remains uninitialized and indeterminate. It does not construct a well-defined program.
Couple of things:
Always initialize local variables.
Always check for success of scanf() before using the returned value, if you have to use scanf(). For better use fgets() to take user input.
In case of failure of input using scanf(), clean up the input buffer before trying to read next input.
The break causes the program to exit the switch case but not the while. To wxit the while as well you should do something like this:
#include <stdio.h>
#include <stdlib.h>
int main()
{
int value;
int done = 0;
while (!done) {
printf("Enter Correct Choice :- \n");
printf("Enter 1 to Create Linklist :- \n");
printf("Enter 2 to Display Linklist :- \n");
printf("Enter 3 to Search Linklist :- \n");
printf("Enter Your Choice Here _________ ");
scanf(" %d", &value);
switch (value) {
case 1:
printf("do stuff\n");
break;
case 2:
printf("do stuff\n");
break;
case 3:
printf("do stuff\n");
break;
default:
printf("Error !! Wrong Choice :- \n");
done = 1;
break;
}
}
return 0;
}
Here I used a variable initialized to 0 which indicates that the operation is not completed yet. When it's time to exit, the variable is set to 1, which causes the program to exit the while loop
Also, always remember to check the return value of printf(), to avoid possible errors
There is no break condition for while().
#include <stdio.h>
#include <stdlib.h>
#include <conio.h>
void create();
void display();
void search();
struct node {
int data;
struct node* link;
};
struct node* head;
int main()
{
int value = 1;
while (value) {
printf("Enter Correct Choice :- \n");
printf("Enter 1 to Create Linklist :- \n");
printf("Enter 2 to Display Linklist :- \n");
printf("Enter 3 to Search Linklist :- \n");
printf("Enter 0 to exit :- \n");
printf("Enter Your Choice Here _________ ");
scanf(" %d", &value);
switch (value) {
case 1:
create();
break;
case 2:
display();
break;
case 3:
search();
break;
default:
printf("Error !! Wrong Choice :- \n");
break;
}
}
return 0;
}
if a non valid integer is enter for scanf(" %d", &value); value is not set and the invalid input is not flush => scanf will never block nor update value
you need to check scanf returns 1 (you read 1 value) and if not to flush the invalid input for instance reading all the line
so you can replace
scanf(" %d", &value);
switch (value) {
...
}
by
if (scanf("%d", &value) != 1) {
puts("invalid input");
while ((value = getchar()) != '\n') {
if (value == EOF) {
puts("EOF, exit");
exit(-1);
}
}
}
else {
switch(value) {
...
}
}
of course you can also manage the invalid input in your default case forcing an invalid value :
if (scanf("%d", &value) != 1) {
while ((value = getchar()) != '\n') {
if (value == EOF) {
puts("EOF, exit");
exit(-1);
}
}
value = -1; /* any value except 1,2 or 3 */
}
switch(value) {
...
}
Out of that you have no option to stop the execution, you can do :
...
puts("Enter 4 to exit :-);
...
switch (value) {
...
case 4:
exit(0);
...
}
I belive your intention is to run the program as long as "0" is not entered, but ter is no case for "0". also when we have scanf for %d and entering a "char" instead scanf will not read the char from buff. data on value will not get changed and it will keep printing existing data. (garbage if we enter invalid data first time itself, or any entered data.)
used fgets to read the input data, and do a scanf from buf, even when data is incorrect we are clearing the std input. so program will not get in to a infinite loop with scanf failure.
initilised "value = 0"
added case for "0".
scanf is replaced with fget +sscanf
#include <stdio.h>
#include <stdlib.h>
int main()
{
int value = 0;
char buff[256] = {0};
while (1) {
value = -1;
printf("Enter Correct Choice :- \n");
printf("Enter 1 to Create Linklist :- \n");
printf("Enter 2 to Display Linklist :- \n");
printf("Enter 3 to Search Linklist :- \n");
printf("Enter Your Choice Here _________ ");
fgets(buff, 255, stdin);
sscanf(buff, "%d", &value);
switch (value) {
case 1:
//create();
printf("case : 1\n");
break;
case 2:
//display();
printf("case : 2\n");
break;
case 3:
//search();
printf("case : 3\n");
break;
case 0 :
printf("case : 0 : Exiting program\n");
return 0;
default:
printf("Error !! Wrong Choice :- %d\n", value);
break;
}
}
return 0;
}

Stack Pop program in c, returning wrong output everytime

I am a beginner in programming. I just made this program in c language for popping elements from Stack. Firstly, I defined function, then scanned a stack and then used a menu for popping elements. But the output is "The stack is empty" everytime. Can you spot the mistake? It will be of great help.
/* Program to Pop elements from a given stack*/
#include<stdio.h>
#include<conio.h>
#define MAX_SIZE 20
int stack[MAX_SIZE],top=NULL;
int pop() //function define
{
int x;
if(top==NULL)
return(NULL);
else
{
x=stack[top];
top=top-1;
return(x);
}
}
main() //program initialization
{
int c,i,x;
clrscr();
printf("Enter the size of stack:");
scanf("%d",&top);
printf("Enter %d elements of stack from top to bottom:",top);
for(i=top;i>0;i--)
scanf("%d",stack[i]);
//Pop element from stack
while(1)
{
printf("1.Enter 1 to Pop element from stack\n");
printf("2.Enter 2 to Print Stack\n");
printf("3.Enter 3 to Exit\n");
scanf("%d",&c);
switch(c)
{
case 1:
{
x=pop();
if(x!=NULL)
printf("\nThe number poped is: %d\n",x);
else
printf("\nThe stack is empty!!");
break;
}
case 2:
{
if(top==NULL)
printf("stack is empty!!\n");
else
{
printf("stack is\n");
for(i=top;i>0;i--)
printf("%d\n",stack[i]);
}
break;
}
case 3:
{
exit(0);
break;
}
default:
{
printf("Wrong input\n");
}
printf("\n");
}
getch();
}
}
scanf("%d",stack[i]); - this line which fills in the stack should be fixed to scanf("%d",&stack[i]);
scanf should receive the address(es) of the parameter(s) to be able to modify it (them). Please check the scanf documentation for more details and options.
Also please verify the return value of scanf as it is explained here: how do we test the return values from the scanf() function?

Why is my static stack not working?

static stack implementation
this is also not deleting according to the lifo principle
static stack implementation:
it is not taking name for the second time
this is the new code now tell me why is it not working
please help
typedef struct student {
char name[20];
int roll;
int age;
} mystruct;
#define size 40
int top;
static mystruct s[size];
void push()
{
if (top == size - 1) {
printf("\noverflow"); //
} else {
printf("\nenter the name of the student");
gets(s[top].name);//not taking name for d 2 time
printf("\nenter the roll number");
scanf("%d", &s[top].roll);
printf("\nenter the age of the student");
scanf("%d", &s[top].age);
++top;
}
}
void pop()
{
if (top == -1)
{
printf("\nunderflow");
} else {
printf("%s", s[top].name);
printf("%d", s[top].roll);
printf("%d", s[top].age);
printf("\npopped");
--top;
}
}
void display()
{
int i;
if (top == -1) {
printf("\nstack is empty");
} else {
for (i = top; i > 0; i--) {
printf("\nthe name of the student is%s", s[top].name);
}
printf("\nthe roll no of the student is%d", s[top].roll);
printf("\nthe age of the student is%d", s[top].age);
}
}
main()
{
top = -1;
char ch;
while (1) {
printf("\nwelcome to static stack menu");
printf("\n1.PUSH\n2.POP\n3.DISPLAY\n0.EXIT");
printf("\nplease enter your choice\n");
ch = getche();
if (ch == '0') {
break;
}
switch (ch) {
case '1':
push();
break;
case '2':
pop();
break;
case '3':
display();
break;
default:
printf("choice not valid");
break;
}
}
}
The first problem I noticed was that top is initialized to -1. Trying to access the member data of s[top] when top is initialized to -1 will result in unpredictable behavior.
I would suggest changing the line
top = -1;
to
top = 0;
That changes the basic assumption you have made in push, pop, and display about when the stack is empty and when it is full. Instead of checking if ( top == -1 ), you have to now check if (top == 0 ). Instead of checking if ( top == size - 1 ), you have to now check if ( top == size ).
In pop, you have to use top-1 instead of top.
The for loop in display is not scoped correctly. You need to use:
for (i = top-1; i >= 0; i--) {
printf("\nthe name of the student is %s", s[i].name);
printf("\nthe roll no of the student is %d", s[i].roll);
printf("\nthe age of the student is %d", s[i].age);
}
Also, reading the options for the menu and reading the subsequent input is little bit tricky.
After you read the menu option, you have to make sure that you eat up all the input until the next newline. Otherwise, gets() will read everything after your menu option until the end of the line. If you typed 1 for the menu and then typed Return/Enter, the name will be automatically accepted as "\n". Hence, I suggest the lines:
printf("\nwelcome to static stack menu");
printf("\n1.PUSH\n2.POP\n3.DISPLAY\n0.EXIT");
printf("\nplease enter your choice\n");
ch = fgetc(stdin);
/* Skip till the end of line is read. */
while ( fgetc(stdin) != '\n' );
Also, after you read the age of the object, you have to eat everything up to the newline. Otherwise, the newline character is read in as the choice for the next menu option.
scanf("%d", &s[top].age);
/* Skip till the end of line is read. */
while ( fgetc(stdin) != '\n' );
Here's the fully working file. I have replaced gets by fgets and getche by fgetc.
#include <stdio.h>
#include <string.h>
typedef struct student {
char name[20];
int roll;
int age;
} mystruct;
#define size 40
int top;
static mystruct s[size];
void push()
{
if (top == size) {
printf("\noverflow"); //
} else {
printf("\nenter the name of the student: ");
fgets(s[top].name, 20, stdin);//not taking name for d 2 time
// The newline character is part of s[top].name when fgets is
// finished. Remove that.
s[top].name[strlen(s[top].name)-1] = '\0';
printf("\nenter the roll number: ");
scanf("%d", &s[top].roll);
printf("\nenter the age of the student: ");
scanf("%d", &s[top].age);
/* Skip till the end of line is read. */
while ( fgetc(stdin) != '\n' );
++top;
}
}
void pop()
{
if (top == 0)
{
printf("\nunderflow");
} else {
printf("%s, ", s[top-1].name);
printf("%d, ", s[top-1].roll);
printf("%d", s[top-1].age);
printf("\npopped");
--top;
}
}
void display()
{
int i;
if (top == 0) {
printf("\nstack is empty");
} else {
for (i = top-1; i >= 0; i--) {
printf("\nthe name of the student is %s", s[i].name);
printf("\nthe roll no of the student is %d", s[i].roll);
printf("\nthe age of the student is %d", s[i].age);
}
}
}
main()
{
top = 0;
char ch;
while (1) {
printf("\nwelcome to static stack menu");
printf("\n1.PUSH\n2.POP\n3.DISPLAY\n0.EXIT");
printf("\nplease enter your choice\n");
ch = fgetc(stdin);
/* Skip till the end of line is read. */
while ( fgetc(stdin) != '\n' );
if (ch == '0') {
break;
}
switch (ch) {
case '1':
push();
break;
case '2':
pop();
break;
case '3':
display();
break;
default:
printf("choice, %c, not valid", ch);
break;
}
}
}
You need to change getche() to getchar()
Note: getche() is a non-standard function.
Maybe this will be useful http://www.delorie.com/djgpp/doc/libc/libc_385.html
Pay attention to implementation note:
"If you can detect the situation when one of the conio functions is called for the very first time since program start, you could work around this problem by calling the gppconio_init function manually"
or just replace it with getchar(). And there meaned conio included.

Resources