Mình cũng muốn đóng góp tí:
Nhà hàng có 4 nhân viên ( 4 cores, lần lượt là core A, B, C, D )
Nhân viên có thể làm mọi task từ nấu ăn, bồi bàn, nhận order từ user ...
Được cái 4 nhân viên không biết được những công việc của các nhân viên khác
Thread có thể hiểu là những chỉ dẫn cho nhân viên để nhân việc thực hiện task
Khách đến ăn là user
Quản lý chỉ dùng 1 nhân viên
Sync: Nhân viên đợi khách gọi món => nhân viên vô bếp nấu => nhân viên đem ra => đợi khách ăn xong => nhân viên dọn dẹp.
Trường hợp có nhiều khách đến ăn mà chỉ có 1 nhân viên ra phục vụ thì khách đến sau đợi đến mùa quýt nên quản lý dùng 4 nhân viên
Parallelism: A ghi món xong giao cho B nấu xong đến C bê ra D đợi khách ăn xong rồi dọn dẹp.
Hoặc mình có thể code sao cho mỗi core đều làm y chang:
(A ghi món => A nấu => A bê => A dọn dẹp)
(B ghi món => B nấu => B bê => B dọn dẹp)
(C ghi món => C nấu => C bê => C dọn dẹp)
(D ghi món => D nấu => D bê => D dọn dẹp)
Nói chúng là mình tận dùng toàn bộ core
Trong java có hàm để run parallelStream
Async ( hay còn gọi là non-blocking ): Trong lúc đợi khách gọi món, đợi khách ăn xong thì cho nhân viên làm việc khác. Nếu A đang đợi khách ăn xong thì A có thể ghi món cho khách mới.
Asyn là cách để đạt được concurrency.
Quản lý muốn đem lại trải nghiệm đồng thời (concurrency) cho khách hàng
Giả sử:
- 2 khách hàng gọi món cùng 1 thời điểm ( thời gian đợi của khách 1 là 10s, khách 2 là 20s)
- chỉ 1 nhân viên A
- đợi + ghi món mất 5p, nấu 20p, bê ra 3p, đợi + dọn dẹp 4p
Concurrency: A trong lúc đợi khách 1 thì sẽ chuyển qua phục vụ khách 2. Thậm chí nếu không đợi thì A vẫn phục vụ qua lại giữa khách 1 và khách 2.
Khách hàng cảm thấy như mình được phục vụ liên tục, nhưng thực sự không phải vậy.
Thực tế thì làm việc với concurrency rất phức tạp, dễ lỗi. Lỗi phổ biến như là: race condition, deadlock. Nên concurrency chỉ khuyên dùng cho heavy task thôi. Việc thiết kế code để cho phù hợp với concurrency cũng rất chát :<