С++ standard: разыменование NULL-указателя для получения ссылки?
Мне интересно, что говорит о коде С++:
int* ptr = NULL;
int& ref = *ptr;
int* ptr2 = &ref;
На практике результат состоит в том, что ptr2
является NULL, но мне интересно, это просто деталь реализации или это хорошо определено в стандарте?
В разных случаях разыменование указателя NULL должно приводить к сбою, но здесь я разыгрываю его, чтобы получить ссылку, которая реализуется компилятором в качестве указателя, поэтому на самом деле нет никакого разыменования NULL.
Ответы
Ответ 1
Разыменование указателя NULL - это поведение undefined.
Фактически стандарт называет эту точную ситуацию в примечании (8.3.2/4 "Ссылки" ):
Примечание: в частности, нулевая ссылка не может существовать в четко определенной программе, поскольку единственная способом создания такой ссылки было бы привязать ее к "объекту", полученному разыменованием нулевого указателя, что вызывает поведение undefined.
В качестве варианта: когда-то я знаю, что указатель NULL может быть "разыменован" четко определенным образом в качестве операнда оператора sizeof
, потому что операнд sizeof
isn ' t фактически оценивается (так что разыменование никогда не происходит).
Ответ 2
Выделение указателя NULL явно является undefined поведением в стандарте С++, поэтому то, что вы видите, специфично для реализации.
Копирование из 1.9.4 в черновик стандарта С++ 0x (аналогично предыдущим стандартам в этом отношении):
Некоторые другие операции описаны в этом Международном стандарте undefined (например, эффект разыменование нулевого указателя). [Примечание: настоящий международный стандарт не предъявляет никаких требований к поведение программ, содержащих undefined. - конечная нота]
Ответ 3
Разыменование указателя NULL - это поведение undefined. Вы должны проверить, имеет ли значение значение NULL перед разыменованием его.
Ответ 4
Для полноты: http://www.open-std.org/jtc1/sc22/wg21/docs/cwg_active.html#232 конкретно рассказывает об этой проблеме.
Ответ 5
int& ref = *ptr;
Вышеприведенное утверждение на самом деле ничего не делает. Поэтому нет проблем, пока вы не используете ref
(что недопустимо).