Newbie question stack implementation

S

Sandie C

Hi All
newbie here
i am trying to push integers to a stack and when the input is complete, I
would like to pop them and print them out as they come off the stack.
TIA
Sandie
code here

#include <stdio.h>

#define MAXSTACK 1000

int push(int );

int pop (int );

int stack[MAXSTACK]; /* define stack size*/

int count; /* count for checking if stack full, data for the data to move
around the stack*/

void main(void){

int data;


printf("please input Data type (-1) to end data input\n"); /* print to
screen instructions*/

while(data !=(-1)){

scanf("%d", &data); /* look for first data*/



push(data); /*push data to stack*/



}

while (data){


pop(data);

printf("reversed is %d ",data);

}

}









push(int val){

if (count>=MAXSTACK) return -1; /*stack full*/

else

stack[count++]=val;

return val;

}

pop(int *val){

if (count==0) return -1;

*val=stack[--count];

return *val;



}
 
D

dandelion

Sandie C said:
Hi All
newbie here

We were all newbies once, so don't worry 'bout that.
i am trying to push integers to a stack and when the input is complete, I
would like to pop them and print them out as they come off the stack.
TIA
Sandie
code here

#include <stdio.h>

#define MAXSTACK 1000

int push(int );

It is nice to provide a name for the argument such that the user may gain
some insight into the semantics of that argument.

int push(int value);
int pop (int );

int pop(int* value);

Since that's the way you define it below.
int stack[MAXSTACK]; /* define stack size*/

Actually the stack size is defined by "#define MAXSTACK 1000". Here, the
stack itself is defined.
int count; /* count for checking if stack full, data for the data to move
around the stack*/

This is usually called "top-of-stack" (or something simular).
void main(void){

main() is _required_ to return an 'int'

int main(void)

or

int main(int argc, char* argv[])
int data;


printf("please input Data type (-1) to end data input\n"); /* print to
screen instructions*/

while(data !=(-1)){

scanf("%d", &data); /* look for first data*/



push(data); /*push data to stack*/

What happens if someone enters '-1' ?
}

while (data){

What happens if someone enters '0'?
pop(data);

printf("reversed is %d ",data);

}

}

push(int val){

Eventhough 7ou have declared a prototype, the definition should have a
return type defined
aswell.

int push(int value)
if (count>=MAXSTACK) return -1; /*stack full*/

the "count" variable is only incremented by 1, ever. So

if(count == MAXSTACK)

would suffice.
else

stack[count++]=val;

return val;

}


pop(int *val){

int pop(int* val)

Besides, this does not match the prototype given.
if (count==0) return -1;

*val=stack[--count];

return *val;
}

The main problem I see with your code is that you do not distinguish between
valid results and
error conditions. Entering either '-1' or '0' in the scanf would break your
code.

With a stack, there are two main error conditions to worry about:

A) Stack overflow (no more stack space left). and

B) Stack underflow (stack is empty).

A is only a problem when pushing data, B is only a problem when popping
data.

So if yiu were to define

#define SUCCESS 1
#define FAILURE 0

static int top_of_stack = 0;

you could write

int push(int value)
{
if(top_of_stack < MAXSTACK)
{
stack[top_of_stack++] = value;
return SUCCES;
}

return FAILURE;
}

and

int pop(int* value)
{
if(top_of_stack >= 0)
{
*value = stack[--top_of_stack];
return SUCCES;
}

return FAILURE;
}

and you would be certain wether or not one of the operations fails or
succeeds, whatever the user enters.

....
while(SUCCESS == pop(&value))
{
printf("Value = %d\n", value);
}
....

Conclusion:

* Consider the possible errors which may arise from an algorithm and think
of some way to indicate
that error without possible confusion with a legitimate (successfull)
value being returned.

HTH, dandelion.
 
J

Jens.Toerring

