Middle
How does shared_ptr work in C++?
sobes.tech AI
Answer from AI
shared_ptr is a smart pointer that implements shared resource ownership semantics. It holds a pointer to the object and a pointer to a control block.
Control block contains:
- Strong reference count.
- Weak reference count.
- User-defined deleter, if specified.
- User-defined allocator, if specified.
- Pointer to the stored object (the same as stored in the
shared_ptr).
Working principle:
- Creation: When the first
shared_ptrpointing to an object is created, a control block is created, and reference counters are initialized: strong — 1, weak — 0.std::shared_ptr<int> ptr1 = std::make_shared<int>(10); // Creates an int object and a control block - Copying: When copying a
shared_ptr, the strong reference count in the control block increases by 1.std::shared_ptr<int> ptr2 = ptr1; // Increases the strong reference count - Assignment: When assigning a
shared_ptr, the old resource's reference count is decremented, and the new resource's count is incremented.std::shared_ptr<int> ptr3; ptr3 = ptr1; // Decrements old resource's count, increments new resource's count - Deletion: When a
shared_ptris destroyed (e.g., goes out of scope), the strong reference count is decremented.{ std::shared_ptr<int> ptr4 = ptr1; // Increases the strong reference count // ptr4 goes out of scope } // Decrements the strong reference count - Resource release: When the strong reference count reaches zero, the resource (the object pointed to by
shared_ptr) is deleted using the specified deleter (ordeleteby default). - Control block release: The control block is released when both counters (strong and weak) reach zero.
Advantages:
- Automatic memory management for shared resources.
- Safety against double deletion.
- Support for user-defined deleters.
Disadvantages:
- Cyclic references can lead to memory leaks (solved with
weak_ptr). - Slight overhead due to the control block and atomic operations on counters.
- Thread safety of operations on the
shared_ptritself (copying, assignment, changing the stored pointer), but not on the object it points to.