Học C++ từ Cơ Bản đến Nâng Cao

Website tự học lập trình C++ miễn phí, thực chiến, dễ hiểu

Quản lý bộ nhớ nâng cao

1. Smart Pointer

  • std::unique_ptr: sở hữu đơn, không thể sao chép.
  • std::shared_ptr: đếm tham chiếu, nhiều đối tượng cùng sở hữu.
  • std::weak_ptr: tránh vòng lặp sở hữu với shared_ptr.

#include 
std::unique_ptr up = std::make_unique(10);
std::shared_ptr sp1 = std::make_shared(20);
std::shared_ptr sp2 = sp1;
std::weak_ptr wp = sp1;
    
Ưu điểm:
  • Tự động giải phóng bộ nhớ giúp tránh memory leak.
  • Dễ quản lý và an toàn hơn new/delete thủ công.
Nhược điểm:
  • Dễ gây lỗi nếu dùng sai kiểu (ví dụ dùng shared_ptr không cần thiết).
  • Có chi phí hiệu năng (đặc biệt với shared_ptr vì quản lý ref-count).
Khi nào nên dùng:
  • Dùng unique_ptrkhi bạn chắc chắn chỉ cần một owner.
  • Dùng shared_ptr khi cần chia sẻ ownership giữa nhiều phần của chương trình.
  • Dùng weak_ptr để tránh vòng lặp tham chiếu giữa các shared_ptr.

2. RAII – Resource Acquisition Is Initialization

RAII là kỹ thuật đảm bảo tài nguyên (file, memory...) được cấp phát và thu hồi đúng cách bằng cách gắn với vòng đời object.


class FileWrapper {
    FILE* f;
public:
    FileWrapper(const char* name) { f = fopen(name, "r"); }
    ~FileWrapper() { if (f) fclose(f); }
};
    
🔒 Lưu ý: RAII đặc biệt quan trọng trong C++ vì không có GC như Java. Nên dùng RAII cho mọi tài nguyên như file, lock, socket...

3. Leak Detector

  • Valgrind: công cụ phân tích runtime chạy trên Linux. Nó giám sát chương trình trong quá trình thực thi để:
    • Phát hiện bộ nhớ cấp phát mà không giải phóng (memory leak).
    • Truy cập ngoài vùng nhớ hợp lệ (invalid read/write).
    • Sử dụng vùng nhớ đã giải phóng (use-after-free).
  • AddressSanitizer (ASan): trình phân tích thời gian chạy được tích hợp trong compiler như GCC/Clang.
    • Phát hiện lỗi tràn bộ đệm (buffer overflow), lỗi truy cập use-after-free.
    • Nhanh hơn Valgrind, phù hợp tích hợp vào CI/CD hoặc debug local nhanh.
    • Không cần cài thêm tool ngoài, chỉ cần biên dịch lại với flag -fsanitize=address.

// Dùng với gcc/clang
$ g++ -fsanitize=address -g main.cpp -o app
$ ./app
    
📌 Lưu ý: Trong dự án lớn, bạn nên chạy Valgrind hoặc ASan định kỳ trong CI/CD để phát hiện sớm lỗi bộ nhớ khó debug.

← Quay lại C++ Nâng Cao