💻 Exemplos: Capítulo 10: Ponteiros Inteligentes: unique_ptr, shared_ptr e weak_ptr
💻 Exemplos: Capítulo 10: Ponteiros Inteligentes: unique_ptr, shared_ptr e weak_ptr
Especialização em Sistemas com C++ • Demonstrações Práticas Compiláveis
🎯 Objetivo dos Exemplos
Apresentar a gestão moderna de recursos e propriedade de memória com os ponteiros inteligentes da biblioteca padrão (<memory>): propriedade exclusiva com std::unique_ptr (zero overhead de runtime), propriedade compartilhada com contador de referência atômico via std::shared_ptr, e quebra de ciclos de referência cruzada com std::weak_ptr.
1. Código Fonte Completo (main.cpp)
/**
* @file main.cpp
* @brief Gerenciamento de memória com std::unique_ptr, std::shared_ptr e std::weak_ptr em C++20.
*/
#include <iostream>
#include <memory>
#include <string>
class ServicoKernel {
public:
std::string nome;
explicit ServicoKernel(std::string n) : nome(std::move(n)) {
std::cout << "[Kernel] Servico '" << nome << "' criado no Heap." << '\n';
}
~ServicoKernel() {
std::cout << "[Kernel] Servico '" << nome << "' destruido da memoria." << '\n';
}
void processar() const {
std::cout << " -> Executando carga de trabalho no servico: " << nome << '\n';
}
};
// Demonstração de ciclo quebrado com std::weak_ptr
struct NoGrafo;
struct NoGrafo {
std::string id;
std::shared_ptr<NoGrafo> proximo;
std::weak_ptr<NoGrafo> vizinho_fraco; // weak_ptr NÃO incrementa use_count, prevenindo leak!
explicit NoGrafo(std::string i) : id(std::move(i)) {
std::cout << "[Grafo] Vertice '" << id << "' alocado." << '\n';
}
~NoGrafo() {
std::cout << "[Grafo] Vertice '" << id << "' desalocado." << '\n';
}
};
int main() {
std::cout << "=== CAPÍTULO 10: SMART POINTERS MODERNOS EM C++20 ===" << '\n';
// 1. std::unique_ptr com std::make_unique (Propriedade Exclusiva)
std::cout << "\n--- 1. std::unique_ptr e Transferência de Propriedade ---" << '\n';
{
auto servico = std::make_unique<ServicoKernel>("Daemon_Monitoramento");
servico->processar();
// Transferência de posse (Move)
std::unique_ptr<ServicoKernel> outro_dono = std::move(servico);
if (!servico) {
std::cout << "Ponteiro original esvaziado com sucesso via std::move." << '\n';
}
outro_dono->processar();
} // outro_dono sai de escopo -> objeto é destruído automaticamente aqui
// 2. std::shared_ptr e Contador de Referências
std::cout << "\n--- 2. std::shared_ptr e use_count ---" << '\n';
{
std::shared_ptr<ServicoKernel> ref1 = std::make_shared<ServicoKernel>("Gateway_Compartilhado");
std::cout << "Contador de referencias (use_count): " << ref1.use_count() << '\n';
{
std::shared_ptr<ServicoKernel> ref2 = ref1; // Compartilha posse
std::cout << "Novo observador adicionado. use_count: " << ref1.use_count() << '\n';
ref2->processar();
} // ref2 sai de escopo
std::cout << "Apos destruicao do observador. use_count: " << ref1.use_count() << '\n';
} // ref1 sai de escopo -> destruído aqui
// 3. std::weak_ptr para Quebrar Ciclos
std::cout << "\n--- 3. std::weak_ptr para Prevenção de Referências Circulares ---" << '\n';
{
auto noA = std::make_shared<NoGrafo>("Nodo_Alpha");
auto noB = std::make_shared<NoGrafo>("Nodo_Beta");
noA->proximo = noB;
noB->vizinho_fraco = noA; // Ligação fraca segura
if (auto lockA = noB->vizinho_fraco.lock()) {
std::cout << "Acesso com sucesso ao vizinho fraco: " << lockA->id << '\n';
}
} // Ambos os nós saem de escopo e são 100% destruídos sem vazamento de memória
return 0;
}
2. Instruções de Compilação e Execução
# Compilação com GCC / Clang
g++ -std=c++20 -Wall -Wextra -O2 main.cpp -o app_smart_ptr
./app_smart_ptr
# Compilação com MSVC
cl /std:c++20 /EHsc /W4 /O2 main.cpp /Fe:app_smart_ptr.exe
.\app_smart_ptr.exe
3. Saída Esperada no Terminal
=== CAPÍTULO 10: SMART POINTERS MODERNOS EM C++20 ===
--- 1. std::unique_ptr e Transferência de Propriedade ---
[Kernel] Servico 'Daemon_Monitoramento' criado no Heap.
-> Executando carga de trabalho no servico: Daemon_Monitoramento
Ponteiro original esvaziado com sucesso via std::move.
-> Executando carga de trabalho no servico: Daemon_Monitoramento
[Kernel] Servico 'Daemon_Monitoramento' destruido da memoria.
--- 2. std::shared_ptr e use_count ---
[Kernel] Servico 'Gateway_Compartilhado' criado no Heap.
Contador de referencias (use_count): 1
Novo observador adicionado. use_count: 2
-> Executando carga de trabalho no servico: Gateway_Compartilhado
Apos destruicao do observador. use_count: 1
[Kernel] Servico 'Gateway_Compartilhado' destruido da memoria.
--- 3. std::weak_ptr para Prevenção de Referências Circulares ---
[Grafo] Vertice 'Nodo_Alpha' alocado.
[Grafo] Vertice 'Nodo_Beta' alocado.
Acesso com sucesso ao vizinho fraco: Nodo_Alpha
[Grafo] Vertice 'Nodo_Alpha' desalocado.
[Grafo] Vertice 'Nodo_Beta' desalocado.