проблема с указателями в C - PullRequest
       0

проблема с указателями в C

3 голосов
/ 07 сентября 2010

Я никогда не умел играть с указателями на C. Но на этот раз я хотел бы попросить вас помочь решить мои проблемы с указателями. У меня есть функция, чтобы поместить значение в стек.

void StackPush(stackT *stackPtr, stackElementT element){

 stackNodeT* node = (stackNodeT *) malloc(sizeof(stackNodeT));  

 if (node == NULL){
  fprintf(stderr, "Malloc failed\n");
  exit(1);
 } else {                                   
  node->element = element;
  node->next = StackEmpty(stackPtr)? NULL : *stackPtr; 
  *stackPtr = node;
 }
}

Если я изменю последнюю строку на stackPtr = & node; эта функция не работает. Мой вопрос почему? В чем разница между * stackPtr = node; и stackPtr = & узел;

Любая помощь будет оценена.

Ответы [ 4 ]

3 голосов
/ 07 сентября 2010

stackT *stackPtr определяет stackPtr как указатель на stackT. Вызывающая функция передает объект stackT этой функции.

Теперь *stackPtr = node; изменяет значение, на которое указывает указатель stackPtr, тогда как stackPtr = &node; изменяет локальное значение самой переменной-указателя.

stackT *mystack = createStack();
//mystack points to an empty stack

StackPush1(mystack, elem1);//stackpush1 uses *stackPtr = node;
//mystack points to the node with elem1

StackPush2(mystack, elem2);//stackpush2 uses stackPtr = &node;
//the function updates its local copy, not the passed variable
//mystack still points to the elem1
//node with elem2 is not accessible and is a memory leak.

допустим, у нас есть int k = 4; если я введу что-то вроде * ptr = k; в «основном» теле (не внутри функции) результаты должны совпадать с ptr = & k;?

Не совсем. Запустите следующий код и убедитесь сами:

int k = 4;
//declare a pointer to int and initialize it
int *ptr1 = malloc(sizeof(int));
//now ptr1 contains the address of a memory location in heap

//store the current value into the address pointed to by ptr1
*ptr1 = k; /* this line will fail if we hadn't malloced 
              in the previous line as it would try to 
              write to some random location */

//declare a pointer to int 
int *ptr2;
//and assign address of k to it
ptr2 = &k;

printf("Before \n*ptr1 = %d *ptr2 = %d\n", *ptr1, *ptr2);
//change the value of k
k = 5;
printf("After  \n*ptr1 = %d *ptr2 = %d\n", *ptr1, *ptr2);

Оставьте комментарий, если вам нужно больше разъяснений.

2 голосов
/ 07 сентября 2010
*stackPtr = node;

Это разыменовывает stackPtr и устанавливает объект, на который указывает, значение node.

stackPtr = &node;

Это изменяет указатель stackPtr, чтобы указывать на указатель node, которыйвыделяется в стеке.

По сути, в первом случае вы меняете объект, на который ссылается указатель (называемый referent указателя), но сам указатель остается неизменным.Во втором случае вы меняете указатель на другое.

1 голос
/ 07 сентября 2010

Как только stackPtr передается (по значению), это локальная (автоматическая) переменная, и ее изменение не влияет на автоматические переменные вызывающего. Тем не менее, когда вы делаете:

*stackPtr = node;

вы модифицируете объект, который он указывает на.

0 голосов
/ 07 сентября 2010

* stackPtr = узел

заставляет stackPtr указывать на то, что вы используете malloc.

* stackPtr = & node

заставляет stackPtr указывать на адрес локальной переменной, который, скорее всего, будет недействительным, когда вы вернетесь из этой функции.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...