Я знаю, что это довольно распространенный вопрос, но все же новый для меня!
Я не понимаю концепцию висящего указателя, гуглюсь и пишу тестовые методы, чтобы найти его.
Мне просто интересно, это свисающий указатель? Так как какой бы пример я не нашел, он возвращал что-то, здесь я пробую нечто подобное
Спасибо!
void foo(const std::string name)
{
// will it be Dangling pointer?!, with comments/Answer
// it could be if in new_foo, I store name into Global.
// Why?! And what is safe then?
new_foo(name.c_str());
}
void new_foo(const char* name)
{
// print name or do something with name...
}
Висячий указатель — это указатель, который указывает на недопустимые данные или на данные, которые больше не являются допустимыми, например:
Class *object = new Class();
Class *object2 = object;
delete object;
object = nullptr;
// now object2 points to something which is not valid anymore
Это может происходить даже в объектах, размещенных в стеке:
Object *method() {
Object object;
return &object;
}
Object *object2 = method();
// object2 points to an object which has been removed from stack after exiting the function
Указатель возвращается c_str
может стать недействительным, если строка впоследствии изменена или уничтожена. В вашем примере вы, кажется, не изменяете его, но поскольку неясно, что вы собираетесь делать const char *name
невозможно знать, безопасен ли ваш код или нет.
Например, если вы храните указатель где-то, а затем соответствующая строка уничтожается, указатель становится недействительным. Если вы используете const char *name
просто в объеме new_foo
(например, в целях печати), тогда указатель останется действительным.
Висячий указатель — это (не NULL) указатель, который указывает на нераспределенную (уже освобожденную) область памяти.
Приведенный выше пример должен быть верным, учитывая, что строка не модифицируется с помощью new_foo.
В качестве стиля я объясняю висячий указатель как «указатель, который все еще существует, даже если объект, на который он указывал, больше не существует».
В вашем случае указатель name
существует в течение более короткого периода, чем объект, на который он указывает. Так что это никогда не болтается.
Внутри обычных классов C ++ указатели в течение очень короткого периода времени болтаются внутри деструкторов. Это потому что delete
заявление до последнего }
деструктора, в то время как сам указатель перестает существовать в последний раз }
, Если вы не хотите беспокоиться об этом, используйте, например, unique_ptr<T>
, T*
указатель будет очень коротко болтаться внутри unique_ptr::~unique_ptr
деструктор, который совершенно безопасен.
Взято из Вот. Хотя, даже если это для C, то же самое для C ++.
Если какой-либо указатель указывает адрес памяти какой-либо переменной, но после того, как какая-то переменная была удалена из этой ячейки памяти, тогда как указатель все еще указывает на эту ячейку памяти. Такой указатель известен как висячий указатель, и эта проблема известна как проблема висячего указателя.
Первоначально
Потом
пример
#include<stdio.h>
int *call();
int main() {
int *ptr;
ptr = call();
fflush(stdin);
printf("%d", *ptr);
return 0;
}
int * call() {
int x=25;
++x;
return &x;
}
Его вывод будет мусором, потому что переменная x является локальной переменной. Его область действия и время жизни находятся в вызове функции, следовательно, после того, как возвращаемый адрес переменной x стал мертвым, а указатель все еще указывает, ptr все еще указывает на это местоположение.
Проблема с висящим указателем и висящим указателем
Если какой-либо указатель указывает адрес памяти какой-либо переменной, но после того, как какая-то переменная была удалена из этой ячейки памяти, тогда как указатель все еще указывает на эту ячейку памяти.
Этот указатель называется висячим указателем, а проблема, которая возникает в то время, называется висячей указателем.
Вот некоторые примеры: Проблема с висящим указателем и висящим указателем