Передать по значению в C

Привет, следующий код переносим?

Я просто передаю указатель по значению, и я могу изменить его в вызывающей программе!

void foo(void *p)
{
 void **pp = (void**)p;
 *pp = "hahaha";
}

int main(int argc,char **argv)
{
 void *p = NULL;
 p = &p;
 printf("%p\n",p);
 foo(p);
 printf("%s\n",(char *)p);     // hahaha
 printf("%p\n",p);


return 0;
}

3 ответа

Решение

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

Что вы делаете в основном это:

void foo(void **p)
{
    *p = "hahaha";
}

int main(int argc,char **argv)
{
    void *p = NULL;
    printf("%p\n", &p);
    foo(&p);
    printf("%s\n",(char *)p);     // hahaha
    printf("%p\n", p);
    return 0;
}

с некоторыми добавками и трюками. "Трюки с картами в темноте", я бы сказал, и определенно не очень хорошая идея, чтобы внедрить настоящую программу.

Чтобы фактически ответить на вопрос: да, он должен быть переносимым, потому что стандарт гарантирует, что каждый указатель данных может быть приведен к и из void * без проблем (что вы постоянно делаете в своем коде):

Указатель на void может быть преобразован в или из указателя на любой неполный или тип объекта. Указатель на любой неполный объект или тип объекта может быть преобразован в указатель на void и обратно снова; результат должен сравниваться равным исходному указателю.

(C99, §6.3.2.3.1)

Да, вы можете изменить то, на что указывает указатель, но вы можете сделать это только потому, что указатель на него указывает:

p = &p;

Чтобы ответить на ваш вопрос, да, это портативно; но нет, это вообще не очень хорошая идея.

Вы на самом деле играете с указателями на указатели. Вы по-прежнему передаете указатель по значению, и вы не обманываете компилятор при изменении значения вызывающего. То, что вы изменяете, это просто значение, на которое указывает указатель на указатель.

Не очень хорошая идея для использования в реальной жизни, кроме того, чтобы запутать себя и других программистов.

Другие вопросы по тегам