Tối ưu hóa bộ nhớ với PHP

BinlerdevBinlerdev
4 min read

Phần mở đầu

Chào bạn! Khi bạn viết code PHP, có thể bạn từng gặp tình huống: chương trình càng lớn càng chậm, hoặc báo lỗi hết bộ nhớ. Vậy thì tối ưu bộ nhớ (memory optimization) là một kỹ năng rất quý giá mà bạn nên biết ngay từ đầu — không chỉ để code chạy mượt hơn, tiết kiệm máy chủ mà còn để bạn hiểu rõ hơn cách PHP hoạt động bên trong.


Nội dung chính

Chúng ta sẽ khám phá từng “tips” theo thứ tự từ dễ đến nâng cao:


1. Dùng unset() để giải phóng bộ nhớ

Giải thích dễ hiểu: Khi bạn khai báo biến rồi không dùng nữa, bộ nhớ vẫn “níu” lại cho đến khi hết thời gian chạy script. unset() là cách nói PHP: “Hey, cho mình trả lại bộ nhớ nhé!”

Ví dụ thực tế:

  • Trong trang web bán hàng, sau khi xuất danh sách sản phẩm, bạn có thể unset($products) để giải phóng bộ nhớ.
  • Trong chương trình xử lý file lớn, sau khi finish xử lý chunk, ta unset($chunk).
$data = range(1, 1000000); // mảng dữ liệu lớn
// ... xử lý ...
unset($data); // giải phóng bộ nhớ

2. Tránh lưu toàn bộ dữ liệu lớn trong bộ nhớ

Giải thích: Không nên tải hết dữ liệu (ví dụ từ database) vào memory cùng lúc — dễ gây tràn. Thay vào đó, đọc theo từng phần (chunk/pagination).

Ví dụ:

  • Lấy từng dòng từ cơ sở dữ liệu và xử lý dần.
  • Gộp dữ liệu n page nhỏ và xử lý từng lần.
$stmt = $pdo->query("SELECT * FROM large_table");
while ($row = $stmt->fetch(PDO::FETCH_ASSOC)) {
    // xử lý từng dòng
}

3. Ép PHP thu gom rác bằng gc_collect_cycles()

Giải thích: PHP có garbage collector (GC) tự động dọn những biến không dùng nữa, nhưng bạn có thể gọi thủ công để dọn triệt để hơn, đặc biệt là trong các script chạy lâu (CLI, cron…).

gc_enable(); // kích hoạt nếu chưa có
// ... xử lý nhiều dữ liệu ...
gc_collect_cycles(); // gọi dọn rác thủ công

4. Theo dõi bộ nhớ với memory_get_usage()

Giải thích: Bạn không thể tối ưu nếu không biết chỗ nào tốn bao nhiêu. Hàm này giúp bạn đo bộ nhớ đang dùng ngay tại thời điểm gọi.

echo "Memory hiện tại: " . memory_get_usage() . " bytes";

5. Tối ưu vòng lặp và đệ quy

Giải thích: Mỗi vòng lặp hay lời gọi đệ quy đều tạo thêm biến, làm đầy bộ nhớ dần. Có thể dùng biến đơn giản hoặc chuyển sang cách lặp (iterative) để tiết kiệm.

Ví dụ:

  • Thay vì đệ quy đếm từ 1 đến 1000, bạn dùng for đơn giản.

6. Sử dụng Generators khi xử lý tập dữ liệu lớn

Giải thích: Generator không cần giữ tất cả dữ liệu trong memory — nó “yield” từng phần một, tiết kiệm bộ nhớ cực kỳ hiệu quả.

function getLargeDataSet() {
    for ($i = 0; $i < 1000000; $i++) {
        yield $i;
    }
}

foreach (getLargeDataSet() as $item) {
    // xử lý từng item
}

7. Tải lớp tự động với spl_autoload_register()

Giải thích: Bạn không cần load tất cả file lớp (class) từ đầu — chỉ load khi dùng thông qua cơ chế autoloading. Tránh tình trạng “nạp linh tinh” nhiều code không dùng.

spl_autoload_register(function ($class) {
    include $class . '.php';
});

8. Tối ưu mảng và đối tượng

Giải thích: Mảng PHP khá “nặng” vì lưu rất nhiều metadata. Nếu dữ liệu ít, bạn có thể dùng object hoặc SplFixedArray cho hiệu quả hơn.

Cảnh báo: SplFixedArray có thể tiết kiệm bộ nhớ nhưng khó thao tác hơn mảng bình thường.


9. Dùng công cụ profiling (Xdebug, Blackfire)

Giải thích: Khi code phức tạp, bạn cần đếm xem chỗ nào tốn bộ nhớ nhiều nhất. Tools như Xdebug hay Blackfire giúp bạn đo và đưa ra cách tối ưu cụ thể.


Phần tương tác nhẹ

Bạn thử nghĩ xem:

  • Mình nên dùng unset() ở đâu trong chương trình xử lý file lớn?
  • Tình huống nào nên dùng generator thay vì array thường?

Phần kết

Tóm lại:

  • Bắt đầu với những thứ đơn giản: unset(), đọc dữ liệu từng phần, dùng generator.
  • Khi code phát triển lớn hơn, dùng autoload, profiling để giữ hiệu năng tốt.
  • Kinh nghiệm cá nhân: “Việc tối ưu memory không chỉ giúp chương trình chạy nhanh và văn minh, mà còn khiến bạn hiểu sâu hơn cách PHP vận hành.”

Tài liệu tham khảo

  • Bài gốc của Khouloud Haddad Amamou – Medium, Jan 16, 2025 (Medium)
  • dev.to – cách PHP quản lý bộ nhớ và garbage collector (DEV Community)
  • Zend – dùng generators để tiết kiệm bộ nhớ khi lặp hoặc gọi đệ quy (zend.com)

Chúc bạn học vui và tự tin khám phá sâu hơn PHP nhé!

0
Subscribe to my newsletter

Read articles from Binlerdev directly inside your inbox. Subscribe to the newsletter, and don't miss out.

Written by

Binlerdev
Binlerdev