Explore all courses in this category.
Explore all courses in this category.
Nguyễn Đình Cường
0 comment
09 Nov, 2026
Chương trình chạy chậm, và bạn "linh cảm" rằng hàm A là thủ phạm. Bạn mất cả buổi tối ưu hàm A rồi phát hiện tổng thời gian chạy gần như không đổi. Chuyện này xảy ra rất thường xuyên, vì trực giác của lập trình viên về hiệu năng thường sai. Giải pháp là đo trước bằng profiling.
Profiling là quá trình đo xem chương trình dành thời gian (hoặc bộ nhớ) ở đâu: hàm nào được gọi bao nhiêu lần, mỗi lần mất bao lâu, dòng nào tốn nhiều nhất. Kết quả cho bạn bức tranh khách quan để quyết định tối ưu cái gì.
Quy tắc quen thuộc: phần lớn thời gian chạy thường dồn vào một phần nhỏ của code. Tìm ra phần nhỏ đó là chìa khóa.
Cách nhanh nhất cho thử nghiệm sơ bộ:
// JavaScriptconsole.time('xuLyDonHang');processOrders(orders);console.timeEnd('xuLyDonHang');# Pythonimport timestart = time.perf_counter()process_orders(orders)print(f"Mất {time.perf_counter() - start:.3f} giây")Nên chạy nhiều lần và lấy trung bình hoặc trung vị, vì lần đầu thường chậm hơn do khởi tạo, bộ nhớ đệm, và máy có thể đang bận việc khác.
Mỗi ngôn ngữ đều có công cụ:
| Môi trường | Công cụ thường dùng |
|---|---|
| Trình duyệt / web | Tab Performance và Lighthouse trong DevTools |
| Node.js | node --prof, --inspect với Chrome DevTools |
| Python | cProfile, timeit, thư viện line_profiler |
| PHP | Xdebug, Blackfire |
| Java | JFR (Java Flight Recorder), VisualVM |
| Database | EXPLAIN, nhật ký truy vấn chậm |
Ví dụ với Python:
python -m cProfile -s cumtime my_script.pyLệnh này sắp xếp kết quả theo tổng thời gian tích lũy, giúp bạn thấy hàm nào chiếm nhiều nhất.
# Chậm: 1 truy vấn + N truy vấnorders = db.query("SELECT * FROM orders")for order in orders:order.customer = db.query("SELECT * FROM customers WHERE id = ?", order.customer_id)# Nhanh hơn: lấy hết khách hàng cần thiết một lầnorders = db.query("SELECT * FROM orders")ids = list({o.customer_id for o in orders})customers = db.query("SELECT * FROM customers WHERE id IN (...)", ids)Profiling sẽ cho thấy hàng trăm truy vấn nhỏ nhắc lại, dấu hiệu rất rõ của N+1. (Đoạn code trên là minh họa ý tưởng, cú pháp cụ thể tùy thư viện.)
Đo trước, tối ưu sau. Khi có số liệu, bạn tránh được việc tốn công vào chỗ không cần, đồng thời có bằng chứng thuyết phục khi trao đổi với đồng đội. Hãy làm quen với một công cụ profiling cho ngôn ngữ bạn dùng ngay hôm nay.
Để tìm hiểu cách xây dựng ứng dụng nhanh và ổn định, bạn có thể tham khảo các khóa học trên codebem.com.
Nguyễn Đình Cường
0 comment