kiến thức Javascript cho người mới bắt đầu

4. Tất cả các async callback gọi bởi Web APIs (setInterval(), setTimeout()...) sẽ được cho vào callback queue. Có nghĩa là kể cả khi bạn dùng cái setTimeOut và truyền cho nó 1 callback kèm thời gian chờ bằng 0 thì callback đó vẫn được cho vào callback queue chứ ko phải là dự vào thời gian thực thi để đưa vào.

Có thể test thử đoạn code này để thấy:
JavaScript:
console.log(1);
setTimeout(() => console.log(2), 0);
console.log(3);
console.log(4);
console.log(5);
console.log(6);
console.log(7);
console.log(8);
console.log(9);
console.log(10);
Kết quả sẽ luôn là: 1 3 4 5 6 7 8 9 10 2 dù console.log(2) được set thời gian chờ là 0.
thì ý mình là các async callback được gọi bởi WebAPIs đều cho vào queue, nhưng chưa rõ vụ timer đúng ko fen? chỉ là nếu nhiều async callback sẽ sắp xếp queue đó theo thời gian.

JavaScript:
setTimeout(() => console.log(0), 20);
console.log(1);
setTimeout(() => console.log(2), 0);
console.log(3);
console.log(4);
console.log(5);
console.log(6);
console.log(7);
console.log(8);
console.log(9);
console.log(10);
 
Mình đóng góp như này
Quá trình compile code của javascript như sau.
1. Call stack: Call Stack là một cấu trúc dữ liệu dạng ngăn xếp (stack) dùng để chứa thông tin về hoạt động của chương trình máy tính trong lúc thực thi. Khi xảy ra lỗi sẽ nhìn thấy ở log, ví dụ như stack trace, stack overflow(xảy ra 1 vòng lặp quá kích thước tối đa của stack)
2. JavaScript Runtime: JS Runtime là browser's JS runtime environment. Và nó bao gồm những thành phần sau đây: Event loop, Web APIs, Callback Queue
3. Cơ chế event loop: Khi các dòng lệnh chuẩn bị thực thi thực thi. JS runtime sinh ra 1 sự kiện tên là Event Loop, sự kiện này được chạy trong suốt quá trình runtime. Sự kiện này đưa các dòng lệnh vào call stack, web APIs, Callback Queue
4. Cơ chế bất đồng bộ: Từ cơ chế event loop, Js run time có 1 bộ đếm timer(), hàm này giúp đếm thời gian thực thi của stack, nếu stack nào có sử dụng web APIs (setTimeout, xhr, connection, http request v.v.v) => bộ đếm timer sẽ lớn. event loop sẽ đưa stack đó vào Queue để thực thi và stack tiếp theo được thực hiện, sau khi stack có timer lớn thực hiện xong thì sẽ trả về kết quả ==> nguyên nhân vì sao xảy ra tình trạng bất đồng bộ.
Có gì sai xót các fen góp ý giúp
em thank bac nhieu a
 
thì ý mình là các async callback được gọi bởi WebAPIs đều cho vào queue, nhưng chưa rõ vụ timer đúng ko fen? chỉ là nếu nhiều async callback sẽ sắp xếp queue đó theo thời gian.

JavaScript:
setTimeout(() => console.log(0), 20);
console.log(1);
setTimeout(() => console.log(2), 0);
console.log(3);
console.log(4);
console.log(5);
console.log(6);
console.log(7);
console.log(8);
console.log(9);
console.log(10);

Cái hàm setTimeout hoạt động thế này, khi bạn gọi setTimeout kèm theo 1 cái callback function và 1 cái số thời gian X thì cái 1 cái timer sẽ chạy, khi timer chạy hết X thời gian xong thì callback function sẽ được đẩy vào callback queue nên cái nào bạn set thời gian ngắn hơn thì nó đẩy vào callback queue trước và được even loop lấy ra đưa lên call stack để chạy.

Còn với các web APIs khác, ví dụ XMLHttpRequest thì khi có kết quả nó sẽ đẩy vào callback queue chứ nó ko có cơ chế gì để dự đoán được thời gian thực thi mà sắp xếp callback queue đâu, theo mình biết là như vậy.
 
