Cách Ultralytics tăng tốc model YOLO trên chip bạn yêu thích
Tìm hiểu cách chip, bộ nhớ và xung nhịp ảnh hưởng đến tốc độ YOLO, cũng như cách lượng tử hóa, hợp nhất toán tử và cắt tỉa giúp model chạy nhanh trên CPU, GPU và thiết bị biên.
Francesco Mattioli33 phút đọc
Tại Ultralytics, chúng tôi tạo ra các model thị giác máy tính; về cơ bản, chúng tôi dạy máy tính nhìn! Hãy hình dung những model này như các công thức toán học khổng lồ. Chúng bao gồm các phép toán (chúng tôi gọi là layer) và một lượng lớn con số được gọi là trọng số.
Các model Ultralytics YOLO xử lý hình ảnh đúng như bản chất của chúng: các mảng số! Mỗi pixel thực chất chỉ là các giá trị màu, tức lượng Đỏ, Lục và Lam (do đó là RGB) tại từng điểm cấu thành hình ảnh. Chúng tôi gọi các mảng số này là "tensor" vì nghe thú vị hơn nhiều so với "ma trận đa chiều", mà cụm này lại nghe thú vị hơn nhiều so với "các con số xếp chồng lên nhau thành từng lớp".
Khi bạn đưa một hình ảnh vào model, hình ảnh sẽ bắt đầu một hành trình kỳ thú xuyên qua mạng. Hãy hình dung tensor lướt qua hết layer này đến layer khác, được biến đổi, tích chập và xử lý bằng toán học theo cách tuyệt đẹp nhất. Hãy nghĩ về quá trình này như một bữa tiệc khiêu vũ, nơi các con số hòa trộn và tương tác để trích xuất bản chất giúp phân biệt mèo với mèo hay xe hơi với xe hơi. Chúng tôi gọi quá trình này là trích xuất đặc trưng.
Đầu ra là gì? Thêm nhiều con số nữa! Những con số có ý nghĩa. Trong các tác vụ phát hiện, chúng cho bạn biết chính xác vật thể nằm ở đâu trong hình ảnh và có thể đó là vật thể gì. "Này, có 95% khả năng đó là một con chó ở tọa độ (x, y)!" Chúng tôi gọi quá trình kỳ diệu này là suy luận.
Trước khi các model có thể phát huy tác dụng, chúng cần đến trường; chúng cần được huấn luyện. Giai đoạn huấn luyện là lúc mọi thứ trở nên căng thẳng.
Trong quá trình huấn luyện, mỗi khi đưa một hình ảnh cho mạng, chúng ta không chỉ nhận được câu trả lời. Chúng ta thực hiện thêm hai việc rất nặng. Thứ nhất, tính toán mức độ sai lệch của mạng (chúng tôi gọi là loss, về cơ bản là khoảng cách đến tâm đích). Thứ hai, và đây là phần quan trọng, cập nhật từng con số (hay trọng số) trong mạng dựa trên loss đó. Hãy hình dung việc này như điều chỉnh hàng nghìn núm vặn nhỏ cùng lúc, trong đó mỗi lần điều chỉnh được tính toán để giúp mạng chính xác hơn.
Về cơ bản, chúng ta huấn luyện mạng bằng cách sửa lỗi: mỗi lỗi dạy mạng biết điều KHÔNG nên làm, và chúng ta tinh chỉnh tất cả trọng số để khi gặp lại hình ảnh tương tự, mạng sẽ tiến gần hơn đến câu trả lời đúng. Nói cách khác, mạng học bằng cách được điều chỉnh theo hướng đúng, từng lỗi một, cho đến khi bắt đầu đưa ra dự đoán chính xác.
Chúng ta đang nói đến bao nhiêu con số? Model YOLO11n nhỏ nhắn của chúng tôi có vài triệu tham số. Còn YOLO11x? Model mạnh mẽ đó có hơn 50 triệu tham số! Nhiều tham số hơn đồng nghĩa với khả năng mã hóa nhiều chi tiết hơn, giống như sự khác biệt giữa vẽ bằng bút sáp và có cả bảng màu của họa sĩ.
Trong quá trình suy luận, số lượng tham số trở nên vô cùng quan trọng. Chạy một mạng có 3 triệu tham số cũng như chạy bộ quanh khu nhà. Chạy một mạng có 50 triệu tham số? Giống như chạy marathon trong khi tung hứng những ngọn đuốc đang cháy.
Vậy chính xác thì tính toán LÀ gì? Tất cả việc xử lý số liệu này thực sự diễn ra như thế nào? Làm sao để tăng tốc? Và "tối ưu hóa tính toán" thực sự có nghĩa là gì?
Cách chip thực hiện phép toán#
Tính toán diễn ra trên chip. Những ô silicon nhỏ này về cơ bản là những lâu đài cát có tổ chức nhất vũ trụ. Mọi thao tác máy tính thực hiện, mọi phép cộng, mọi phép so sánh, mọi câu lệnh "nếu điều này thì làm điều kia", đều được khắc vật lý vào silicon. Trên chip có các mạch vật lý thực sự nằm ở những khu vực cụ thể, chuyên dùng để cộng số; những mạch khác phụ trách các phép toán logic. Cứ hình dung như một thành phố thu nhỏ, nơi mỗi khu vực chuyên về một kiểu toán học khác nhau.
Điều này có thể nghe kỳ quặc, ngay cả với bạn nếu bạn là nhà khoa học máy tính. Đó là vì suốt 40 năm qua, chúng ta đã xây hết layer trừu tượng này đến layer trừu tượng khác, giống như món lasagna công nghệ cao chất cao đến mức giờ không còn nhìn thấy lớp đĩa dưới cùng. Chúng ta đã đơn giản hóa mọi thứ đến mức ngày nay, hầu hết lập trình viên không biết tính toán thực sự diễn ra như thế nào trong silicon. Không phải lỗi của họ, mà là do thiết kế!
Hãy bóc tách từng layer. Xét đoạn mã Python đơn giản này:
x = 1
if x == 1:
y = x + 1Chúng ta tạo một biến x, gán giá trị 1 cho biến, rồi nếu x bằng 1 (tiết lộ trước: đúng là vậy), chúng ta tạo y có giá trị bằng x cộng 1. Ba dòng. Thật dễ.
Nhưng đây mới là phần thú vị. Giữa ba dòng tưởng chừng vô hại đó và các electron thực sự di chuyển trong silicon là ÍT NHẤT bốn lớp chuyển đổi đồ sộ (thực tế còn nhiều hơn, nhưng bốn lớp là đủ để minh họa). Hãy cùng tôi khám phá hành trình đầy choáng ngợp này:
Layer 1: Python → Bytecode Trước tiên, Python đọc mã của bạn và biên dịch thành thứ gọi là bytecode, một ngôn ngữ trung gian mà máy tính dễ xử lý hơn nhưng sẽ khiến bạn hoa mắt nếu cố đọc.
Layer 2: Bytecode → Mã máy Trình thông dịch Python (như CPython) nhận bytecode đó và dịch thành mã máy, tức các chỉ dẫn thực tế mà bộ xử lý hiểu được. Tại đây, câu lệnh thanh nhã "if x == 1" biến thành thứ kiểu như "LOAD register, COMPARE register, JUMP if zero flag set."
Layer 3: Mã máy → Microcode Cú ngoặt bất ngờ! Các bộ xử lý hiện đại thậm chí không thực thi mã máy trực tiếp. Chúng phân rã mã máy thành microcode, những phép toán còn nhỏ hơn để các thành phần bên trong chip xử lý. Một lệnh "ADD" đơn lẻ có thể trở thành nhiều vi thao tác.
Layer 4: Microcode → Điện tử vật lý Cuối cùng, chúng ta đến với silicon. Những vi thao tác này kích hoạt các tín hiệu điện thực sự chạy qua transistor. Hàng tỷ công tắc nhỏ bật tắt, electron nhảy múa qua các đường dẫn được thiết kế cẩn thận, và bằng cách nào đó, như có phép màu, 1 + 1 thành 2.
Mỗi layer tồn tại để che giấu độ phức tạp khủng khiếp của layer bên dưới. Giống như búp bê lồng của Nga, ngoại trừ mỗi con búp bê dùng một ngôn ngữ hoàn toàn khác nhau, còn con nhỏ nhất thực sự được tạo nên từ tia sét mắc kẹt trong cát.
Trớ trêu thay, ba dòng Python đó có thể kích hoạt HÀNG TRIỆU lần chuyển mạch của transistor. Nhưng nhờ các lớp trừu tượng này, bạn không cần phải nghĩ đến những điều đó. Bạn chỉ cần viết "y = x + 1" và tin rằng phép màu đang diễn ra đâu đó sâu bên trong silicon.
Kiến trúc#
Mọi thao tác đều được triển khai vật lý trong silicon, và thao tác xảy ra Ở ĐÂU trên chip hoàn toàn phụ thuộc vào cấu trúc liên kết của chip. Giống như quy hoạch thành phố, nhưng dành cho electron. Bộ cộng nằm ở đây, bộ nhân nằm ở kia, và tất cả cần giao tiếp với nhau hiệu quả.
Trên thị trường có hàng trăm loại chip khác nhau, mỗi loại được thiết kế cho những mục đích khác nhau. Điều gì tạo nên sự khác biệt giữa chúng? Cấu trúc liên kết: cách các phép toán được bố trí và triển khai trong miền vật lý. Đây là điều chúng ta gọi là kiến trúc, và có rất nhiều loại:
- x86 (Intel và AMD) - Bậc tiền bối của điện toán máy tính để bàn, phức tạp nhưng mạnh mẽ
- ARM - Cung cấp sức mạnh cho điện thoại và ngày càng nhiều laptop, được thiết kế để tiết kiệm năng lượng
- RISC-V - Kẻ nổi loạn mã nguồn mở, ngày càng phổ biến ở khắp nơi
- PowerPC - Con quái vật của IBM, từng được dùng trong máy chơi game và hiện vẫn phổ biến trong các hệ thống nhúng
- MIPS - Kiến trúc được giới học thuật ưa chuộng, đơn giản và thanh nhã
- SPARC - đóng góp của Sun Microsystems (nay thuộc Oracle) cho lĩnh vực điện toán hiệu năng cao
- Kiến trúc GPU (lõi CUDA của NVIDIA, RDNA của AMD) - Những cỗ máy xử lý song song mạnh mẽ
Mỗi kiến trúc không chỉ bố trí các transistor khác nhau mà còn sử dụng một ngôn ngữ khác. Các lớp trừu tượng mà chúng ta dùng để gửi chỉ dẫn đến những máy này hoàn toàn khác nhau. Giống như phải viết chỉ đường cho ai đó, nhưng tùy chiếc xe của họ mà bạn có thể cần viết bằng tiếng Pháp, tiếng Quan Thoại hoặc bằng điệu nhảy biểu cảm.
Nhịp đập của silicon#
Nhiên liệu cho chip của chúng ta là electron, dòng điện chạy vào chip và cung cấp năng lượng cho việc tính toán. Nhưng chỉ năng lượng thôi thì chưa đủ. Để chip thực sự hoạt động và di chuyển dữ liệu qua cấu trúc liên kết phức tạp, mọi thứ phụ thuộc vào một thành phần then chốt: xung nhịp. Xung nhịp giúp electron chạy qua các đường dẫn cụ thể vào những thời điểm cụ thể. Nếu không có nó, bạn chỉ có silicon được cấp điện nhưng chẳng làm gì.
Hãy tưởng tượng việc điều phối một buổi biểu diễn quy mô lớn, nơi hàng tỷ thành phần cần chuyển động đồng bộ hoàn hảo. Không có nhịp dẫn, mọi thứ sẽ hỗn loạn. Đó chính xác là vai trò của xung nhịp đối với bộ xử lý. Một tinh thể dao động với tần số cực kỳ ổn định, phát ra các xung điện hàng tỷ lần mỗi giây.
Khi nghe nói "bộ xử lý 3.5 GHz", GHz (gigahertz) là tốc độ xung nhịp, tương đương 3,5 tỷ nhịp mỗi giây. Mỗi nhịp được gọi là một chu kỳ xung nhịp, đơn vị thời gian cơ bản trong điện toán.
KHÔNG CÓ GÌ xảy ra giữa các chu kỳ xung nhịp. Toàn bộ máy tính đóng băng, chờ nhịp tiếp theo. Giống như trò đèn đỏ, đèn xanh khắc nghiệt nhất vũ trụ. Ở mỗi "đèn xanh" (xung nhịp):
- Dữ liệu di chuyển giữa các thành phần
- Các phép tính được thực thi
- Các quyết định logic được đưa ra
- Bộ nhớ được đọc hoặc ghi
Một số phép toán mất một chu kỳ (phép cộng đơn giản), trong khi những phép khác mất nhiều chu kỳ (phép chia hoặc lấy dữ liệu từ RAM). Mọi thứ được phối hợp chính xác, hàng tỷ thành phần thực hiện các thao tác riêng của mình và đồng bộ theo nhịp không ngừng này.
Bạn có thể ép xung bộ xử lý bằng cách tăng tốc độ xung nhịp; mọi thứ sẽ chạy nhanh hơn nhưng cũng tạo ra nhiều nhiệt hơn, khiến hệ thống kém ổn định. Ép xung quá mức sẽ làm máy tính bị treo vì các electron thực sự không thể theo kịp nhịp độ.
Ngày trước, các phép toán này được triển khai bằng những cỗ máy lớn bằng cả căn phòng. Nhưng các thành phần thực hiện toàn bộ phép tính này lại vô cùng đơn giản: chúng chỉ là công tắc. Công tắc bật hoặc tắt.
Nối đủ các công tắc này với nhau theo đúng cấu hình là bạn đã có một hệ thống tính toán. Toàn bộ cuộc cách mạng kỹ thuật số bắt nguồn từ cách sắp xếp công tắc tinh vi.
Sự đơn giản này có nghĩa là chỉ cần có công tắc, bất kỳ loại công tắc nào, bạn đều có thể chế tạo máy tính. Người ta đã chế tạo máy tính hoạt động được từ ống dẫn nước và van, quân domino, khối LEGO, viên bi, thậm chí cả redstone trong Minecraft.
Các nguyên lý không thay đổi kể từ thập niên 1940. Chúng ta chỉ ngày càng giỏi hơn trong việc chế tạo công tắc cực nhỏ. Điện thoại của bạn có sức mạnh tính toán lớn hơn tổng số máy tính đã đưa con người lên Mặt Trăng, nhưng vẫn nằm gọn trong túi vì chúng ta đã tìm ra cách chế tạo công tắc ở cấp độ nguyên tử.
Khi chạy các mạng nơ-ron có hàng triệu tham số, chúng ta bật tắt những công tắc nhỏ này hàng tỷ lần mỗi giây, tất cả đều đồng bộ hoàn hảo theo nhịp đập tinh thể. Mọi lần cập nhật trọng số, mọi phép nhân ma trận, mọi hàm kích hoạt đều hoạt động theo nhịp xung nhịp.
Chẳng trách việc huấn luyện model khiến máy tính của bạn kêu như thể đang cố cất cánh!
Khiến mạng nơ-ron chạy BRRRRR#
Được rồi, chúng ta có các chip với hàng tỷ công tắc nhảy múa theo nhịp tinh thể và muốn chạy mạng nơ-ron có hàng triệu tham số trên đó. Chắc dễ thôi nhỉ? Chỉ cần ném các con số vào chip rồi để nó chạy hết tốc lực!
Chạy mạng nơ-ron thật nhanh giống như cố nấu bữa ăn năm món trong một căn bếp mà tủ lạnh cách đó ba dãy nhà, bạn chỉ có một cái chảo, và mỗi nguyên liệu nặng 500 pound. Bản thân phép toán không phải vấn đề lớn nhất; mọi thứ khác mới là vấn đề.
Sự không tương thích về kiến trúc#
Hầu hết chip được thiết kế để chạy Microsoft Word, chứ không phải mạng nơ-ron. CPU được chế tạo với giả định rằng nó sẽ dành cả đời chạy câu lệnh if, vòng lặp và thỉnh thoảng tính thuế cho bạn (một phép tính khiến ngay cả siêu máy tính cũng mệt mỏi về mặt cảm xúc). CPU được tối ưu hóa cho các thao tác tuần tự: làm việc này, rồi đến việc kia, rồi việc tiếp theo.
Nhưng mạng nơ-ron hoàn toàn khác. Chúng muốn làm MỌI THỨ CÙNG MỘT LÚC. Trong quá trình huấn luyện, bạn cập nhật hàng triệu trọng số dựa trên mức độ sai lệch của các dự đoán. Trong quá trình suy luận (thực sự sử dụng model đã huấn luyện), bạn đưa dữ liệu qua hàng triệu phép tính đồng thời. Hãy tưởng tượng bạn cần nhân một triệu con số với một triệu con số khác. CPU của bạn, đáng quý thay, muốn xử lý từng phép một, giống như một kế toán rất nhanh nhưng cực kỳ tỉ mỉ.
Đó là lý do GPU trở thành nền tảng của điện toán AI. GPU được thiết kế cho trò chơi điện tử, nơi cần tính màu của hàng triệu pixel cùng lúc. Hóa ra việc tính màu pixel và thực hiện phép toán trên mạng nơ-ron khá giống nhau một cách đáng ngạc nhiên: cả hai đều cần thực hiện cùng một thao tác trên lượng dữ liệu khổng lồ song song.
Nhưng ngay cả GPU cũng chưa hoàn toàn phù hợp với mạng nơ-ron. Vì thế, các công ty hiện đang chế tạo chip AI chuyên dụng (TPU, NPU và mọi loại từ viết tắt khác kết thúc bằng PU). Những chip này được thiết kế từ đầu chỉ để làm một việc: tăng tốc mạng nơ-ron. Chúng giống như thuê một đầu bếp chỉ biết nấu một món nhưng nấu với tốc độ siêu phàm. Trong khi CPU chật vật xử lý tuần tự các phép toán ma trận và GPU xử lý song song khá tốt, những chip chuyên dụng này ăn ma trận vào bữa sáng, bữa trưa lẫn bữa tối.
Bức tường bộ nhớ (Hay: Vì sao di chuyển bit khó hơn tính toán)#
Trong điện toán mạng nơ-ron hiện đại, chúng ta dành nhiều thời gian và năng lượng hơn cho việc DI CHUYỂN dữ liệu thay vì thực sự TÍNH TOÁN với dữ liệu.
Hãy hình dung chip máy tính của bạn như một nhà toán học thiên tài làm việc nhanh như chớp, nhưng tất cả sách tra cứu đều được cất trong những tòa nhà khác nhau ở khắp thành phố. Họ có thể giải mọi phương trình tức thì, nhưng trước tiên phải lấy được các con số, và hành trình đó mất rất nhiều thời gian.
Chip có thể nhân hai con số trong một chu kỳ xung nhịp (hãy nhớ, đó là một trong hàng tỷ nhịp mỗi giây). Nhanh như chớp! Nhưng đưa những con số đó từ bộ nhớ đến chip có thể mất HÀNG TRĂM chu kỳ. Giống như nhà toán học giải được bài toán trong một giây nhưng cần năm phút đi bộ đến thư viện rồi quay về.
Nguyên nhân là khoảng cách (và không gian). Điện di chuyển nhanh nhưng không phải với tốc độ vô hạn. Dữ liệu phải đi càng xa trên chip thì càng mất nhiều thời gian. Các nhà thiết kế máy tính giải quyết vấn đề này bằng cách tạo ra hệ thống phân cấp bộ nhớ, giống như có nhiều vị trí lưu trữ ở những khoảng cách khác nhau:
- Thanh ghi (được tích hợp trực tiếp vào các đơn vị tính toán): Bàn làm việc của nhà toán học. Truy cập tức thì! Nhưng không gian rất nhỏ, chỉ giữ được khoảng 32 con số. Giống như có giấy ghi chú ngay trước mặt.
- Bộ nhớ đệm L1 (cách vài micromet): Giá sách trong văn phòng. Mất 3-4 chu kỳ để lấy thứ gì đó. Có thể chứa vài nghìn con số.
- Bộ nhớ đệm L2 (cách vài milimet): Tủ hồ sơ cuối hành lang. Mất 10-15 chu kỳ và có thể chứa vài triệu con số.
- Bộ nhớ đệm L3 (ở phía bên kia chip): Phòng lưu trữ ở tầng dưới. Mất 30-50 chu kỳ và chứa hàng chục triệu con số.
- RAM (trên một chip hoàn toàn khác): Kho hàng ở bên kia thành phố. Mất 100-300 chu kỳ. Đây là nơi lưu trữ hàng tỷ con số của bạn.
- SSD/Ổ cứng (kết nối bằng cáp): Một thành phố hoàn toàn khác. Mất hàng triệu chu kỳ. Dung lượng lưu trữ lớn, tốc độ cực chậm.
Cấu trúc cụ thể có thể khác nhau: chip điện thoại của bạn có thể không dùng bộ nhớ đệm L3, trong khi CPU máy chủ có thể có dung lượng L3 rất lớn. Tuy nhiên, nguyên lý vẫn giống nhau: bộ nhớ càng gần thì càng nhanh, nhưng dung lượng càng nhỏ.
Bây giờ là điểm gây khó khăn cho mạng nơ-ron. Hãy tưởng tượng model Ultralytics YOLO của bạn có 50 triệu tham số (ChatGPT có hàng tỷ tham số, tiện thể nói luôn). Đó là 50 triệu con số cần di chuyển từ bộ nhớ đến các đơn vị tính toán rồi quay lại. Ngay cả khi mỗi con số chỉ chiếm 4 byte, vẫn có 200 megabyte dữ liệu cần di chuyển qua hệ thống.
Chip có thể xử lý mỗi con số trong một chu kỳ, nhưng nếu mất 100 chu kỳ để lấy con số đó từ RAM, bạn sẽ dành 99% thời gian chờ dữ liệu được chuyển đến. Giống như một chiếc xe đua Công thức 1 mắc kẹt trong ùn tắc giao thông. Toàn bộ sức mạnh tính toán ở đó, chỉ chờ dữ liệu đến.
Đây là nhận định then chốt: đây CHÍNH LÀ nút thắt cổ chai trong điện toán hiện đại. Hiện tượng này được gọi là nút thắt cổ chai von Neumann. Tăng tốc độ tính toán của chip tương đối dễ. Tăng tốc độ bộ nhớ lại đang chạm đến giới hạn vật lý. Đây là lý do gần như TẤT CẢ hoạt động tối ưu hóa hiệu năng trong AI đều diễn ra ở cấp độ bộ nhớ. Khi kỹ sư tăng tốc mạng nơ-ron, họ hiếm khi làm phép toán nhanh hơn; thay vào đó, họ tìm cách thông minh để giảm lượng dữ liệu di chuyển, lưu cache hiệu quả hơn hoặc truy cập dữ liệu khôn ngoan hơn.
Chip AI hiện đại không chỉ tập trung vào tốc độ tính toán; chúng đặc biệt chú trọng đến băng thông bộ nhớ và chiến lược di chuyển dữ liệu. Chúng nạp trước dữ liệu, tái sử dụng các giá trị đã có trong cache và tổ chức phép tính để giảm thiểu số lần truy cập bộ nhớ. Những người chiến thắng trong cuộc đua phần cứng AI không phải là bên có máy tính nhanh nhất; mà là bên tìm ra cách cung cấp dữ liệu liên tục cho các máy tính đó. Toàn bộ cuộc chơi xoay quanh việc tối ưu hóa các mẫu truy cập bộ nhớ.
Mỗi lần bạn di chuyển một chút dữ liệu, bạn lại tiêu tốn năng lượng. Không nhiều, chỉ cỡ picojoule, nhưng khi di chuyển hàng terabyte mỗi giây, lượng năng lượng đó sẽ tích tụ NHANH CHÓNG. Thực tế, di chuyển dữ liệu qua một khoảng cách 1 mm trên chip còn tốn nhiều năng lượng hơn cả việc thực hiện phép tính!
Đó là lý do laptop của bạn nghe như động cơ phản lực khi huấn luyện mạng neural. Không phải các phép toán tạo ra nhiệt; mà là việc di chuyển dữ liệu. Mỗi lần cập nhật tham số, mỗi phép tính gradient, mỗi lượt truyền xuôi đều thực sự làm căn phòng của bạn nóng lên.
Các bộ tăng tốc AI hiện đại về cơ bản là những bài toán nhiệt động lực học. Ta có thể tích hợp bao nhiêu phép tính trước khi chip nóng chảy? Có thể tản nhiệt nhanh đến mức nào? Cứ như ép xung, nhưng xung nhịp luôn ở mức 11, còn chúng ta chỉ cố không để xảy ra hỏa hoạn.
Giải pháp? Thiết kế có xét đến kiến trúc#
Các mạng neural nhanh nhất không nhất thiết là thông minh nhất, mà là những mạng được thiết kế có tính đến chip. Chúng:
- Giữ dữ liệu ở cục bộ nhiều nhất có thể
- Tái sử dụng phép tính một cách triệt để
- Tương thích hoàn hảo với khả năng của phần cứng
- Giảm thiểu việc di chuyển bộ nhớ bằng mọi giá
Điều này giống như sự khác biệt giữa một công thức nấu ăn yêu cầu "dùng nguyên liệu mua ở cửa hàng tạp hóa gần nhà" và một công thức đòi nhập gia vị từ Tây Tạng, phô mai từ Pháp và nước từ Nam Cực. Cả hai món có thể đều ngon, nhưng một cách chắc chắn thiết thực hơn.
Đó là lý do tăng tốc mạng neural là một nghệ thuật. Chỉ có toán học tốt thôi là chưa đủ; bạn cần hiểu phần cứng, tôn trọng hệ thống phân cấp bộ nhớ và phối hợp nhịp nhàng với kiến trúc.
Chào mừng đến với thế giới nơi khoa học máy tính gặp vật lý, gặp kỹ thuật và gặp cả phép thuật thuần túy. Nơi di chuyển một con số tốn kém hơn tính toán với nó. Nơi xử lý song song thì nhanh, nhưng đồng bộ hóa là cơn ác mộng. Nơi kẻ thù lớn nhất không phải độ phức tạp, mà là khoảng cách.
Cách chúng tôi tăng tốc YOLO#
Khi huấn luyện một model YOLO, bạn sẽ có một mạng neural hoạt động rất tốt trên môi trường huấn luyện của mình. Nhưng vấn đề là: GPU chơi game, iPhone và con chip nhỏ xíu trong camera an ninh của bạn sử dụng những ngôn ngữ hoàn toàn khác nhau. Chúng có điểm mạnh, điểm yếu và cách xử lý dữ liệu rất khác nhau.
Hãy hình dung thế này: GPU có hàng nghìn lõi có thể hoạt động đồng thời — nó được xây dựng để xử lý song song. Trong khi đó, chip di động có thể có các mạch chuyên dụng cho những phép toán AI, nhưng chỉ xử lý được một số loại phép toán nhất định. Còn thiết bị biên trong camera chuông cửa của bạn? Nó phải chạy AI với ngân sách điện năng còn thấp hơn một bóng đèn LED.
Tại Ultralytics, chúng tôi hỗ trợ hơn một tá định dạng xuất khác nhau vì mỗi định dạng được tối ưu cho phần cứng riêng. Vấn đề không phải là có quá nhiều lựa chọn, mà là có lựa chọn phù hợp với nhu cầu cụ thể của BẠN.
Hợp nhất phép toán: Làm được nhiều hơn với ít tài nguyên hơn#
Trong model YOLO ban đầu, nhiều phép toán được thực hiện tuần tự. Ví dụ, ta có thể tích chập, sau đó chuẩn hóa kết quả, rồi áp dụng hàm kích hoạt. Đó là ba bước riêng biệt, mỗi bước cần đọc và ghi bộ nhớ riêng.
Nhưng đây mới là điểm hay: ta có thể kết hợp các phép toán này thành một bước duy nhất. Khi export YOLO để triển khai, chúng tôi hợp nhất các phép toán này. Thay vì:
- Tính tích chập → Lưu vào bộ nhớ
- Tải từ bộ nhớ → Chuẩn hóa → Lưu vào bộ nhớ
- Tải từ bộ nhớ → Áp dụng hàm kích hoạt → Lưu vào bộ nhớ
Ta thực hiện:
- Tính tích chập + chuẩn hóa + hàm kích hoạt → Lưu vào bộ nhớ
Với một model YOLO điển hình xử lý ảnh 640×640, thủ thuật đơn giản này loại bỏ hàng gigabyte dữ liệu truyền bộ nhớ không cần thiết. Trên điện thoại, đây là khác biệt giữa phát hiện thời gian thực mượt mà và độ trễ gây khó chịu.
Dùng số nhỏ hơn: Phép màu lượng tử hóa#
YOLO không thực sự cần các con số có độ chính xác cực cao để phát hiện đối tượng chính xác. Trong quá trình huấn luyện, chúng tôi dùng 32 bit để biểu diễn mỗi trọng số — giống như dùng máy tính khoa học để đong nguyên liệu làm bánh mì kẹp. Khi triển khai thực tế? 8 bit là đủ.
Kỹ thuật này được gọi là lượng tử hóa, và đây là một trong những kỹ thuật tối ưu hóa hiệu quả nhất của chúng tôi. Bằng cách sử dụng các số có kích thước nhỏ hơn:
- Kích thước model giảm 75% (từ 200 MB xuống 50 MB đối với Ultralytics YOLO11x)
- Model chạy nhanh hơn 2–4 lần trên hầu hết thiết bị
- Model tiêu thụ ít điện năng hơn nhiều (pin điện thoại của bạn sẽ cảm ơn bạn)
Không phải lớp nào trong YOLO cũng nhạy như nhau với mức giảm này. Các lớp đầu phát hiện cạnh và hình dạng cơ bản? Chúng rất vững — ta có thể dùng số 8 bit mà không gặp vấn đề gì. Các lớp phát hiện cuối cùng xác định "đây là mèo hay chó?" cần độ chính xác cao hơn một chút. Vì vậy, chúng tôi điều chỉnh độ chính xác theo từng lớp, chỉ dùng số bit vừa đủ để duy trì độ chính xác mà vẫn tối đa hóa tốc độ.
Chọn thuật toán tốt nhất#
Có hàng chục cách khác nhau để thực hiện cùng một phép toán. Có thể tính phép tích chập đơn giản (phép toán cốt lõi trong YOLO) bằng các thuật toán hoàn toàn khác nhau, và lựa chọn tốt nhất tùy thuộc vào phần cứng cụ thể cũng như kích thước đầu vào của bạn.
Khi export YOLO, framework tối ưu hóa của chúng tôi thực sự thử nghiệm các thuật toán khác nhau và chọn thuật toán nhanh nhất cho trường hợp cụ thể của bạn. Cứ như có nhiều tuyến đường đến cùng một điểm đến và lựa chọn dựa trên tình hình giao thông hiện tại. Trên GPU, chúng tôi có thể dùng thuật toán xử lý nhiều pixel đồng thời. Trên CPU, chúng tôi có thể dùng thuật toán được tối ưu cho xử lý tuần tự. Toán học vẫn như nhau, nhưng chiến lược thực thi hoàn toàn khác.
Bộ nhớ: Nút thắt cổ chai tiềm ẩn#
Bạn còn nhớ chúng ta đã nói bộ nhớ mới là nút thắt cổ chai thực sự trong điện toán hiện đại không? Điều này đặc biệt đúng với YOLO. Model có thể có 50 triệu tham số và trong quá trình suy luận, tạo ra hàng gigabyte kết quả trung gian. Việc di chuyển toàn bộ dữ liệu này thường chậm hơn phép tính thực tế.
Chúng tôi sử dụng một số thủ thuật để giảm thiểu việc di chuyển bộ nhớ:
Lập lịch thông minh: Chúng tôi sắp xếp các phép toán sao cho dữ liệu được sử dụng ngay khi còn nằm trong bộ nhớ đệm tốc độ cao. Với mạng kim tự tháp đặc trưng của YOLO, cách này giảm 40% lưu lượng bộ nhớ.
Chia ô: Thay vì xử lý toàn bộ ảnh cùng lúc, chúng tôi chia ảnh thành các ô nhỏ hơn vừa với bộ nhớ đệm. Nhờ vậy, bộ xử lý có thể làm việc với bộ nhớ cục bộ tốc độ cao thay vì liên tục lấy dữ liệu từ bộ nhớ chính chậm hơn.
Tái sử dụng bộ đệm: Thay vì liên tục cấp phát bộ nhớ mới cho kết quả trung gian, chúng tôi tái sử dụng cùng các bộ đệm bộ nhớ. Cách này cực kỳ hiệu quả — toàn bộ backbone của YOLO có thể chạy chỉ với một nhóm bộ đệm có thể tái sử dụng.
Cắt tỉa: Ít hơn là nhiều hơn#
Một điều đáng ngạc nhiên là các model YOLO thường được thiết kế phức tạp hơn mức cần thiết. Trong nhiều lớp, chúng ta thường có thể loại bỏ các kênh mà hầu như không ảnh hưởng đến độ chính xác. Việc này không chỉ làm model nhỏ hơn mà còn giúp model chạy nhanh hơn, vì số phép tính cần thực hiện thực sự giảm đi.
Quy trình này rất tinh gọn: chúng ta phân tích những phần của mạng đóng góp ít nhất vào kết quả phát hiện cuối cùng, loại bỏ các phần đó rồi tinh chỉnh model để bù lại. Trên các thiết bị chạy bằng pin, mức cải thiện hiệu quả này có thể giúp thiết bị hoạt động thêm nhiều giờ.
Tăng tốc phần cứng: Tận dụng thế mạnh của từng chip#
Mỗi loại bộ xử lý phù hợp với những tác vụ khác nhau, và chênh lệch hiệu năng giữa chúng không chỉ là khác biệt về tốc độ xung nhịp mà còn phản ánh khác biệt căn bản về kiến trúc. GPU có hàng nghìn lõi hoạt động song song, rất phù hợp với các phép tích chập của YOLO. NPU trên thiết bị di động có các mạch chuyên dụng được thiết kế riêng cho mạng nơ-ron. CPU là bộ xử lý đa năng, linh hoạt nhưng không chuyên biệt.
Chìa khóa để tối ưu là ghép các phép toán của YOLO với thế mạnh của từng chip. GPU xử lý rất tốt cùng một phép toán trên nhiều dữ liệu đồng thời. NPU di động có thể chỉ hỗ trợ một số phép toán nhất định nhưng thực thi chúng cực kỳ hiệu quả. edge TPU chỉ hoạt động với số nguyên 8 bit nhưng đạt tốc độ ấn tượng trong giới hạn đó.
Phép màu biên dịch#
Khi bạn export một model YOLO, phía sau hậu trường sẽ diễn ra một điều đáng chú ý. Chúng tôi không chỉ chuyển đổi định dạng tệp — mà thực sự biên dịch model riêng cho phần cứng đích của bạn. Điều này giống như sự khác biệt giữa Google Translate và một người bản ngữ. Quá trình biên dịch:
- Phân tích model của bạn để hiểu cấu trúc và yêu cầu của model
- Xem xét khả năng của phần cứng — phần cứng làm tốt việc gì và gặp khó khăn ở đâu
- Tạo mã đã tối ưu để giao tiếp bằng ngôn ngữ gốc của phần cứng
Trình biên dịch có thể sắp xếp lại các phép toán để tận dụng tốt hơn bộ nhớ đệm của bộ xử lý, chọn các lệnh chuyên dụng mà chip hỗ trợ, hoặc thậm chí dùng machine learning để tìm chiến lược tối ưu hóa tốt nhất. Đúng vậy, chúng tôi đang dùng AI để tối ưu AI — tương lai đã đến!
Bước biên dịch này có thể tạo ra chênh lệch hiệu năng gấp 10 lần. Cùng một model YOLO có thể chạy ì ạch với mã chung nhưng lại hoạt động cực nhanh với các lệnh được tối ưu đúng cách.
Triển khai thực tế trên thiết bị biên#
Hãy cùng tìm hiểu điều gì xảy ra khi YOLO bước vào thế giới thực – cụ thể là môi trường đầy thách thức của thiết bị biên. Hãy tưởng tượng một camera an ninh cần chạy YOLO 24/7 để phát hiện đối tượng. Camera phải hoạt động trong những điều kiện vô cùng hạn chế:
- Bộ nhớ: Có thể tổng RAM chỉ từ 512 MB đến 2 GB
- Điện năng: Thường chỉ 2–5 watt (ít hơn bộ sạc điện thoại)
- Tản nhiệt: Không có quạt, chỉ tản nhiệt thụ động
- Độ tin cậy: Phải chạy liên tục mà không bị lỗi
Điều quan trọng là chọn được sự đánh đổi phù hợp. Trên thiết bị biên, chúng tôi thường:
- Dùng lượng tử hóa INT8 (độ chính xác thấp hơn, tiêu thụ ít điện năng hơn nhiều)
- Giảm số khung hình xử lý khi hoạt động ít
- Phân bổ công việc cho các bộ xử lý khác nhau để kiểm soát nhiệt độ
- Giữ model đủ nhỏ để nằm trọn trong bộ nhớ tốc độ cao
Quy trình tối ưu hóa#
Tại Ultralytics, chúng tôi áp dụng quy trình tối ưu hóa có hệ thống. Trước tiên, chúng tôi lập hồ sơ hiệu năng của model để xác định thời gian thực sự được dùng vào đâu. Nhiều khi, nút thắt cổ chai không nằm ở nơi bạn nghĩ. Có thể 80% thời gian được dành cho chỉ một vài lớp, hoặc việc truyền bộ nhớ chiếm phần lớn thời gian tính toán.
Tiếp theo, chúng tôi áp dụng các phương pháp tối ưu theo từng vòng lặp:
- Bắt đầu với những nút thắt cổ chai lớn nhất
- Mỗi lần áp dụng một phương pháp tối ưu
- Đo lường cả mức cải thiện tốc độ lẫn ảnh hưởng đến độ chính xác
- Giữ lại các phương pháp tối ưu đem lại sự đánh đổi hợp lý
- Lặp lại cho đến khi đạt mục tiêu
Tương lai: Điện toán không đồng nhất#
Các thiết bị hiện đại ngày càng thông minh hơn trong việc phối hợp nhiều bộ xử lý. Điện thoại của bạn không chỉ có một bộ xử lý — mà có nhiều bộ xử lý, mỗi bộ chuyên trách các tác vụ khác nhau:
- Cảm biến camera có ISP (bộ xử lý tín hiệu hình ảnh) để tiền xử lý
- NPU (bộ xử lý thần kinh) chạy suy luận YOLO
- CPU xử lý logic phức tạp và điều phối
- GPU hiển thị kết quả trên màn hình
Tương lai của việc tối ưu YOLO là phân chia model giữa các bộ xử lý này một cách thông minh. Có thể NPU xử lý các phép tích chập chính, CPU thực hiện logic phát hiện cuối cùng, còn GPU trực quan hóa kết quả. Mỗi bộ xử lý làm phần việc mình giỏi nhất, tạo ra một pipeline hiệu quả hơn bất kỳ bộ xử lý đơn lẻ nào có thể đạt được.
Chúng tôi đang phát triển các thuật toán phân vùng thông minh để tự động xác định cách tốt nhất phân chia YOLO giữa các bộ xử lý hiện có, không chỉ xét đến khả năng của từng bộ xử lý mà còn cả chi phí di chuyển dữ liệu giữa chúng.
Tóm lại#
Tối ưu model YOLO không chỉ là chuyển đổi định dạng tệp; đó còn là biến AI tiên tiến nhất thành thứ thực sự hoạt động được trong thực tế. Thông qua các kỹ thuật như lượng tử hóa (sử dụng số nhỏ hơn), cắt tỉa (loại bỏ các phần không cần thiết), hợp nhất phép toán (kết hợp các bước) và quản lý bộ nhớ thông minh, chúng ta có thể cải thiện đáng kể hiệu năng mà vẫn duy trì độ chính xác.
Điều đáng chú ý là không có phương pháp tối ưu nào "tốt nhất" cho mọi trường hợp. Máy chủ đám mây có nguồn điện không giới hạn cần các phương pháp tối ưu khác với drone chạy bằng pin. Điện thoại có chip AI chuyên dụng cần cách xử lý khác Raspberry Pi. Đó là lý do Ultralytics cung cấp nhiều tùy chọn export đến vậy — mỗi tùy chọn được tối ưu cho các tình huống khác nhau.
Mọi tối ưu hóa mà chúng ta đã thảo luận đều phục vụ một mục tiêu: đưa thị giác máy tính đến mọi nơi. Dù bạn đang xây dựng chuông cửa thông minh, ứng dụng drone hay dịch vụ đám mây quy mô lớn, chúng tôi cung cấp các công cụ giúp YOLO hoạt động trong những giới hạn của bạn.
Khi xuất model YOLO bằng Ultralytics, bạn không chỉ lưu một tệp. Bạn đang tận dụng nhiều năm nghiên cứu nhằm đưa mạng nơ-ron vào ứng dụng thực tiễn. Bạn đang chuyển đổi một model AI tiên tiến thành thứ có thể chạy trên phần cứng thực tế, với những giới hạn thực tế, để giải quyết các vấn đề thực tế.
Đó là công việc của Ultralytics. Chúng tôi thu hẹp khoảng cách giữa nghiên cứu AI và triển khai thực tiễn. Chúng tôi giúp thị giác máy tính hoạt động ở mọi nơi, vì tương lai của AI không chỉ nằm ở việc sở hữu những model tốt nhất – mà còn ở việc đưa những model đó vào ứng dụng thực tế.
Được viết bởi
Bình luận
Đặt câu hỏi, chia sẻ kết quả hoặc giúp đỡ người khác.