Sandie C said:
i am trying to push integers to a stack and when the input is complete, I
would like to pop them and print them out as they come off the stack.
#include <stdio.h>
#define MAXSTACK 1000
int push(int );
int pop (int );
int stack[MAXSTACK]; /* define stack size*/
int count; /* count for checking if stack full, data for the data to move
around the stack*/
void main(void){

main() must always return an int, so make that

int main( void )
int data;
printf("please input Data type (-1) to end data input\n"); /* print to
screen instructions*/
while(data !=(-1)){

Problem here is that the first time round 'data' has an uninitialized
value which could be chanc be -1. To avoid this you will have to ini-
tialize 'data' to a value (better something else than -1) before you
use it's value.
scanf("%d", &data); /* look for first data*/
push(data); /*push data to stack*/

Here's a problem with the stack becoming full. In that case push()
returns -1 but you don't do anything with that return value, so
you won't notice the stack getting full. You only stop reading
when the user enters -1. You need here

data = push( data );

to be able to find out if the stack became full.
while (data){
pop(data);
printf("reversed is %d ",data);
}

There are several problems here with the way you try to get back the
values from the stack, see below for more details. But even if that
would work correctly you still would have a problem with this loop -
it only stops if 'data' is 0, but pop() seems to return -1 when the
stack is empty. So, unless you had 0 stored on the stack (in which
case the loop would end prematurely) the loop will run forever!

Finally, you need a return statement here since main() must return an
int, so use e.g.

return 0;
push(int val){

Since push() is supposed to return an int you better have here

int push( int val )

if you want your program also to work according to the new C99 standard.
if (count>=MAXSTACK)
return -1; /*stack full*/
else
stack[count++]=val;
return val;
}
pop(int *val){

Beside the missing 'int' before the function name here's also the
problem that this doesn't match the function declaration above,
where you told the compiler that the function would take an int
argument - here you say that the fucntion expects an int pointer.
This also doesn't match the way you use pop() in main(), where
you pass an int to the function.
if (count==0) return -1;
*val=stack[--count];
return *val;
}

This looks a bit strange. Why do you use a pointer at all? And why
don't you use the return value of pop() in main()? A simpler (and
hopefully working) version of that function would be

int pop( void ) {
if ( count == 0 )
return -1;
return stack[ --count ];
}

and you need to call it in main() as

data = pop();

Of course, there's a design problem with this program - the dealing
with -1, which is a completely legal value to store on the stack.
You can store it (but only as the very last element) but you can't
get it back since it's impossible to distinguish from the "stack is
empty" condition...
Regards, Jens
 
J

Jonathan Bartlett

pop(data);

This needs to be "pop(&data);"

Previous posters are right, though, using pointers is pointless (no pun
intended, but good cheesy humor anyway), you might as well just skip the
pointer and pass it back as a value.

Jon
 
K

Keith Thompson

Problem here is that the first time round 'data' has an uninitialized
value which could be chanc be -1. To avoid this you will have to ini-
tialize 'data' to a value (better something else than -1) before you
use it's value.

Better yet, use a do-while loop rather than a while loop.

A while loop:

while (condition) { statements; }

is useful when the body of the loop may be executed zero or more times
(zero times if the condition is false to begin with). In this case,
you always want to execute the body of the loop at least once, so it
makes more sense to test the termination condition at the bottom:

do {
statements;
} while (condition);

I find that while loops are more common than do-while loops, but this
is one case where a do-while actually makes more sense.

Incidentally, if the first entered value is -1, indicating that
there's no data, you'll have an empty stack to begin with. Make sure
you handle that case correctly.

You should also consider using a different way to mark the end of the
user's input. -1 could be a valid value, but you're using it as an
end marker. You should eventually consider using EOF. (But I'd get
this version working first.)
 
J

Joe Wright

Sandie said:
Hi All
newbie here
i am trying to push integers to a stack and when the input is complete, I
would like to pop them and print them out as they come off the stack.
TIA
Sandie
code here

#include <stdio.h>

#define MAXSTACK 1000

int push(int );

int pop (int );

int stack[MAXSTACK]; /* define stack size*/

int count; /* count for checking if stack full, data for the data to move
around the stack*/

void main(void){

int data;


printf("please input Data type (-1) to end data input\n"); /* print to
screen instructions*/

while(data !=(-1)){

scanf("%d", &data); /* look for first data*/



push(data); /*push data to stack*/



}

while (data){


pop(data);

printf("reversed is %d ",data);

}

}









push(int val){

if (count>=MAXSTACK) return -1; /*stack full*/

else

stack[count++]=val;

return val;

}

pop(int *val){

if (count==0) return -1;

*val=stack[--count];

return *val;



}
Hi Sandie. What do you think of this?

#include <stdio.h>
#include <stdlib.h>

#define SD 10 /* stack depth */

int stack[SD]; /* the stack */
int sp = 0; /* index into the stack. zero == empty */

/*
push() and pop() return -1 on failure.
this precludes -1 as valid value on the stack.
*/
int push(int data) {
int ret;
if ((ret = -(sp == SD)) == 0)
stack[sp++] = data;
return ret;
}

int pop(void) {
int ret;
if ((ret = -(sp == 0)) == 0)
ret = stack[--sp];
return ret;
}

int main(void) {
char line[80];
int data = 0;
printf("Please input up to %d integers, one per line. Input -1
to end.\n", SD);
while (1) {
fgets(line, sizeof line, stdin);
data = atoi(line);
if (data == -1) break;
if (push(data) == -1) {
puts("Stack is Full.");
break;
}
}
puts("The stack holds..");
while ((data = pop()) != -1)
printf("%d\n", data);
return 0;
}
 
T

Taran

Joe said:
Sandie said:
Hi All
newbie here
i am trying to push integers to a stack and when the input is complete, I
would like to pop them and print them out as they come off the stack.
TIA
Sandie
code here

#include <stdio.h>

#define MAXSTACK 1000

int push(int );

int pop (int );

int stack[MAXSTACK]; /* define stack size*/

int count; /* count for checking if stack full, data for the data to move
around the stack*/
void main(void){
int data;
printf("please input Data type (-1) to end data input\n"); /* print to
screen instructions*/
while(data !=(-1)){
scanf("%d", &data); /* look for first data*/
push(data); /*push data to stack*/
}
while (data){
pop(data);
printf("reversed is %d ",data);
}

In addition to what has been discussed in the this thread its better if
you have a function int IsEmpty() for the stack. So while popping off
the stack you can safely pop without worrying about the underflow by
just using this function. Moreover this completes the functionalities
of the stack and also this looks elegant than comparing count to
MAXSTACK.
Similarly for IsFull().
Though at first this might look as unnecessary, but still this makes
code easier to understand and maintainable. What if tomorrow you
change the way stack is represented from array to linked list say.


/**/ while(!IsEmpty()) //while popping
/**/ {
/**/ /whatever you code was doing/
/**/ }

/**/ int IsEmpty(void)
/**/ {
/**/ if (count==0)
/**/ return EMPTY;
/**/ else
/**/ return NOT_EMPTY;
/**/ }

/**/ int IsFull(void)
/**/ {
/**/ if (count==(MAXSTACK-1))
/**/ return FULL;
/**/ else
/**/ return NOT_FULL;
/**/ }

/**/ int pop(void)
/**/ {
/**/ int ret_val;
/**/ if(!IsEmpty())
/**/ ret_val=stack[count--];
/**/ else
/**/ ret_val=ERROR;
/**/ return ret_val;
/**/ }

/**/ int push(int data)
/**/ {
/**/ int ret_val;
/**/ if(!IsFULL())
/**/ stack[count++]=data;
/**/ ret_val=SUCCESS;
/**/ else
/**/ ret_val=ERROR;
/**/ return ret_val;
/**/ }

where EMTPY and NOT_EMPTY are #defines.
#define EMPTY 1
#define NOT_EMPTY 0
#define FULL 1
#define NOT_FULL 0

HTH
Regards,
Taran
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Similar Threads


Members online

Forum statistics

Threads
473,997
Messages
2,570,239
Members
46,827
Latest member
DMUK_Beginner

Latest Threads

Top