Last edited:
Cái hàm setTimeout hoạt động thế này, khi bạn gọi setTimeout kèm theo 1 cái callback function và 1 cái số thời gian X thì cái 1 cái timer sẽ chạy, khi timer chạy hết X thời gian xong thì callback function sẽ được đẩy vào callback queue nên cái nào bạn set thời gian ngắn hơn thì nó đẩy vào callback queue trước và được even loop lấy ra đưa lên call stack để chạy.

Còn với các web APIs khác, ví dụ XMLHttpRequest thì khi có kết quả nó sẽ đẩy vào callback queue chứ nó ko có cơ chế gì để dự đoán được thời gian thực thi mà sắp xếp callback queue đâu, theo mình biết là như vậy.
Ông nói gà bà nói vịt rồi.
ý ông @Dev cùi đang giải thích lại sao js là single-thread mà lại đẻ ra concept bất đồng bộ. Lý do là để xử lý các long-running task, tránh blocking js (vốn là single-thread). Concept async này xử lý bằng cách browser sẽ cung cấp một số webAPIs chạy độc lập với js. Thay vì phải ngồi chờ xử lý hết đống long running task mới làm tiếp thì js core có thể làm việc khác cho tới khi các webAPIs long running task (như send request chẳng hạn) chạy xong và notify cho bên js (cơ chế thông báo thì như ông @digiaodo diễn giải, chạy xong thì push sang callback-queue => event loop => call stack). Về cơ bản đây chỉ đơn giản là một hành động chia nhỏ task ra để các tác vụ như render, painting có thời gian chen vào giữa. Thay vì ta có một task to là call API và chờ đến khi có kết quả thì process data mình sẽ chia thành 3 task callAPI (do js làm), chờ có kết quả và thông báo (webAPIs làm), processData (sau khi chờ có kết quả webAPI push task này vào callbackqueue, để lên lịch cho js làm). Và giữa các task này giờ ta có thể nhét vào các task giúp cái web nó responsive hơn như recalculate style, painting, do other scripting
 
Sẵn đây thì cũng giúp ae trả lời câu hỏi phỏng vấn muôn thuở. Tại sao js là single-thread mà lại phổ biến với concept bất đồng bộ/asynchronous?

Lý do mình có giải thích ở trên, JS là single-thread và nó chạy sync + là một dạng ngôn ngữ thông dịch (execute line by line, cái này tranh cãi nhiều, nhưng quan điểm của mình nó là thông dịch).
Concept asynchronous, callback/promise/async-await được đề xuất nhằm một mục đích duy nhất là split long running task thành các task nhỏ hơn để tăng hiệu suất cho một ngôn ngữ single-thread như js. Và js chạy async được là do environment support (browser, node, etc). Tự thân nó chạy một mình thì define thêm mấy cái async/microtask/macro hoàn toàn không có ý nghĩa, vì nó vẫn sẽ phải chạy tuần tự (đơn luồng mà).

Mọi người hay nhầm về JS, single thread, asynchronous là do JS nó gắn với browser, nên nhiều lúc mọi người nhầm tưởng mấy cái của browser/environment là của JS. Một ví dụ điển hình là Promise.resolve() ở môi trường browser sẽ có behaviour khác môi trường node.
 
Sẵn đây thì cũng giúp ae trả lời câu hỏi phỏng vấn muôn thuở. Tại sao js là single-thread mà lại phổ biến với concept bất đồng bộ/asynchronous?

Lý do mình có giải thích ở trên, JS là single-thread và nó chạy sync + là một dạng ngôn ngữ thông dịch (execute line by line, cái này tranh cãi nhiều, nhưng quan điểm của mình nó là thông dịch).
Concept asynchronous, callback/promise/async-await được đề xuất nhằm một mục đích duy nhất là split long running task thành các task nhỏ hơn để tăng hiệu suất cho một ngôn ngữ single-thread như js. Và js chạy async được là do environment support (browser, node, etc). Tự thân nó chạy một mình thì define thêm mấy cái async/microtask/macro hoàn toàn không có ý nghĩa, vì nó vẫn sẽ phải chạy tuần tự (đơn luồng mà).

