Страница 1 из 2
указатель на локальную переменную
Добавлено: 26 сен 2004, 13:11
versus
привет
подскажи плз, что то я запутался
вот на такой код, gcc, естественного говорит ворнинг про использоване адреса локальной переменной
Код: Выделить всё
#include <stdio.h>
#include <unistd.h>
char* some_function()
{
char str[1024] = "hello world!";
return str;
}
int main()
{
char* ptr;
ptr = some_function();
// usleep((long)1E3) /* подождать пока локальная переменная удалится
printf("%s\n", ptr);
return 0;
}
понятно, что код этот совсем некорректен, в том смысле что лучше было бы использовать malloc и free, но все таки не смотря на ворнинг к большому для меня удивлению программа все таки печатает "hello world!".. как это понимать? разве память занимаемая str не должна удалится после завершения some_function? и тогда при попытке printf получится segfault... однако вместо этого нормальный вывод. Почему?
Добавлено: 26 сен 2004, 13:37
Absurd
Этот код работает случайно, потому что компилятору нет резона занулять локальные переменные, и они там остаются по старым адресам.
Но программист должен думать, что там уже ничего нет.
Добавлено: 26 сен 2004, 13:42
Hup
Я так полагаю. что строка просто висит в памяти... Нужно посмотреть Турбо дебагером дамб памяти
Добавлено: 26 сен 2004, 14:09
versus
Absurd, спасибо.
Добавлено: 27 сен 2004, 18:14
Kolinus
Absurd прав. Как говорят мои преподаватели - это типичная ошибка второкурсника.
Если после вызова some_function обЪявить еще какую-нить переменную и проинициализировать ее то ptr скорее всего "свалится" с нужной тебе строки
Добавлено: 28 сен 2004, 11:19
Absurd
В принципе, если есть большая нужда возвращать строчку типа const char * или char * (хуже), то можно массив str[] объявить как
статический
Код: Выделить всё
const char* some_function()
{
static char str[1024] = "hello world!";
return str;
}
В таком случае строка str будет жить не в стеке, а в области данных, где ее никто не будет трогать.
Добавлено: 28 сен 2004, 16:40
Kolinus
Еще есть способ - после того как сделал вызов такого метода, сразу вызывать strcpy в локальную переменную функции main - но это опять же если только сильно надо

Добавлено: 29 сен 2004, 17:43
Hawk
Удивительно но факт, следующий код так же будет полностью корректным -
Код: Выделить всё
const char* some_function()
{
char* str = "hello world!";
return str;
}
в этом случае строчка "hello world!" становится статической константой и существует даже до вызова функции не говоря уж о возвращении из неё. В отличии от char str[1024] = "hello world!" когда создается локальный массив с который копируется эта статическая строчка
Добавлено: 29 сен 2004, 18:24
Eugie
Hawk, неудивительно: по-сути ты просто возвращаешь адрес на константную строку (литерал), неважно, что объявленный локально - он все равно фиксирован в памяти
Добавлено: 29 сен 2004, 18:35
Hawk
Eugie и я о том же