Ссылки и указатели

Тема дорожной карты · Modern C++ Developer

Ссылки и указатели — два механизма косвенного доступа к данным в C++, с разной семантикой и применением. Указатель (T*) — переменная, хранящая адрес другого объекта; может быть nullptr, может быть переназначен, поддерживает арифметику. Ссылка (T&) — alias на существующий объект; не может быть null, инициализируется один раз и не переназначается, не поддерживает арифметику. Современный C++ предпочитает ссылки указателям там, где null невозможен — это выражено в типе и компилятор гарантирует safety.

Как это работает

Указатель: int* p = &x;p хранит адрес x, доступ через *p, поля — p->field. Возможна арифметика: p + 1 — следующий int в памяти. Может быть nullptr (всегда проверяйте перед dereferencing). C++11 ввёл smart pointers (unique_ptr, shared_ptr, weak_ptr) — RAII-обёртки, владеющие памятью. Ссылка: int& r = x;r — псевдоним для x, все операции с r действуют на x. Lvalue reference (T&) — обычная ссылка, привязывается к именованным объектам. Rvalue reference (T&&, C++11) — привязывается к временным/выражениям, основа move semantics. Forwarding reference (T&& в template-контексте) — универсальная, выводится в lvalue или rvalue по deduction правилам.

Когда применять

Передавайте в функции по const T& для read-only доступа к большим объектам (избегаем копий). По T& — для модификации параметра без указателя. По T* — когда параметр опциональный (может быть nullptr), для arrays с длиной, для C-API совместимости. Используйте std::unique_ptr<T> вместо raw T* для owning resources, std::shared_ptr<T> для shared ownership (но осторожно — оверхед reference counting + cycles), std::weak_ptr<T> для observers без удержания. Raw pointer оставьте для non-owning observers и performance-критичных мест.

Типичные ошибки

Dangling pointer — указатель на освобождённую память (use-after-free), classical undefined behavior. Возврат ссылки на local variable — даёт dangling reference. delete на указатель, не от new — undefined. Double-delete — UB. Использование raw new/delete вместо smart pointers в современном коде. Циклические shared_ptr — leak (используйте weak_ptr). Передача больших объектов по value, когда нужна const T& — копирование стоит CPU.

Связанные понятия

Полезные ресурсы