Mọi người hay nhầm về JS, single thread, asynchronous là do JS nó gắn với browser, nên nhiều lúc mọi người nhầm tưởng mấy cái của browser/environment là của JS. Một ví dụ điển hình là Promise.resolve() ở môi trường browser sẽ có behaviour khác môi trường node.
Browser ngoài javascript runtime còn có nhiều process khác nữa, ngoài việc thực thi JS thì browser còn nhiều tác vụ khác: render, UI, networking,… nên mặc dù JS là singlethread nhưng browser thì không.
ý kiến của mình như này
 
Cái hàm setTimeout hoạt động thế này, khi bạn gọi setTimeout kèm theo 1 cái callback function và 1 cái số thời gian X thì cái 1 cái timer sẽ chạy, khi timer chạy hết X thời gian xong thì callback function sẽ được đẩy vào callback queue nên cái nào bạn set thời gian ngắn hơn thì nó đẩy vào callback queue trước và được even loop lấy ra đưa lên call stack để chạy.

Còn với các web APIs khác, ví dụ XMLHttpRequest thì khi có kết quả nó sẽ đẩy vào callback queue chứ nó ko có cơ chế gì để dự đoán được thời gian thực thi mà sắp xếp callback queue đâu, theo mình biết là như vậy.
bổ sung 1 chút chỗ cái nào bạn set thời gian ngắn hơn thì nó đẩy vào callback queue trước và được even loop lấy ra đưa lên call stack để chạy thì còn tuỳ thuộc vào vị trí của cái setTimeout đó nữa.
JavaScript:
setTimeout(() => console.log(0), 20);
console.log(1);
setTimeout(() => console.log(2), 0);
console.log(3);
console.log(4);
console.log(5);
console.log(6);
console.log(7);
console.log(8);
console.log(9);
console.log(10);

ví dụ nhu đoạn này nếu thêm setTimeout(() => console.log(1000), 3); trên cùng thì nó sẽ log 1000 trước 2 dù 2 đc setTimeout 0s.
 
Tôi thấy thớt có ý tốt khi muốn chia sẻ kinh nghiệm của mình. Nhưng tôi nhắc nhở nhẹ là năm 2022 rồi, mở cửa hội nhập tây âu nó mở cả đống công ty để moi chất xám dev Việt kia kìa, anh muốn nhiều tiền và môi trường làm việc và học tập chuyên nghiệp thì mời anh trình bày kiến thức bằng tiếng anh. Nó không những giúp cải thiện Writing của anh mà còn giúp cho tụi dev nghiệp dư đọc bài của anh bắt buộc phải đọc và tư duy bằng tiếng anh để cho chúng nó tốt lên. Chứ anh mà cứ trình bày kiến thức bằng tiếng Việt thế này thì cứ ru rú ở mấy công ty outsource, product Việt làng nhàng, toxic và nghiệp dư nhé:sneaky:
 
6.2 Object
Ngoài đời hay trong lập trình đều vậy, k có cái gì gọi là định nghĩa chính xác 100% cả, đúng người này nhưng với người khác thì chưa chắc. Nhưng chúng ta thường theo số đông. Đó là lí do vì sao trong lập trình có nhiều cái gây tranh cãi, chưa thống nhất nhau về định nghĩa và cách dùng như vậy. Cũng giống như 1+ 3 = 2+ 2 = 8-4 = 4, nó đều quy về 1 kết quả nhưng có nhiều cách tính, cách trình bày. Từ qua đến giờ, e có theo dõi cuộc tranh luận của các bác về setTimeOut(), ý kiến và cách biện luận của các bác e đều đọc , tất nhiên những chỗ e sẽ k hiểu hết. Chính vì thế, e nên đứng ở giữa, nghe các bác nói + tìm hiểu thêm, mục đích cuối cùng vẫn là tìm ra đường của mình. Thật sự, nhiều bác cứ sợ tranh luận hay nói đúng hơn là sợ thua, sợ mình nói sai bị bắt bẻ. Giờ thì e ít chứ khoảng time còn học c3 e rất hay tranh luận với bạn với thầy, chính những cái kiến thức đấy sẽ nhớ lâu hơn là học. E còn nhớ năm 11 thi hsg tỉnh môn Toán, nhờ cái hay tranh luận mà e tìm đc phương pháp tính ra nghiệm của bài Bất đẳng thức. Mà BDT tìm đc nghiệm thì xem như done.
Có vẻ như e nói lệch đề hơi nhiều :)) Nhưng thread này đang đi đúng mục đích e lập ra. E sẽ đẩy nhanh tiến độ 2-3 bài, từ bài 10 trở lên mới có nhiều cái hay, cái tranh luận mà e và mọi người sẽ rất mong đợi.

