问题
void push(stack *head, int valuee)
{
if(head->next==NULL && head->value==-1)
{
head->value = valuee;
printf("First element %d inserted\n",valuee);
}
else
{
stack *temp = new stack;
temp->value = valuee;
temp->next = head;
head = temp;
printf("Element %d inserted\n",valuee);
}
}
First element is inserted properly but when i continue inserting elements, none of the elements are inserted after the first one. Read somewhere that i have to pass pointer to pointer of stack but I did this same thing during a postfix infix question and it was working over there. Help me with this problem here. Many thanks for any help in advance
Previous example of infix postfix which was working fiine
void push(char c, stack *node)
{
stack *B = (stack *)malloc(sizeof(stack));
if (node->next == NULL)
{
node->next = B;
B->value = c;
B->next =NULL;
}
else
{
B->next = node->next;
node->next = B;
B->value = c;
}
}
回答1:
You can change the function like this
stack* push(stack *head, int valuee)
//return void to stack *
return head;
//In the end return the new head
and it will work. Call push like this
head = push(head,value);
回答2:
Why u need pointer to pointer ?
You want to modify the contents of a pointer so if you pass only a pointer to the function it is pass by copy so you can not modify it actually.
In the case of infix-prefix scenario you must have not modified the string you would have read it only, so a pointer to pointer is not required.
回答3:
For this line of code in the else
portion of the if
statement:
head = temp;
Your intention is to mutate head
, in other words, change what head
is pointing to. However, pointers are passed in as values, just like other variables. In other words, suppose I call the push
function somewhere else. For simplicity, suppose I call it in the main
function, something like this:
int main()
{
stack *headOfStack = new stack;
// suppose this next push triggers the else portion of the push code
push(headOfStack, 6);
}
Now, after the push(headOfStack, 6);
statement has been executed, your intention is to expect headOfStack
to point to a new "stack node" which contains the value 6
. Now, headOfStack
is a pointer to a variable of type stack. It stores a memory address. You can think of a memory address as some integer. When we call push
, we are copying the content of headOfStack
(the content of headOfStack
is a memory address) into the local variable head
of the push
function. Therefore, when:
head = temp;
is executed, we are assigning the contents of temp
to head
. What is temp
? It is a pointer to a variable of type stack
. In other words, the value of temp
is a memory address. So head = temp;
simply assigns the memory address contained in temp
to the local variable head
. The local variable head
in the push
function and our headOfStack
variable in the main
function are two completely different variables with different memory addresses. If my explanation has been clear so far, this means that when we modify head
in the push
function, the headOfStack
variable in main
is totally unchanged.
What you want to do in this case is:
void push(stack **headPtr, int valuee)
{
// this will get the actual pointer we are interested in
stack *head = *headPtr;
if(head->next==NULL && head->value==-1)
{
head->value = valuee;
printf("First element %d inserted\n",valuee);
}
else
{
stack *temp = new stack;
temp->value = valuee;
temp->next = head;
// mutation is done here
*headPtr = temp;
printf("Element %d inserted\n",valuee);
}
}
And its usage, using our fictional main
function:
int main()
{
stack *headOfStack = new stack;
// notice the use of &headOfStack instead of headOfStack
push(&headOfStack, 6);
}
Just remember that pointers store memory addresses, and that pointers are just variables, and they have memory addresses as well. To mutate a pointer (change what a pointer is pointing to), just pass in its memory address to the function.
Hope that helps!
EDIT for new edit in question
void push(char c, stack *node)
{
stack *B = (stack *)malloc(sizeof(stack));
if (node->next == NULL)
{
node->next = B;
B->value = c;
B->next =NULL;
}
else
{
B->next = node->next;
node->next = B;
B->value = c;
}
}
For this version of push
, what it's doing is essentially:
If
node->next == NULL
, sonode
has no successor, then set its successor to a newly allocated node with valuec
Otherwise,
node->next != NULL
andnode
has some successor. Then we would set the newly allocated nodeB
tonode
's successor, and setnode
's original successor to beB
's successor. Or in other words, it splices a new nodeB
(with valuec
) in betweennode
and its successor.
I am finding it quite hard to explain this, but a simple explanation is, this push
does not change what node
is pointing to. At nowhere did we show intention to mutate node
. I think the stuff involving B
should be quite understandable, so let's focus on the node->next
assignments.
I am assuming that the stack
is a struct that looks something like this:
struct stack {
char value;
struct stack *next;
};
Now, suppose in our main
function, we have a stack
:
stack x;
Notice that x
is not a pointer. I think we all agree that doing x.value = something
and x.next = something
will mutate those fields.
Now, let's look at this:
stack *y = malloc(sizeof(struct stack));
We know that y
stores an address to an actual struct stack
(the actual struct stack
is at *y
). So y->value = something
and y->next = something
will mutate those fields.
So hopefully you can see why the node->value
assignments work. Essentially node
contains an address to an actual struct stack
, whose value is *node
. By pointer syntax, node->value
and node->next
assignments will change the contents of node
.
Not a very good explanation I know. But just write more code. Pointers confused the hell out of me when I was first starting out with C. I think that these days, I can still be confused by 2 or 3 layers of indirection, and I've encountered some very nasty pointer bugs. Just practice more... some day you will really get it. I know it's what they all say, but it's true.
来源:https://stackoverflow.com/questions/20613273/push-of-stack-not-inserting-the-new-value-c