Nội dung bài viết
Video học lập trình mỗi ngày
Performance JavaScript - Đây là một thử nghiệm của hackernoon.com nhưng để lại nhiều tranh cãi, và mỗi người một ý kiến. Và đây là ý kiến trong mọi ý kiến. Còn bạn thế nào?
Trước tiên chúng ta mổ xẻ 3 thí nghiệm của bài viết "3 JavaScript Performance Mistakes You Should Stop Doing" được đăng tải trên hackernoon vào năm 2018 nhưng nó vẫn hữu ích cho mọi devjs. Vì thử nghiệm đơn giản nhưng để lại nhiều suy nghĩ của mỗi người. Ngoài ra bạn có biết Developer hơn nhau ở performance ở chỗ nào không? 3 Thử nghiệm này đều sử dụng trên thiết bị macOS, Chrome browser và Nodejs với phiên bản v10.11.0.
1 - Vòng lặp qua một mảng
Có nhiều web của Việt Nam lấy về và dịch sai, họ cữ ngỡ là loop qua một array nhưng thực tế không phải như vậy mà tính tổng thông qua một array. Nhà thử nghiệm đưa ra một file có 10.000 items. Và tính tổng sau khi loop qua một array bằng 5 cách phổ biến từ ES5 cho đến bây giờ.
Và kết quả như sau
For Loop, average loop time: ~10 microseconds For-Of, average loop time: ~110 microseconds ForEach, average loop time: ~77 microseconds While, average loop time: ~11 microseconds Reduce, average loop time: ~113 microseconds
Các bạn có thể thử cách sử dụng và sự khác biệt giữa for...in, for...of and forEach trong javascript, còn ở đây chúng ta chỉ nói đến hiệu suất thử nghiệm ở đây. Nhìn sơ qua bạn có thể thấy rằng tạo sao phương pháp Reduce() được khuyên sử dụng nhiều nhưng lại kém nhất về hiệu suất?
Ngay cả những phương pháp được ES6 giới thiệu cũng có hiệu suất kém hẳn so với cách truyền thống for
(cũng là phương pháp hoạt động tốt nhất). Lý do vì sao phương pháp mới nhất và được đề xuất nhiều nhất lại kém về hiệu suất có nhiều lý do nhưng chủ yếu là 2 lý do đó chính là Reduce và foreach Mỗi lần thực thi một hàm thì có callback, nói hay hơn là chính là đệ quy, mà bạn biết về cú pháp đệ quy trong javascript rồi.
Ngoài ra đó chính là phân tích mã code các kiểu trước khi thự thi nữa. Một lần nữa xin nhắc lại đó là đang nêu chi tiết phần thi nghiệm, chứ tôi chưa nói phần tôi nhé.
2 - Copy array javascript
Hồi sáng có post bài "14 cách copy array trong javascript" thì cũng nó nói một chút đến về hiệu suất này. Trong thực tế lập trình, ít ai dùng đến cách này nhưng chủ yếu chúng ta nói về tính bất biến trong javascript. Thử nghiệm hiệu suất cũng cho kết quả thú vị, khi sao chép 10.000 dữ liệu ngẫu nhiên. Và cùng xem kết quả thử nghiệm
Duplicate using Slice, average: ~367 microseconds Duplicate using Map, average: ~469 microseconds Duplicate using Spread, average: ~512 microseconds Duplicate using Conct, average: ~366 microseconds Duplicate using Array From, average: ~1,436 microseconds Duplicate manually, average: ~412 microseconds
Kết luận của thí nghiệm này là phương pháp cũ vẫn nhanh hơn phương pháp mới. Sử dụng các phương pháp Operator Spread của ES6 [... arr] và Array.from, cộng với phương thức Map() của ES5, hiệu suất của arr.map (x => x) không tốt bằng phương thức cũ arr.slice () và phương thức kết nối [].concat(arr)
3 - Iterating Objects
Một trường hợp thường gặp khác là lặp đối tượng (Iterating Objects). Chúng ta có phương thức cũ for-in và phương thức mới Object.keys(obj) và Object.entries(obj). Cùng với một 10K dữ liệu thì cho kết quả như sau:
Object iterate For-In, average: ~240 microseconds Object iterate Keys For Each, average: ~294 microseconds Object iterate Entries For-Of, average: ~535 microseconds
4 - Performance JavaScript với quan điểm của tôi
Nói về Performance JavaScript thì 3 thí nghiệm này không đủ để nói lên vấn đề về hiệu suất khi lập trình. Bới vì sao? Các ví dụ thử nghiệm này rất đơn điệu và đơn giản, do đó các kết quả thử nghiệm này không thể chứng minh tính hợp lệ của kết luận này. Ý tưởng của họ không hoàn toàn đúng, nếu bất lịch sử là SAI. Chính vì sự phức tạp của các phương thức mới mà hiệu suất có thể được phản ánh tốt hơn.
Tôi nói vậy có nhiều bạn sẽ không hiểu, để tôi nói đơn giản hơn đó là những phương pháp mà cho kết quả chậm với 3 thí nghiệm này ví dụ như reduce() thì nó thuộc về về các hàm bậc cao (Higher order function) là thực hiện các hoạt động phức tạp hơn và nhận được hiệu suất tốt hơn nhiều. Để chứng minh thì đưa ra thực tế là. Ví dụ, nếu bạn được yêu cầu tính tổng từ 1 đến 100, bạn có sử dụng reduce() không? Nhưng thay vào đó, nếu bạn muốn hợp nhất mảng hai chiều thành mảng một chiều, bạn sẽ sử dụng phương pháp gì?
Có nhiều trường hợp phức tạp hơn, mặc dù tôi chưa thử những cách này nhưng tôi chắc chắn rằng sử dụng Reduce sẽ có hiệu suất tốt hơn sử dụng for. Ngoài ra đừng nghĩ rằng Chúng ta cùng nhau trở về cổ đại là sướng hơn nhé. Sai bét và Xin hết.
Đọc bài thí nghiệm ở đây: hackernoon.com