Thảo luận Bài 7
+54
LeMInhTien(I11C)
PhamHoangQuan (113A)
MaiTrieuHung16 (113A)
ThuyDuong23 (I12A)
MaiThiHongTham70 (113A)
NguyenThiNgocPhuong(113A)
vutanthanh68 (113A)
PhamHuyHoang(I113A)
ledinhngankhanh (113a)
NguyenHuuLinh31(113A)
TrangSiMinhHai (113A)
vuthanhluan_10761241
PhanDiecLoi34 (113A)
CaoTheAnh01(113A)
DoVanTan(113A)
VuongXuongThong (113A)
LamVuThai (113A)
LePhamTuanVu02 (113A)
huynhquanghao_I92C
LeDangBaoNgoc55 (113A)
DangThiKimKhanh (113A)
nguyenchithuc(113A)
NguyenVuLinh12053_I11C
LeThanhNhan45 (113A)
NguyenPhamTanPhat(113A)
TranThiThuyHang79 (113A)
nguyenvanluc(113a)
trantrungnam-HC11TH2A
dothanhnhan44 (113A)
VuTanPhat (113A)
TranMinhNhat61 (102c)
lechaukhoa(113A)
nguyentuannghiaem _(113A)
nguyenduchuy19 (113A)
LeHuynhChiTam (113A)
NguyenVanLam(I13A)
TranThichThem (113A)
NguyenVanHau12 (113A)
phamanhtuan95(113A)
TranThiHuyenTrang(113A)
Trannguyenkhoa26 (113A)
buidainghia(113A)
HaHoangCongTien80 (113A)
NgoManhHung (113A)
tranthanhphu49 (113A)
PhamQuocAnh02 (113A)
NguyenNgocTrungNam (113A)
vuquoctoan (I13A)
NguyenThiThuThuy (113A)
TranThiThuyQuyen (113A)
VuMinhTan (113A)
NguyenThanhHien (113A)
nguyendangnguyen43(i13a)
Admin
58 posters
Trang 3 trong tổng số 6 trang
Trang 3 trong tổng số 6 trang • 1, 2, 3, 4, 5, 6
Re: Thảo luận Bài 7
nguyenvanluc(113a) đã viết:Có bạn bào thực sự hiểu bài 7 không?mình không hiểu lắm,nhờ mấy bạn trợ giúp.
Bạn nói rõ hơn đi. Để mọi người cùng giúp nào
Trannguyenkhoa26 (113A)- Tổng số bài gửi : 35
Join date : 16/07/2012
Age : 35
Re: Thảo luận Bài 7
Bài của bạn thiếu S3 chỗ cấu trúc P3 rồi.TranMinhNhat61 (102c) đã viết:Đồng bộ các tiến trình P1, P2, P3 sau cho P1,P2 hoàn tất trước P3.
semaphore synch = -1;
P1 P2 P3 S1 S2 wait(synch); signal(synch); signal(synch);
Kết quả phải là như thế này:
P1 | P2 | P3 |
S1 | S2 | wait(synch); |
signal(synch); | signal(synch); | S3 |
NguyenVanHau12 (113A)- Tổng số bài gửi : 7
Join date : 16/07/2012
Mục đích của đồng bộ hoá công việc các tiến trình và Ví dụ minh hoạ.
- Đồng bộ là có chờ, chờ là cùng làm việc với nhau cùng lúc,cùng đi chơi với nhau, cùng phối hợp ăn-rơ với nhau.
- Đồng bộ hoá công việc các tiến trình là tổ chức điều khiển công việc sao cho chúng làm việc với nhau cùng lúc, ăn khớp, có trước có sau để đảm bảo tính nhất quán, tính toàn vẹn của tài nguyên dùng chung, theo yêu cầu của ng sử dụng.
- Tài nguyên dùng chung là I/O, buffer, bộ nhớ và các tuyến trình truyền thống nặng cùng chia sẻ chạy chung với nhau. Vùng nhớ là các cùng tráo đổi với nhau khi làm việc.
VD: Bạn Dương Văn A lên bảng ghi < bộ nhớ dùng chung >. Nhưng khi lên bảng bạn đó đang viết tên mình, khi viết đến chữ Dương chưa xong, thì 1 bạn trong lớp chụp ảnh <nhà tiêu thụ>, như vậy nội dung bạn đã chụp hok đảm bảo tính nhất quán và tính toàn vẹn.
-Bên cạnh đó, một khía cạnh khác của đồng bộ hoá các tiến trình là tránh hiện tượng Deadlock ( hiện tượng kẹt tiến trình ).
VD: Hiện tượng kẹt xe, khi ở mức cao điểm thì không có xe nào đi đc, nhưng khi chú công an điều phối thì kẹt xe sẻ giảm đi đáng kể.
- Đồng bộ hoá công việc các tiến trình là tổ chức điều khiển công việc sao cho chúng làm việc với nhau cùng lúc, ăn khớp, có trước có sau để đảm bảo tính nhất quán, tính toàn vẹn của tài nguyên dùng chung, theo yêu cầu của ng sử dụng.
- Tài nguyên dùng chung là I/O, buffer, bộ nhớ và các tuyến trình truyền thống nặng cùng chia sẻ chạy chung với nhau. Vùng nhớ là các cùng tráo đổi với nhau khi làm việc.
VD: Bạn Dương Văn A lên bảng ghi < bộ nhớ dùng chung >. Nhưng khi lên bảng bạn đó đang viết tên mình, khi viết đến chữ Dương chưa xong, thì 1 bạn trong lớp chụp ảnh <nhà tiêu thụ>, như vậy nội dung bạn đã chụp hok đảm bảo tính nhất quán và tính toàn vẹn.
-Bên cạnh đó, một khía cạnh khác của đồng bộ hoá các tiến trình là tránh hiện tượng Deadlock ( hiện tượng kẹt tiến trình ).
VD: Hiện tượng kẹt xe, khi ở mức cao điểm thì không có xe nào đi đc, nhưng khi chú công an điều phối thì kẹt xe sẻ giảm đi đáng kể.
NguyenPhamTanPhat(113A)- Tổng số bài gửi : 22
Join date : 17/07/2012
Age : 37
HaHoangCongTien80 (113A)- Tổng số bài gửi : 22
Join date : 17/07/2012
Thế nào là loại trừ lẫn nhau?
- Giả sử có n tiến trình { P0, P1 , ... , Pn-1 }. Mỗi tiến trình có đoạn mã gọi là Đoạn tương tranh ( ĐTT ) trong đó tiến trình có thể truy cập và thay đổi vùng nhớ, tập tin hay tài nguyên chung.
- Tính Loại trừ lẫn nhau hay Loại trừ tương hỗ (Mutual Exclusion) về phương diện thời gian: Khi có 1 tiến trình đang ở trong ĐTT của nó thì không có tiến trình nào khác trong nhóm cũng tại đoạn như vậy, nghĩa là: Mỗi thời điểm chỉ có 1 tiến trình được phép truy cập và/hoặc thay đổi tài nguyên chung.
- Các tiến trình tương tranh có cấu trúc mã bao gồm Entry Section (Đoạn Đăng nhập), Critical Section (Đoạn Tương tranh), Exit Section (Đoạn Đăng xuất) và các Remainder Section (Đoạn Còn lại).
Ví Dụ Minh họa:
trong giờ kiểm tra môn hệ điều hành khi làm bài xong thầy gọi từng bạn lên nộp bài trong cùng lúc đó thì cũng có nhiều bạn lên nộp bài vì vậy các bạn đó phải chờ khi nào thầy gọi đèn lượt thỉ mới được nộp bài.
- Tính Loại trừ lẫn nhau hay Loại trừ tương hỗ (Mutual Exclusion) về phương diện thời gian: Khi có 1 tiến trình đang ở trong ĐTT của nó thì không có tiến trình nào khác trong nhóm cũng tại đoạn như vậy, nghĩa là: Mỗi thời điểm chỉ có 1 tiến trình được phép truy cập và/hoặc thay đổi tài nguyên chung.
- Các tiến trình tương tranh có cấu trúc mã bao gồm Entry Section (Đoạn Đăng nhập), Critical Section (Đoạn Tương tranh), Exit Section (Đoạn Đăng xuất) và các Remainder Section (Đoạn Còn lại).
Ví Dụ Minh họa:
trong giờ kiểm tra môn hệ điều hành khi làm bài xong thầy gọi từng bạn lên nộp bài trong cùng lúc đó thì cũng có nhiều bạn lên nộp bài vì vậy các bạn đó phải chờ khi nào thầy gọi đèn lượt thỉ mới được nộp bài.
dothanhnhan44 (113A)- Tổng số bài gửi : 17
Join date : 17/07/2012
Đồng bộ hóa tiến trình
là đồng bộ hóa các luồng ở bên trong của tiến trình, là biết cách điều khiển các luồng cho chúng ăn nhập với nhau có trước có sau để đảm bảo tính nhất quán và tính toàn vẹn của tài nguyên dùng chung,và đảm bảo theo yêu cầu của người dùng.
VD1:
Trong thư viện của trường học chỉ có 1 máy tính (tài nguyên dùng chung) , Sinh viên A vào sử dụng máy tính để nghiên cứu tư liệu .Sinh viên B vào sau muốn sừ dụng máy tính thì phài đợi SV A sử dụng xong mới dùng được .
VD2 :
Tong công ty , có 1 chiếc thang máy ( tài nguyên dùng chung ) , nhân viên A vào thang máy trước nên lên trước . Nhân viên B tới sau thì đợi lên sau .
VD1:
Trong thư viện của trường học chỉ có 1 máy tính (tài nguyên dùng chung) , Sinh viên A vào sử dụng máy tính để nghiên cứu tư liệu .Sinh viên B vào sau muốn sừ dụng máy tính thì phài đợi SV A sử dụng xong mới dùng được .
VD2 :
Tong công ty , có 1 chiếc thang máy ( tài nguyên dùng chung ) , nhân viên A vào thang máy trước nên lên trước . Nhân viên B tới sau thì đợi lên sau .
NguyenVuLinh12053_I11C- Tổng số bài gửi : 41
Join date : 07/08/2012
Re: Thảo luận Bài 7
TranThiThuyHang79 (113A) đã viết:VuMinhTan (113A) đã viết:đồng bộ hóa công việc của P1, P2, P3. sao cho:
a) P1 trước P2 và P3?
b) P1 và P2 trước P3?
ai hiểu rõ vấn đề này nói rõ dùm mình đc ko oa oa.........
a) thực hiện công việc đồng bộ sao cho P1 thực hiện trước nhất, sau đó đến P2 or P3 không phân biệt thứ tự ai vào trước thực hiện trước.
b) tương tự trên thực hiện sao cho P1 và P2 thi hành trước sau đó đến P3
cái đó thì mình bek nhưng mình ko hiểu cái chỗ s1 hay synal gì đó ...
VuMinhTan (113A)- Tổng số bài gửi : 29
Join date : 30/07/2012
Re: Thảo luận Bài 7
Nói đến "đồng bộ hóa" là phải có thời gian chờ.
VD: Trong 1 chương trình khuyến mãi giảm giá có nhiều người vào mua hàng thì mọi người phải xếp hàng chờ, chờ cho tới lượt mình mới được vào, lần lượt hết bạn A vào mua tới lượt bạn B vào.
VD: Trong 1 chương trình khuyến mãi giảm giá có nhiều người vào mua hàng thì mọi người phải xếp hàng chờ, chờ cho tới lượt mình mới được vào, lần lượt hết bạn A vào mua tới lượt bạn B vào.
nguyenchithuc(113A)- Tổng số bài gửi : 30
Join date : 02/08/2012
Age : 34
Tóm tắt nội dung bài 7
BÀI 7 :ĐỒNG BỘ HÓA TIẾN TRÌNH
1) Khải niệm
- Mục đích của việc đồng bộ hóa công việc là đảm bảo tình nhất quán của tài nguyên dùng chung và tránh dc hiện tượng DEAdLOCK
- Trở lại với vấn đề Sản Xuất – Tiêu thụ với giải pháp mới dùng biến đếm count
2) Vấn đề tương tranh
- Giả sử có n tiến trình . Mổi tiến trình có đoạn mã gọi là Đoạn tương tranh trong đó tiến trình có thể truy cập và thay đổi vùng nhớ ,tập tin hay tài nguyên chung
- Tình loại trừ lẫn nhau hay loại trừ tương hổ về phương diện thời gian : khi có 1 tiến trình đang ở trong đoạn tương tranh của nó thì không có tiến trình nào khác trong nhóm cũng tại đoạn như vậy , nghỉa là : Mỗi thời điểm chỉ có 1 tiến trình dc phép truy cập và thay đổi tài nguyên chung
- Các tiến trình có cấu trúc mã bao gồm : Đoạn đăng nhập ,Đoạn tương tranh , đoạn đăng xuất , đoạn còn lại
Vậy để giải quyết vấn đề này thì phải thỏa các ĐK sau :
Loại trừ lẫn nhau : Mỗi thời điểm chỉ có 1 tiến trình vận hành trong đoạn tương tranh
Tiến triển . Không có tiến trình nào phải chờ vô hạn tại Đoạn đăng nhập
3) Vấn đề thực thi đèn hiệu
- Loại đèn dùng biến đếm S kể trên dc gọi là Khóa xoay nghĩa là trong lệnh Wait vẫn có vòng lặp vô tận kiểm tra S có <= 0 hay không
- Để khắc phục nhược điểm của giải pháp chờ bận , có thể sửa định nghĩa tác nguyên Wait : thay vì chờ bận , tiến trình tự khóa mình , chuyển sang trậng thái Waiting , xếp vào hàng chờ đèn hiệu . Trình điều phối CPU có thể lựa chọn tiến trình khác trong hàng chờ Ready để thực hiện
- Khi 1 tiến trình nào đó dc thực hiện lệnh Signal một tiến trình P đang chờ tại S dc lựa chọn và đánh thức bằng lệnh Wake Up (p) để chuyển từ trạng thài Waiting sang Ready
4) DEADLOCK AND STARVATION
-Deadlock : tình huống bị kẹt của 1 nhóm tiến trình trong nhóm đều chờ 1 sự kiện có thể chỉ dc gây ra bởi 1 tiến trình khác trong nhóm
- Starvation : Chờ vô hạn tại đèn hiệu do các tiến trình dc rút khỏi hàng chờ theo quy tắc LIFO hoặc theo độ ưu tiên cao hơn
1) Khải niệm
- Mục đích của việc đồng bộ hóa công việc là đảm bảo tình nhất quán của tài nguyên dùng chung và tránh dc hiện tượng DEAdLOCK
- Trở lại với vấn đề Sản Xuất – Tiêu thụ với giải pháp mới dùng biến đếm count
2) Vấn đề tương tranh
- Giả sử có n tiến trình . Mổi tiến trình có đoạn mã gọi là Đoạn tương tranh trong đó tiến trình có thể truy cập và thay đổi vùng nhớ ,tập tin hay tài nguyên chung
- Tình loại trừ lẫn nhau hay loại trừ tương hổ về phương diện thời gian : khi có 1 tiến trình đang ở trong đoạn tương tranh của nó thì không có tiến trình nào khác trong nhóm cũng tại đoạn như vậy , nghỉa là : Mỗi thời điểm chỉ có 1 tiến trình dc phép truy cập và thay đổi tài nguyên chung
- Các tiến trình có cấu trúc mã bao gồm : Đoạn đăng nhập ,Đoạn tương tranh , đoạn đăng xuất , đoạn còn lại
Vậy để giải quyết vấn đề này thì phải thỏa các ĐK sau :
Loại trừ lẫn nhau : Mỗi thời điểm chỉ có 1 tiến trình vận hành trong đoạn tương tranh
Tiến triển . Không có tiến trình nào phải chờ vô hạn tại Đoạn đăng nhập
3) Vấn đề thực thi đèn hiệu
- Loại đèn dùng biến đếm S kể trên dc gọi là Khóa xoay nghĩa là trong lệnh Wait vẫn có vòng lặp vô tận kiểm tra S có <= 0 hay không
- Để khắc phục nhược điểm của giải pháp chờ bận , có thể sửa định nghĩa tác nguyên Wait : thay vì chờ bận , tiến trình tự khóa mình , chuyển sang trậng thái Waiting , xếp vào hàng chờ đèn hiệu . Trình điều phối CPU có thể lựa chọn tiến trình khác trong hàng chờ Ready để thực hiện
- Khi 1 tiến trình nào đó dc thực hiện lệnh Signal một tiến trình P đang chờ tại S dc lựa chọn và đánh thức bằng lệnh Wake Up (p) để chuyển từ trạng thài Waiting sang Ready
4) DEADLOCK AND STARVATION
-Deadlock : tình huống bị kẹt của 1 nhóm tiến trình trong nhóm đều chờ 1 sự kiện có thể chỉ dc gây ra bởi 1 tiến trình khác trong nhóm
- Starvation : Chờ vô hạn tại đèn hiệu do các tiến trình dc rút khỏi hàng chờ theo quy tắc LIFO hoặc theo độ ưu tiên cao hơn
LeDangBaoNgoc55 (113A)- Tổng số bài gửi : 15
Join date : 16/07/2012
Re: Thảo luận Bài 7
Thanks!
nguyendangnguyen43(i13a) đã viết:Khái niệm đèn hiệu
- Đèn hiệu là phương tiện đồng bộ hoá được E.W. Dijkstra đề xuất năm 1965.
- Đèn hiệu được mô tả bằng một biến kiểu nguyên với 2 tác nguyên là Wait (Chờ) và Signal (Báo hiệu):
typedef int semaphore; // Định nghĩa kiểu Đèn hiệu
wait (semaphore S)
{
while ( S <= 0 ); // Chờ bận nếu S<=0
S --; // Giảm S đi 1
}
signal (semaphore S)
{
S ++; // Tăng S lên 1
}
-Việc kiểm tra S <= 0 và giảm S (trong Wait) hoặc tăng S (trong Signal) phải được thực hiện trọn vẹn (không xảy ra ngắt trong thời gian thi hành), do đó Wait và Signal được gọi là các tác nguyên (Atomic Operations).
huynhquanghao_I92C- Tổng số bài gửi : 21
Join date : 15/11/2010
Re: Thảo luận Bài 7
Cái này sao giống trong WIKI MEDIA quá vậy.
Dù sao cũng thanks bạn nhiều. Thông tin bổ ích..
Dù sao cũng thanks bạn nhiều. Thông tin bổ ích..
NgoManhHung (113A) đã viết:_ Tên đầy đủ là Edsger Wybe Dijkstra, sinh ngày 11 tháng 5 năm 1930 tại Rotterdam, mất ngày 6 tháng 8 năm 2002 tại Nuenen sau một thời gian dài bị ung thư, ông là nhà khoa học máy tính Hà Lan.
_ Ông được nhận giải thưởng Turing cho các đóng góp có tính chất nền tảng trong lĩnh vực ngôn ngữ lập trình. Không lâu trước khi chết, ông đã được nhận giải Bài báo ảnh hưởng lớn trong lĩnh vực tính toán phân tán của ACM dành cho bài báo đã khởi đầu cho ngành con Tự ổn định. Sau khi ông qua đời, giải thưởng thường niên này đã được đổi tên thành giải thưởng ACM Edsger W. Dijkstra.
_ Dijkstra học vật lý lý thuyết tại Đại học Leiden, nhưng ông đã nhanh chóng nhận ra rằng ông quan tâm đến lập trình hơn.
_ Thời kỳ đầu, ông làm việc tại Trung tâm toán học, Viện nghiên cứu quốc gia về toán học và khoa học máy tính tại Amsterdam, ông còn giữ chức vị giáo sư tại Đại học Kỹ thuật Eindhoven, Hà Lan. Đầu thập kỷ 1970, ông làm cộng tác nghiên cứu tại Burroughs Corporation, sau đó giữ vị trí Schlumberger Centennial Chair ngành Khoa học máy tính tại Đại học Texas tại Austin, Mỹ. Ông nghỉ hưu năm 2000.
_ Trong các đóng góp của ông cho ngành khoa học máy tính có thuật toán đường đi ngắn nhất, còn được biết với tên Thuật toán Dijkstra, hệ điều hành THE và cấu trúc semaphore để phối hợp hoạt động của nhiều bộ vi xử lý và nhiều chương trình. Một khái niệm khác trong lĩnh vực tính toán phân tán đã được khởi đầu nhờ Dijkstra là self-stabilization - một cách khác để đảm bảo tính đáng tin cậy của hệ thống. Thuật toán Dijkstra được sử dụng trong SPF (Shortest Path First), dùng trong giao thức định tuyến OSPF (Open Shortest Path First).
_ Ông còn nổi tiếng với đánh giá thấp về lệnh GOTO trong lập trình máy tính. Bài báo năm 1968 "A Case against the GO TO Statement" (EWD215) được xem là một bước quan trọng tiến tới việc lệnh GOTO bị thay thế dần trên quy mô lớn bởi các cấu trúc lập trình chẳng hạn như vòng lặp while. Phương pháp này còn được gọi là Lập trình có cấu trúc. Dijkstra đã rất hâm mộ ngôn ngữ lập trình ALGOL 60, và đã làm việc trong nhóm cài đặt trình biên dịch đầu tiên cho ngôn ngữ này.
_ Từ những năm 1970, mối quan tâm chính của Dijkstra là kiểm định hình thức (formal verification).
_ Dijkstra còn nổi tiếng với các bài luận của ông về lập trình; ông là người đầu tiên tuyên bố rằng việc lập trình có đặc điểm cố hữu là khó khăn và phức tạp đến mức các lập trình viên cần phải khai thác mọi kỹ thuật và các phương pháp trừu tượng hóa có thể để hy vọng có thể quản lý được độ phức tạp của nó một cách thành công.Ông còn nổi tiếng với thói quen viết tay cẩn thận các bản thảo bằng bút máy. Các bản thảo này được gọi là EWD, do Dijkstra đánh số chúng bằng tiết đầu tố EWD. Ông thường phân phát các bản phô-tô của bản EWD mới cho các đồng nghiệp của mình; những người nhận được lại phô-tô và tiếp tục phân phát các bản sao, bằng cách đó các bản EWD được phát tán khắp cộng đồng khoa học máy tính quốc tế. Các chủ đề chính là về khoa học máy tính và toán học, ngoài ra còn có các báo cáo công tác, thư và các bài phát biểu. Hơn 1300 bài EWD đã được quét thành ảnh, số lượng được chuyển thành dạng điện tử để phục vụ nghiên cứu ngày càng tăng, chúng được lưu trữ và cung cấp trực tuyến tại Đại học Texas.
_ Dijkstra đã là một trong những người tiên phong trong nghiên cứu về tính toán phân tán. Có người còn cho là một số bài báo của ông đã thiết lập ngành nghiên cứu này.
_ Dijkstra còn được ghi nhận là cả đời chỉ sở hữu duy nhất một chiếc máy tính (vào cuối đời) và họa hoằn mới thực sự sử dụng nó, để đi đôi với quan niệm của ông rằng khoa học máy tính trừu tượng hơn chứ không chỉ là lập trình, quan niệm này được thể hiện trong nhiều câu nói nổi tiếng chẳng hạn như "Khoa học máy tính đối với máy tính cũng như thiên văn học đối với kính thiên văn".
_ Một năm sau khi ông mất, giải thưởng PODC Influential Paper Award in distributed computing (bài báo ảnh hưởng trong lĩnh vực tính toán phân tán) của tổ chức ACM (Association for Computing Machinery) đã được đổi tên thành Giải thưởng Dijkstra để vinh danh ông.
huynhquanghao_I92C- Tổng số bài gửi : 21
Join date : 15/11/2010
Re: Thảo luận Bài 7
- Code:
Sản xuất-Tiêu thụ
(đồng bộ bằng 2 đèn hiệu)
#include <stdio.h>
#include <conio.h>
#include <windows.h>
#define BUFFER_SIZE 10
int buffer[BUFFER_SIZE];
char s[BUFFER_SIZE];
int in=0;
int out=0;
int nextProduced=1;
HANDLE semEmpty, semFull; // Hai đèn hiệu
CRITICAL_SECTION critSec; // Biến kiểu Mutex
void Producer(void * p){
while (1){
// ... Sản xuất (nextProduced)
// Chờ đến khi có chỗ trống
WaitForSingleObject(semEmpty, INFINITE);
EnterCriticalSection(&critSec);
buffer[in]=nextProduced++;
switch ((int)p){
case 1:
s[in]=’P’;
break;
case 2:
s[in]=’p’;
break;
default:
s[in]=’S’;
};
in=(in+1)%BUFFER_SIZE;
// Tăng (semFull) lên 1
ReleaseSemaphore(semFull, 1, NULL);
LeaveCriticalSection(&critSec);
SuspendThread(GetCurrentThread());
}
}
void Consumer(){
int nextConsumed;
while (1){
// Chờ đến khi có sản phẩm
WaitForSingleObject(semFull, INFINITE);
EnterCriticalSection(&critSec);
nextConsumed=buffer[out];
out=(out+1)%BUFFER_SIZE;
// Tăng (semEmpty) lên 1
ReleaseSemaphore (semEmpty, 1, NULL);
LeaveCriticalSection(&critSec);
// ... Tiêu thụ (nextConsumed)
SuspendThread(GetCurrentThread());
}
}
void ShowBuffer(){ // In nội dung bộ đệm
const char * LeftMargin="\n ";
int i;
printf(LeftMargin);
for(i=0; i<(in*5); i++) putchar(' '); printf("!in");
printf(LeftMargin);
for (i=0; i<BUFFER_SIZE-1; i++)
printf("%c%2d, ", s[i], buffer[i]);
printf("%c%2d", s[BUFFER_SIZE-1], buffer[BUFFER_SIZE-1]);
printf(LeftMargin);
for(i=0; i<(out*5); i++) putchar(' ');
printf("^out");
printf("\n");
}
int main(){
HANDLE ProducerHandle1, ProducerHandle2;
HANDLE ConsumerHandle1, ConsumerHandle2;
DWORD ProducerID1, ProducerID2;
DWORD ConsumerID1, ConsumerID2;
semEmpty=CreateSemaphore(0, BUFFER_SIZE, BUFFER_SIZE, 0);
semFull=CreateSemaphore(0, 0, BUFFER_SIZE, 0);
InitializeCriticalSection(&critSec);
// Tạo các luồng nhưng ở trạng thái ngủ (Suspend)
ProducerHandle1=CreateThread(0,0,
(LPTHREAD_START_ROUTINE)Producer, (void *) 1, 4, &ProducerID1);
ProducerHandle2=CreateThread(0,0,
(LPTHREAD_START_ROUTINE)Producer, (void *) 2, 4, &ProducerID2);
ConsumerHandle1=CreateThread(0,0,
(LPTHREAD_START_ROUTINE)Consumer, 0, 4, &ConsumerID1);
ConsumerHandle2=CreateThread(0,0,
(LPTHREAD_START_ROUTINE)Consumer, 0, 4, &ConsumerID2);
while(1)
{
printf("\n- Nhấn P/p để sản xuất, C/c để tiêu thụ:");
switch (getch()){
case 'P': // Đánh thức luồng SX 1
ResumeThread(ProducerHandle1);
break;
case 'p': // Đánh thức luồng SX 2
ResumeThread(ProducerHandle2);
break;
case 'C': // Đánh thức luồng TT 1
ResumeThread(ConsumerHandle1);
break;
case 'c': // Đánh thức luồng TT 2
ResumeThread(ConsumerHandle2);
break;
case '0': // Kết thúc ứng dụng
printf("\n");
CloseHandle(semEmpty);
CloseHandle(semFull);
DeleteCriticalSection(&critSec);
return 0;
}
EnterCriticalSection(&critSec);
ShowBuffer();
LeaveCriticalSection(&critSec);
}
}
Code bài hôm nay mọi người tìm hiểu nào
Trannguyenkhoa26 (113A)- Tổng số bài gửi : 35
Join date : 16/07/2012
Age : 35
PHÁT BIỂU BÀI TOÁN SẢN XUẤT - TIÊU THỤ VỚI THUẬT GIẢI ĐỒNG BỘ HÓA BẰNG 3 ĐÈN HIỆU "semFull, semEmpty và Mutex" BẰNG C# 2005
Code C# 2005 bài toán sản xuất - tiêu thụ với thuật giải đồng bộ hoá bằng 3 đèn hiệu "semFull, semEmpty và Mutex" của thầy !
* Form BufferState :(frmBufferState.cs)
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
using System.Threading;
namespace SanXuatTieuThu2005
{
public partial class frmBufferState : Form
{
public frmBufferState()
{
InitializeComponent();
}
int topLblIn, topLblOut;
private void frmBufferState_Load(object sender, EventArgs e)
{
topLblIn = this.lblIn.Top;
topLblOut = this.lblOut.Top;
}
private void timer1_Tick(object sender, EventArgs e)
{
Program.mutex.WaitOne();
for (int i = 0; i < Program.BUFFER_SIZE; i++)
{
this.Controls["txtItem"+i.ToString()].Text = "S"+Program.buffer[i].ToString();
this.Controls["txtProducer" + i.ToString()].Text = "P" + Program.s[i].ToString();
}
lblIn.Top = this.Controls["txtItem" + Program.ptrIn.ToString()].Top;
lblOut.Top = this.Controls["txtItem" + Program.ptrOut.ToString()].Top;
Program.mutex.ReleaseMutex();
}
}
}
*Form Panel (frmPanel.cs)
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
using System.Threading;// dùng cho Semaphore
namespace SanXuatTieuThu2005
{
public partial class frmPanel : Form
{
public frmPanel()
{
InitializeComponent();
}
// hai mảng luồng
Thread[] thrConsumers = new Thread[Program.numConsumers];
Thread[] thrProducers = new Thread[Program.numProducers];
// ko cần HANDLE
Semaphore semEmpty, semFull;// chứa đối tượng thuộc lớp Semaphore (đèn hiệu), không dùng HANDLE
// C# ko dùng biến con trỏ
int NextProduced;
int NextConsumed;
private void btnStart_Click(object sender, EventArgs e)
{
(new frmBufferState()).Show();
NextProduced = 1;
semEmpty = new Semaphore(Program.BUFFER_SIZE, Program.BUFFER_SIZE, "E");// đèn hiệu có tên E
semFull = new Semaphore(0, Program.BUFFER_SIZE, "F");// đèn hiệu có tên F
Program.mutex = new Mutex();
for (int i = 0; i < Program.numProducers; i++)
{
thrProducers[i] = new Thread(new ParameterizedThreadStart(Producer));
thrProducers[i].Priority = ThreadPriority.Normal;
thrProducers[i].Start(i);
}
for (int i = 0; i < Program.numConsumers; i++)
{
thrConsumers[i] = new Thread(new ParameterizedThreadStart(Consumer));
thrConsumers[i].Priority = ThreadPriority.Normal;
thrConsumers[i].Start(i);
}
}
public void Producer(object id)
{
while(true)
{
Thread.Sleep((int)(DateTime.Now.Ticks % 2000));
semEmpty.WaitOne();// chờ tại đèn hiệu semEmpty
//WaitOne - chờ một lát
Program.mutex.WaitOne();// xin phép vào đoạn tương tranh
Program.buffer[Program.ptrIn] = NextProduced++;
Program.s[Program.ptrIn] = ((int)id) + 1;
Program.ptrIn = (Program.ptrIn + 1) % Program.BUFFER_SIZE;
semFull.Release();
Program.mutex.ReleaseMutex();
}
}
public void Consumer(object id)
{
while (true)
{
Thread.Sleep((int)(DateTime.Now.Ticks % 1500));
semFull.WaitOne();
Program.mutex.WaitOne();
NextConsumed = Program.buffer[Program.ptrOut];
Program.ptrOut = (Program.ptrOut + 1) % Program.BUFFER_SIZE;
semEmpty.Release();
Program.mutex.ReleaseMutex();
}
}
private void btnSuspend_Click(object sender, EventArgs e)
{
for (int i = 0; i < Program.numProducers; i++)
{
thrProducers[i].Suspend();
}
for (int i = 0; i < Program.numConsumers; i++)
{
thrConsumers[i].Suspend();
}
btnProducer1.ForeColor = Color.Gray;
}
private void btnResume_Click(object sender, EventArgs e)
{
for (int i = 0; i < Program.numProducers; i++)
{
if (thrProducers[i].ThreadState == ThreadState.Suspended)
thrProducers[i].Resume();
}
for (int i = 0; i < Program.numConsumers; i++)
{
if (thrConsumers[i].ThreadState == ThreadState.Suspended)
thrConsumers[i].Resume();
}
btnProducer1.ForeColor = Color.Black;
}
private void frmPanel_FormClosing(object sender, FormClosingEventArgs e)
{
try
{
for (int i = 0; i < Program.numProducers; i++)
{
if (thrProducers[i].ThreadState == ThreadState.Suspended)
thrProducers[i].Resume();
thrProducers[i].Abort();
}
for (int i = 0; i < Program.numConsumers; i++)
{
if (thrConsumers[i].ThreadState == ThreadState.Suspended)
thrConsumers[i].Resume();
thrConsumers[i].Abort();
}
}
catch (Exception e1) { }
}
private void btnProducer1_Click(object sender, EventArgs e)
{
if (thrProducers[0].ThreadState == ThreadState.Suspended)
{
thrProducers[0].Resume();
btnProducer1.ForeColor = Color.Black;
}
else
{
thrProducers[0].Suspend();
btnProducer1.ForeColor = Color.Gray;
}
btnProducer1.Refresh();
}
private void frmPanel_Load(object sender, EventArgs e)
{
}
}
}
* Program.cs
using System;
using System.Collections.Generic;
using System.Windows.Forms;
using System.Threading;
namespace SanXuatTieuThu2005
{
static class Program
{
///
/// The main entry point for the application.
///
[STAThread]
static void Main()
{
Application.EnableVisualStyles();
Application.SetCompatibleTextRenderingDefault(false);
Application.Run(new frmPanel());
}
// toàn bộ là tài nguyên dùng chung
public const int BUFFER_SIZE = 10;
public const int numProducers = 6;
public const int numConsumers = 4;
public static int[] buffer = new int[BUFFER_SIZE];
public static int[] s = new int[BUFFER_SIZE];
public static int ptrIn = 0, ptrOut = 0; // hai con trỏ In và Out
public static Mutex mutex; // đèn hiệu mutex
}
}
* Form BufferState :(frmBufferState.cs)
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
using System.Threading;
namespace SanXuatTieuThu2005
{
public partial class frmBufferState : Form
{
public frmBufferState()
{
InitializeComponent();
}
int topLblIn, topLblOut;
private void frmBufferState_Load(object sender, EventArgs e)
{
topLblIn = this.lblIn.Top;
topLblOut = this.lblOut.Top;
}
private void timer1_Tick(object sender, EventArgs e)
{
Program.mutex.WaitOne();
for (int i = 0; i < Program.BUFFER_SIZE; i++)
{
this.Controls["txtItem"+i.ToString()].Text = "S"+Program.buffer[i].ToString();
this.Controls["txtProducer" + i.ToString()].Text = "P" + Program.s[i].ToString();
}
lblIn.Top = this.Controls["txtItem" + Program.ptrIn.ToString()].Top;
lblOut.Top = this.Controls["txtItem" + Program.ptrOut.ToString()].Top;
Program.mutex.ReleaseMutex();
}
}
}
*Form Panel (frmPanel.cs)
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
using System.Threading;// dùng cho Semaphore
namespace SanXuatTieuThu2005
{
public partial class frmPanel : Form
{
public frmPanel()
{
InitializeComponent();
}
// hai mảng luồng
Thread[] thrConsumers = new Thread[Program.numConsumers];
Thread[] thrProducers = new Thread[Program.numProducers];
// ko cần HANDLE
Semaphore semEmpty, semFull;// chứa đối tượng thuộc lớp Semaphore (đèn hiệu), không dùng HANDLE
// C# ko dùng biến con trỏ
int NextProduced;
int NextConsumed;
private void btnStart_Click(object sender, EventArgs e)
{
(new frmBufferState()).Show();
NextProduced = 1;
semEmpty = new Semaphore(Program.BUFFER_SIZE, Program.BUFFER_SIZE, "E");// đèn hiệu có tên E
semFull = new Semaphore(0, Program.BUFFER_SIZE, "F");// đèn hiệu có tên F
Program.mutex = new Mutex();
for (int i = 0; i < Program.numProducers; i++)
{
thrProducers[i] = new Thread(new ParameterizedThreadStart(Producer));
thrProducers[i].Priority = ThreadPriority.Normal;
thrProducers[i].Start(i);
}
for (int i = 0; i < Program.numConsumers; i++)
{
thrConsumers[i] = new Thread(new ParameterizedThreadStart(Consumer));
thrConsumers[i].Priority = ThreadPriority.Normal;
thrConsumers[i].Start(i);
}
}
public void Producer(object id)
{
while(true)
{
Thread.Sleep((int)(DateTime.Now.Ticks % 2000));
semEmpty.WaitOne();// chờ tại đèn hiệu semEmpty
//WaitOne - chờ một lát
Program.mutex.WaitOne();// xin phép vào đoạn tương tranh
Program.buffer[Program.ptrIn] = NextProduced++;
Program.s[Program.ptrIn] = ((int)id) + 1;
Program.ptrIn = (Program.ptrIn + 1) % Program.BUFFER_SIZE;
semFull.Release();
Program.mutex.ReleaseMutex();
}
}
public void Consumer(object id)
{
while (true)
{
Thread.Sleep((int)(DateTime.Now.Ticks % 1500));
semFull.WaitOne();
Program.mutex.WaitOne();
NextConsumed = Program.buffer[Program.ptrOut];
Program.ptrOut = (Program.ptrOut + 1) % Program.BUFFER_SIZE;
semEmpty.Release();
Program.mutex.ReleaseMutex();
}
}
private void btnSuspend_Click(object sender, EventArgs e)
{
for (int i = 0; i < Program.numProducers; i++)
{
thrProducers[i].Suspend();
}
for (int i = 0; i < Program.numConsumers; i++)
{
thrConsumers[i].Suspend();
}
btnProducer1.ForeColor = Color.Gray;
}
private void btnResume_Click(object sender, EventArgs e)
{
for (int i = 0; i < Program.numProducers; i++)
{
if (thrProducers[i].ThreadState == ThreadState.Suspended)
thrProducers[i].Resume();
}
for (int i = 0; i < Program.numConsumers; i++)
{
if (thrConsumers[i].ThreadState == ThreadState.Suspended)
thrConsumers[i].Resume();
}
btnProducer1.ForeColor = Color.Black;
}
private void frmPanel_FormClosing(object sender, FormClosingEventArgs e)
{
try
{
for (int i = 0; i < Program.numProducers; i++)
{
if (thrProducers[i].ThreadState == ThreadState.Suspended)
thrProducers[i].Resume();
thrProducers[i].Abort();
}
for (int i = 0; i < Program.numConsumers; i++)
{
if (thrConsumers[i].ThreadState == ThreadState.Suspended)
thrConsumers[i].Resume();
thrConsumers[i].Abort();
}
}
catch (Exception e1) { }
}
private void btnProducer1_Click(object sender, EventArgs e)
{
if (thrProducers[0].ThreadState == ThreadState.Suspended)
{
thrProducers[0].Resume();
btnProducer1.ForeColor = Color.Black;
}
else
{
thrProducers[0].Suspend();
btnProducer1.ForeColor = Color.Gray;
}
btnProducer1.Refresh();
}
private void frmPanel_Load(object sender, EventArgs e)
{
}
}
}
* Program.cs
using System;
using System.Collections.Generic;
using System.Windows.Forms;
using System.Threading;
namespace SanXuatTieuThu2005
{
static class Program
{
///
/// The main entry point for the application.
///
[STAThread]
static void Main()
{
Application.EnableVisualStyles();
Application.SetCompatibleTextRenderingDefault(false);
Application.Run(new frmPanel());
}
// toàn bộ là tài nguyên dùng chung
public const int BUFFER_SIZE = 10;
public const int numProducers = 6;
public const int numConsumers = 4;
public static int[] buffer = new int[BUFFER_SIZE];
public static int[] s = new int[BUFFER_SIZE];
public static int ptrIn = 0, ptrOut = 0; // hai con trỏ In và Out
public static Mutex mutex; // đèn hiệu mutex
}
}
LePhamTuanVu02 (113A)- Tổng số bài gửi : 9
Join date : 19/07/2012
Câu 1 : Trình bày mục đích đồng bộ hóa công việc các tiến trình.Ví dụ?
Đồng bộ hóa các tiến trình là quản lý công việc của luồng và tiến trình một cách hợp lý nhất và đáp ứng được yêu cầu.
Mục đích đồng bộ hóa các tiến trình.
- Đảm bảo tính nhất quán của tài nguyên dùng chung.
Ví dụ: bài toán sản xuất tiêu thụ một
bạn trong lớp lên bảng làm bài (tài nguyên dùng chung của lớp), khi bạn trên bảng chưa làm xong bài toàn thì bạn phía dưới nghi lại thông tin là sai. Muốn nghi đúng bài tập đang làm thì bạn phía dưới phải đợi bạn trên bảng làm xong rồi mới nghi lại dầy đủ.
- Tránh Deadlock ( hiện tượng kẹt tiến trình).
Ví dụ: hiện tượng kẹt xe khi có cảnh sát giao thông điều tiết phân tuyến đường (luồng) thì sẽ không còn kẹt xe nữa.
Mục đích đồng bộ hóa các tiến trình.
- Đảm bảo tính nhất quán của tài nguyên dùng chung.
Ví dụ: bài toán sản xuất tiêu thụ một
bạn trong lớp lên bảng làm bài (tài nguyên dùng chung của lớp), khi bạn trên bảng chưa làm xong bài toàn thì bạn phía dưới nghi lại thông tin là sai. Muốn nghi đúng bài tập đang làm thì bạn phía dưới phải đợi bạn trên bảng làm xong rồi mới nghi lại dầy đủ.
- Tránh Deadlock ( hiện tượng kẹt tiến trình).
Ví dụ: hiện tượng kẹt xe khi có cảnh sát giao thông điều tiết phân tuyến đường (luồng) thì sẽ không còn kẹt xe nữa.
LamVuThai (113A)- Tổng số bài gửi : 41
Join date : 16/07/2012
Giải thích hàm mới
*SemEmpty: là biến dùng chứa mục quản của đèn hiệu, đèn này quản lý số vùng trống trong bộ đệm
*SemFull: là biến dùng chứa mục quản của đèn hiệu, đèn này quản lý số sản phẩm trong bộ đệm.
*CritSec: là biến đối tượng thuộc lớp CRITICAL_SECTION. Đây chính là biến kiểu Mutex (đèn hiệu nhị phân) dùng để bảo vệ đoạn tương tranh trong ứng dụng thứ nhất của đèn hiệu.
Code sản xuất - tiêu thụ viết bằng cách mới:
Producer:
wait(SemEmpty)
............................
signal(SemFull)
Consumer:
wait(SemFull)
...........................
signal(SemEmpty)
*SemFull: là biến dùng chứa mục quản của đèn hiệu, đèn này quản lý số sản phẩm trong bộ đệm.
*CritSec: là biến đối tượng thuộc lớp CRITICAL_SECTION. Đây chính là biến kiểu Mutex (đèn hiệu nhị phân) dùng để bảo vệ đoạn tương tranh trong ứng dụng thứ nhất của đèn hiệu.
Code sản xuất - tiêu thụ viết bằng cách mới:
Producer:
wait(SemEmpty)
............................
signal(SemFull)
Consumer:
wait(SemFull)
...........................
signal(SemEmpty)
Trannguyenkhoa26 (113A)- Tổng số bài gửi : 35
Join date : 16/07/2012
Age : 35
Thực thi đèn hiệu trong Windows
CreateSemaphore : là khởi tạo semaphore.
WaitForSingleObject : là đợi chờ 1 đối tượng.
* max : là giá trị tối đa của đèn hiệu.
* t : là tên đèn hiệu.
- [_]Nếu t=0 trong CreateSemaphore thì đèn hiệu tương ứng sẽ là đèn hiệu không tên, còn gọi là đèn hiệu nội tiến trình và chỉ được dùng để báo hiệu giữa các luồng bên trong 1 tiến trình mà thôi ( giống điện thoại nội hạt hay điện thoại nội bộ 1 công ty).
- [_] Nếu t là 1 chuỗi kí tự dạng "Tên đèn hiệu" thì đèn hiệu tương ứng là đèn hiệu có tên và thường gọi là đèn hiệu liên tiến trình (như điện thoại liên tỉnh, đường dài).
* timeout : thời gian chờ, nếu hết thời gian này mà đèn chưa xanh, thì qua được lệnh chờ này.
- VD : Xe lên cầu : wait (s,5000); //sau 5 giây mà đèn vẫn đỏ, thì xe này được lên cầu.
ReleaseSemaphore : là rời khỏi semaphore.
* 1 : giá trị của đèn hiệu sẽ tăng lên 1, tùy theo yêu cầu, có thể là 2, 3,... (phụ thuộc vào max cho phép).
* Tên biến nguyên Z nào đó ở vị trí NULL : lấy giá trị đèn hiệu trước khi tăng lên 1 để đưa vào biến Z.
NgoManhHung (113A)- Tổng số bài gửi : 8
Join date : 20/07/2012
Bài toán Producer - Consumer được đồng bộ bằng 2 đèn viết bằng C++
Đèn hiệu nhị phân có thể được thực thi bằng Critical Section hoặc đối tượng Mutex
#include
#include
#include
#define BUFFER_SIZE 10
int buffer[BUFFER_SIZE];
char s[BUFFER_SIZE];
int in=0;
int out=0;
int nextProduced=1;
HANDLE semEmpty, semFull; // Hai đèn hiệu
CRITICAL_SECTION critSec; // Biến kiểu Mutex
void Producer(void * p){
while (1){
// ... Sản xuất (nextProduced)
// Chờ đến khi có chỗ trống
WaitForSingleObject(semEmpty, INFINITE);
EnterCriticalSection(&critSec);
buffer[in]=nextProduced++;
switch ((int)p){
case 1:
s[in]=’P’;
break;
case 2:
s[in]=’p’;
break;
default:
s[in]=’S’;
};
in=(in+1)%BUFFER_SIZE;
// Tăng (semFull) lên 1
ReleaseSemaphore(semFull, 1, NULL);
LeaveCriticalSection(&critSec);
SuspendThread(GetCurrentThread());
}
}
void Consumer(){
int nextConsumed;
while (1){
// Chờ đến khi có sản phẩm
WaitForSingleObject(semFull, INFINITE);
EnterCriticalSection(&critSec);
nextConsumed=buffer[out];
out=(out+1)%BUFFER_SIZE;
// Tăng (semEmpty) lên 1
ReleaseSemaphore (semEmpty, 1, NULL);
LeaveCriticalSection(&critSec);
// ... Tiêu thụ (nextConsumed)
SuspendThread(GetCurrentThread());
}
}
void ShowBuffer(){ // In nội dung bộ đệm
const char * LeftMargin="\n ";
int i;
printf(LeftMargin);
for(i=0; i<(in*5); i++) putchar(' '); printf("!in");
printf(LeftMargin);
for (i=0; i printf("%c%2d, ", s[i], buffer[i]);
printf("%c%2d", s[BUFFER_SIZE-1], buffer[BUFFER_SIZE-1]);
printf(LeftMargin);
for(i=0; i<(out*5); i++) putchar(' ');
printf("^out");
printf("\n");
}
int main(){
HANDLE ProducerHandle1, ProducerHandle2;
HANDLE ConsumerHandle1, ConsumerHandle2;
DWORD ProducerID1, ProducerID2;
DWORD ConsumerID1, ConsumerID2;
semEmpty=CreateSemaphore(0, BUFFER_SIZE, BUFFER_SIZE, 0);
semFull=CreateSemaphore(0, 0, BUFFER_SIZE, 0);
InitializeCriticalSection(&critSec);
// Tạo các luồng nhưng ở trạng thái ngủ (Suspend)
ProducerHandle1=CreateThread(0,0,(LPTHREAD_START_ROUTINE)Producer, (void *) 1, 4, &ProducerID1);
ProducerHandle2=CreateThread(0,0,(LPTHREAD_START_ROUTINE)Producer, (void *) 2, 4, &ProducerID2);
ConsumerHandle1=CreateThread(0,0,(LPTHREAD_START_ROUTINE)Consumer, 0, 4, &ConsumerID1);
ConsumerHandle2=CreateThread(0,0,(LPTHREAD_START_ROUTINE)Consumer, 0, 4, &ConsumerID2);
while(1)
{
printf("\n- Nhấn P/p để sản xuất, C/c để tiêu thụ:");
switch (getch()){
case 'P': // Đánh thức luồng SX 1
ResumeThread(ProducerHandle1);
break;
case 'p': // Đánh thức luồng SX 2
ResumeThread(ProducerHandle2);
break;
case 'C': // Đánh thức luồng TT 1
ResumeThread(ConsumerHandle1);
break;
case 'c': // Đánh thức luồng TT 2
ResumeThread(ConsumerHandle2);
break;
case '0': // Kết thúc ứng dụng
printf("\n");
CloseHandle(semEmpty);
CloseHandle(semFull);
DeleteCriticalSection(&critSec);
return 0;
}
EnterCriticalSection(&critSec);
ShowBuffer();
LeaveCriticalSection(&critSec);
}
}
#include
#include
#include
#define BUFFER_SIZE 10
int buffer[BUFFER_SIZE];
char s[BUFFER_SIZE];
int in=0;
int out=0;
int nextProduced=1;
HANDLE semEmpty, semFull; // Hai đèn hiệu
CRITICAL_SECTION critSec; // Biến kiểu Mutex
- _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
void Producer(void * p){
while (1){
// ... Sản xuất (nextProduced)
// Chờ đến khi có chỗ trống
WaitForSingleObject(semEmpty, INFINITE);
EnterCriticalSection(&critSec);
buffer[in]=nextProduced++;
switch ((int)p){
case 1:
s[in]=’P’;
break;
case 2:
s[in]=’p’;
break;
default:
s[in]=’S’;
};
in=(in+1)%BUFFER_SIZE;
// Tăng (semFull) lên 1
ReleaseSemaphore(semFull, 1, NULL);
LeaveCriticalSection(&critSec);
SuspendThread(GetCurrentThread());
}
}
- _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
void Consumer(){
int nextConsumed;
while (1){
// Chờ đến khi có sản phẩm
WaitForSingleObject(semFull, INFINITE);
EnterCriticalSection(&critSec);
nextConsumed=buffer[out];
out=(out+1)%BUFFER_SIZE;
// Tăng (semEmpty) lên 1
ReleaseSemaphore (semEmpty, 1, NULL);
LeaveCriticalSection(&critSec);
// ... Tiêu thụ (nextConsumed)
SuspendThread(GetCurrentThread());
}
}
- _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
void ShowBuffer(){ // In nội dung bộ đệm
const char * LeftMargin="\n ";
int i;
printf(LeftMargin);
for(i=0; i<(in*5); i++) putchar(' '); printf("!in");
printf(LeftMargin);
for (i=0; i
printf("%c%2d", s[BUFFER_SIZE-1], buffer[BUFFER_SIZE-1]);
printf(LeftMargin);
for(i=0; i<(out*5); i++) putchar(' ');
printf("^out");
printf("\n");
}
- _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _ _
int main(){
HANDLE ProducerHandle1, ProducerHandle2;
HANDLE ConsumerHandle1, ConsumerHandle2;
DWORD ProducerID1, ProducerID2;
DWORD ConsumerID1, ConsumerID2;
semEmpty=CreateSemaphore(0, BUFFER_SIZE, BUFFER_SIZE, 0);
semFull=CreateSemaphore(0, 0, BUFFER_SIZE, 0);
InitializeCriticalSection(&critSec);
// Tạo các luồng nhưng ở trạng thái ngủ (Suspend)
ProducerHandle1=CreateThread(0,0,(LPTHREAD_START_ROUTINE)Producer, (void *) 1, 4, &ProducerID1);
ProducerHandle2=CreateThread(0,0,(LPTHREAD_START_ROUTINE)Producer, (void *) 2, 4, &ProducerID2);
ConsumerHandle1=CreateThread(0,0,(LPTHREAD_START_ROUTINE)Consumer, 0, 4, &ConsumerID1);
ConsumerHandle2=CreateThread(0,0,(LPTHREAD_START_ROUTINE)Consumer, 0, 4, &ConsumerID2);
while(1)
{
printf("\n- Nhấn P/p để sản xuất, C/c để tiêu thụ:");
switch (getch()){
case 'P': // Đánh thức luồng SX 1
ResumeThread(ProducerHandle1);
break;
case 'p': // Đánh thức luồng SX 2
ResumeThread(ProducerHandle2);
break;
case 'C': // Đánh thức luồng TT 1
ResumeThread(ConsumerHandle1);
break;
case 'c': // Đánh thức luồng TT 2
ResumeThread(ConsumerHandle2);
break;
case '0': // Kết thúc ứng dụng
printf("\n");
CloseHandle(semEmpty);
CloseHandle(semFull);
DeleteCriticalSection(&critSec);
return 0;
}
EnterCriticalSection(&critSec);
ShowBuffer();
LeaveCriticalSection(&critSec);
}
}
NgoManhHung (113A)- Tổng số bài gửi : 8
Join date : 20/07/2012
ví dụ minh hoạ của đồng bộ hoá tiến trình
1 cặp nam nữ A và B đến tiệm ảnh cưới của C để chụp hình cưới.
cả A và B cùng nhau vào thay đồ cưới.Chú rể A thay xong quần áo cưới trước cô dâu B nhưng cũng không được chụp hình vì phải đợi cô dâu B thay xong và cả 2 cùng nhau chụp hình.
cả A và B cùng nhau vào thay đồ cưới.Chú rể A thay xong quần áo cưới trước cô dâu B nhưng cũng không được chụp hình vì phải đợi cô dâu B thay xong và cả 2 cùng nhau chụp hình.
VuongXuongThong (113A)- Tổng số bài gửi : 20
Join date : 17/07/2012
Re: Thảo luận Bài 7
Khái niệm về đồng bộ hóa tiến trình
Đồng bộ hóa tiến trình là đồng bộ hóa các luồng ở bên trong của tiến trình, là biết cách điều khiển các luồng cho chúng ăn nhập với nhau có trước có sau để đảm bảo tính nhất quán và tính toàn vẹn của tài nguyên dùng chung,và đảm bảo theo yêu cầu của người dùng.
Tài nguyên dùng chung trong bài toán sản xuất tiêu thụ là Buffer, các biến In,Out
Ví dụ BUFFER_SIZE 10
Tài nguyên dùng chung là vùng nhớ để chúng trao đổi thông tin với nhau.
Tránh được hiện tượng Deadlock.
Trở lại vấn đề bài toán sản xuất – tiêu thụ với giải pháp mới dùng biến đếm Count.
Cấu trúc bộ nhớ đệm chung.
#define BUFFER_SIZE 10
typedef struct {
. . . // Mô tả các thành phần của 1 khoang chứa
} item;
item buffer [BUFFER_SIZE]; // Bộ nhớ đệm.
int in = 0; // Con trỏ tới vị trí trống kế kiếp.
int out = 0; // Con trỏ tới vị trí lấy tiếp theo.
int count= 0;// Đếm số sản phẩm có trong Buffer.
Đồng bộ hóa tiến trình là đồng bộ hóa các luồng ở bên trong của tiến trình, là biết cách điều khiển các luồng cho chúng ăn nhập với nhau có trước có sau để đảm bảo tính nhất quán và tính toàn vẹn của tài nguyên dùng chung,và đảm bảo theo yêu cầu của người dùng.
Tài nguyên dùng chung trong bài toán sản xuất tiêu thụ là Buffer, các biến In,Out
Ví dụ BUFFER_SIZE 10
Tài nguyên dùng chung là vùng nhớ để chúng trao đổi thông tin với nhau.
Tránh được hiện tượng Deadlock.
Trở lại vấn đề bài toán sản xuất – tiêu thụ với giải pháp mới dùng biến đếm Count.
Cấu trúc bộ nhớ đệm chung.
#define BUFFER_SIZE 10
typedef struct {
. . . // Mô tả các thành phần của 1 khoang chứa
} item;
item buffer [BUFFER_SIZE]; // Bộ nhớ đệm.
int in = 0; // Con trỏ tới vị trí trống kế kiếp.
int out = 0; // Con trỏ tới vị trí lấy tiếp theo.
int count= 0;// Đếm số sản phẩm có trong Buffer.
DoVanTan(113A)- Tổng số bài gửi : 26
Join date : 16/07/2012
Age : 35
Đến từ : Trà Vinh
Re: Thảo luận Bài 7
4 điều kiện cần dẫn đến deadlock
-Loại trừ lẫn nhau (Multual Exclusion): Ít nhất có 1 tài nguyên có tính không chia sẻ (non-shareable), nghĩa là mỗi thời điểm chỉ có một tiến trình được sử dụng nó.
- Giữ và chờ (Hold and Wait): Có 1 tiến trình đang giữ tài nguyên và xin thêm tài nguyên đang bị độc chiếm bởi tiến trình khác.
- Không có tiếm quyền (No Preemption): Tài nguyên đang giữ bởi tiến trình không thể bị tiếm quyền mà phải được tiến trình này tự nguyện trả lại hệ thống sau khi dùng xong.
- Chờ xoay vòng (Circular Wait): Giả sử có n tiến trình đang chờ tài nguyên là {P1,P2…Pn}, khi đó P1 chờ TN giữ bởi P2, tiến trình P2 chờ TN giữ bởi P3, …, Pn chờ P1.
-Loại trừ lẫn nhau (Multual Exclusion): Ít nhất có 1 tài nguyên có tính không chia sẻ (non-shareable), nghĩa là mỗi thời điểm chỉ có một tiến trình được sử dụng nó.
- Giữ và chờ (Hold and Wait): Có 1 tiến trình đang giữ tài nguyên và xin thêm tài nguyên đang bị độc chiếm bởi tiến trình khác.
- Không có tiếm quyền (No Preemption): Tài nguyên đang giữ bởi tiến trình không thể bị tiếm quyền mà phải được tiến trình này tự nguyện trả lại hệ thống sau khi dùng xong.
- Chờ xoay vòng (Circular Wait): Giả sử có n tiến trình đang chờ tài nguyên là {P1,P2…Pn}, khi đó P1 chờ TN giữ bởi P2, tiến trình P2 chờ TN giữ bởi P3, …, Pn chờ P1.
DoVanTan(113A)- Tổng số bài gửi : 26
Join date : 16/07/2012
Age : 35
Đến từ : Trà Vinh
Re: Thảo luận Bài 7
Định nghĩa | Thực thi trong Visual C |
typedef int semaphore; semaphore s = n; | HANDLE s;// khai báo biến semaphore với kiểu mục quản s=CreateSemaphore (0, n, max, t);// // t - tên đèn hiệu hoặc 0 //n: giá trị ban đầu của đèn hiệu //max: giá trị tối đa của đèn hiệu |
wait (s); | WaitForSingleObject (s, timeout); /* timeout = INFINITE hoặc số ms chờ |
signal (s); | ReleaseSemaphore (s, 1, NULL); |
DoVanTan(113A)- Tổng số bài gửi : 26
Join date : 16/07/2012
Age : 35
Đến từ : Trà Vinh
Ví dụ nhỏ về lập trình đa luồng (Thread) C#
Sau 1 hồi lượm nhặt trên mạng mình thấy có một ví dụ rất đơn giản + dễ hiểu về Thread
Vd này sẽ tạo 2 người A, B trong 1 cuộc thi đếm, xem ai đếm từ 0->100 nhanh nhất:
Để thực hiện mình tạo 2 đối tượng A, B như sau:
public static void A()
{
for (int i = 0; i < 100; i++)
{
Console.WriteLine(i.ToString());
}
Console.WriteLine("A đã đọc xong"); // Báo hiệu A thực hiện xong
}
public static void B()
{
for (int i = 0; i < 100; i++)
{
Console.WriteLine(i.ToString());
}
Console.WriteLine("B đã đọc xong"); // Báo hiệu B thực hiện xong
}
*Sau đó cho A,B vào 2 luồng để chúng thực hiện
ThreadStart ts1 = new ThreadStart(A); // Chỉ định thằng A lên đọc
ThreadStart ts2 = new ThreadStart(B); // Chỉ định thằng B lên đọc
// Sẵn sàng cho cuộc đấu
Thread tA = new Thread(ts1);
Thread tB = new Thread(ts2);
// Bắt đầu bấm giờ
tA.Start();
tB.Start();
tA.Join();
tB.Join();
// Hai thằng tranh nhau đếm
Console.WriteLine("Cuộc thi kết thúc");
Console.ReadLine();
Các bạn xem project nhá
http://www.mediafire.com/?9qpcasz7x4p0767
Vd này sẽ tạo 2 người A, B trong 1 cuộc thi đếm, xem ai đếm từ 0->100 nhanh nhất:
Để thực hiện mình tạo 2 đối tượng A, B như sau:
public static void A()
{
for (int i = 0; i < 100; i++)
{
Console.WriteLine(i.ToString());
}
Console.WriteLine("A đã đọc xong"); // Báo hiệu A thực hiện xong
}
public static void B()
{
for (int i = 0; i < 100; i++)
{
Console.WriteLine(i.ToString());
}
Console.WriteLine("B đã đọc xong"); // Báo hiệu B thực hiện xong
}
*Sau đó cho A,B vào 2 luồng để chúng thực hiện
ThreadStart ts1 = new ThreadStart(A); // Chỉ định thằng A lên đọc
ThreadStart ts2 = new ThreadStart(B); // Chỉ định thằng B lên đọc
// Sẵn sàng cho cuộc đấu
Thread tA = new Thread(ts1);
Thread tB = new Thread(ts2);
// Bắt đầu bấm giờ
tA.Start();
tB.Start();
tA.Join();
tB.Join();
// Hai thằng tranh nhau đếm
Console.WriteLine("Cuộc thi kết thúc");
Console.ReadLine();
Các bạn xem project nhá
http://www.mediafire.com/?9qpcasz7x4p0767
phamanhtuan95(113A)- Tổng số bài gửi : 22
Join date : 18/07/2012
Trang 3 trong tổng số 6 trang • 1, 2, 3, 4, 5, 6
Trang 3 trong tổng số 6 trang
Permissions in this forum:
Bạn không có quyền trả lời bài viết