Vào với bài học, ở bài Array e có lấy ví dụ vì sao cần mảng. Giả sử ta có mảng lưu trữ tên của 30 học sinh đó rồi, giờ ta cần biết thêm về age, address, tên của phụ huynh,... thì sẽ làm như nào? Chẳng lẽ, tạo ra các array chứa age, address, .. hay sao? Rồi làm sao để in thông tin của học sinh đó ra?
1665738987793.png

Nếu như lớp 30 học sinh thì sao, có đảm bảo rằng tất cả thông tin sẽ chính xác. Chính vì thế, js cho ra thêm khái niệm về Object. Dịch ra có nghĩa là đối tượng( như hoa, xe, người,...) Đã là đối tượng thì sẽ có thuộc tính(màu gì, tên, tuổi, ...) và phương thức( như người thì có ăn, chạy,..tóm lại là hành động) . Khai báo object như array, chỉ thay đổi dấu [] thành {}.
1665739508904.png

Cũng như aray, object có 2 kiểu khai báo. Đoạn code phía trên là 1 cách khai báo kết hợp giữa array và object. Giờ ta thấy có vẻ là dễ nhìn hơn, và k sợ bị nhầm thông tin.
Nói thêm 1 chút về object. Ở C++, object học để viết code theo OOP(Object Oriented Programming hay còn gọi là lt hướng đối tượng). Sang JS cũng vậy, js có 2 kiểu viết chủ yếu là class cpn và func. Trước đây thì trong ReactJS thì class cpn khá là phổ biến, nhưng từ khi ra đời hook, nó sp cho func thì ít khi có dự án viết theo class cpn. Nhưng k có nghĩa là k cần, vì e thấy tính kế trong class khá là hay.

1665741466943.png

Ở trên e có nói là đối tượng sẽ có thuộc tính và phương thức(hành động), thuộc tính là những gì miêu tả về đối tượng như name, age, address và phương thức là những gì đối tượng hành động như run. Trong đó, phương thức phải ở dưới dạng function. Về function là gì ta sẽ học ở bài dưới, vì phần này sẽ có rất nhiều thứ phải học.
Để truy cập vào thuộc tính hay phương thức của 1 đối tượng, ta dùng toán tử dấu chấm(.), trong đó khi truy cập vào phương thức ta cần thêm (). Tại sao phải() thì ta sẽ đc học ở bài function.

Cách bác vào trình duyệt hiển thị file HTMl, chuột phải chọn Inpsect rồi chọn console, bấm dấu mũi tên ta thấy các prototype của object
1665748633759.png

Phần này e nghĩ các bác nên search trên mạng để đọc cho dễ hiểu, e đề cử đọc của mozilla.

Bài này end đến đây thôi các bác, k phải là e k nói kĩ, mà e nghĩ chỉ cần biết những kiến thức căn bản như này là đc. Để những bài sau vừa học kiến thức mới + bổ sung các kiến thức nâng cao, đi sâu hơn.
 
các bác thấy js khó nhất là phần nào? cá nhân e trầy trật nhất phần asynchronus, lúc đầu tưởng nắm chắc e nó trong tay r đến khi bắt tay vào làm 1 cái website bán hàng đơn giản bằng nodejs + reactjs mới thấy lắm lúc hơi loạn.
 
các bác thấy js khó nhất là phần nào? cá nhân e trầy trật nhất phần asynchronus, lúc đầu tưởng nắm chắc e nó trong tay r đến khi bắt tay vào làm 1 cái website bán hàng đơn giản bằng nodejs + reactjs mới thấy lắm lúc hơi loạn.
Mình cũng thấy phần xử lí đa luồng hơi khó quản lí được.Với giờ mình cũng chưa rõ cái phần prototype .
 
Back
Top