Tin họcBạn có muốn phản ứng với tin nhắn này? Vui lòng đăng ký diễn đàn trong một vài cú nhấp chuột hoặc đăng nhập để tiếp tục.

Tin học
Cơ sở lập trình-Công nghệ phần mềm-Hệ điều hành
Ví dụ về đa luồng
+2VoDucDacThong (I102C)NguyenThiLai (102C)6 posters
Tin học :: Your first category :: Hoàn chỉnh kiến thức 102C
Trang
1 trong tổng số
1 trang

Ví dụ về đa luồng
NguyenThiLai (102C) 19/4/2011, 12:33
Mình thấy ví dụ này khá hay và cũng dể hiểu,mình nghĩ mấy bạn nên tham khảo:Ví dụ này mình sẽ mô tả 2 luồng (cho đơn giản) được thực thi cùng một lúc.Ở đây thì bạn cứ tưởng tượng ra rằng có hai thằng tên là A và B thi đếm từ 0 cho đến 100, thằng nào đếm xong trước thì báo cáo và được về chỗ. Tương ứng mình sẽ tạo ra 2 phương thức A() và B() (mỗi luồng sẽ xử lý một thằng). void A() { for(int i=0; i<=100; i++) Console.WriteLine(i.ToString()); Console.WriteLine("A đã đọc xong"); // Báo cáo đã đọc xong } void B() { for(int i=0; i<=100; i++) Console.WriteLine(i.ToString()); Console.WriteLine("B đã đọc xong"); // Báo cáo đã đọc xong }Bây giờ thầy giáo (hoặc là bạn) bỗng cao hứng gọi 2 thằng lên thi đọc --> 2 thằng A và B cùng đọc Đến đây trong phương thức hàm main() của chương trình bạn sẽ phải gọi 2 thằng này static void main() { 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 (thi đếm nhanh

) 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(); }// Thư viện tham chiếu nằm trong namespace System.Threading;// Bạn cần khai báo sử dụng nó using Sytem.Threading; # Truyền tham số cho ThreadCó nhiều cách truyền tham số, tuỳ theo nhu cầu mà dùng sao cho phù hợpThông qua phương thức Start(object) thì bạn có thể truyền tham số theo cách này.Ví dụ: using System; using System.Threading; class ThreadSample { public static void Main() { Thread newThread = new Thread(ThreadSample.DoWork); newThread.Start(100); // Dữ liệu truyền vào là một số nguyên // Để Start luồng sử dụng phương thức thể hiện (instance method) // thì trước tiên ta cần khởi tạo nó trước khi gọi ThreadSample worker = new ThreadSample(); newThread = new Thread(worker.DoMoreWork); newThread.Start("Truyền đối tượng cho thread thực thi"); // Nếu biết trước được đối tượng truyền vào thì ta cần ghép kiểu cho nó // để việc sử dụng được hiệu quả hơn } public static void DoWork(object data) { Console.WriteLine("Ðây là luồng tĩnh."); Console.WriteLine("Dữ liệu truyền vào: Data = {0}", data); } public void DoMoreWork(object data) { Console.WriteLine("Đây là luồng cần được khởi tạo"); Console.WriteLine("Dữ liệu truyền vào là: Data = {0}", data); } }Đôi khi ta cũng sử dụng ThreadPool cho việc khởi chạy một luồng mới với tham số là _Param ThreadPool.QueueUserWorkItem(new WaitCallback(_ThreadProc), _Param);Bạn hãy tham khảo về nó tại đây: http://dotnetperls.com/threadpool # Chờ đợi một luồng khácBằng việc sử dụng phương thức Join(); ta có thể cho phép chờ đợi một luồng khác thực hiện xong (để thu thập dữ liệu chẳng hạn - do chia nhỏ công việc mà), thì luồng đã gọi nó mới tiếp tục được công việc của nó static void Main(string[] args) { Console.WriteLine("Main thread: Gọi luồng thứ 2 ThreadProc()..."); Thread t = new Thread(new ThreadStart(ThreadProc)); t.Start(); for (int i = 0; i < 50; i++) { Console.WriteLine("Main thread: Do Some Work."); Thread.Sleep(0); } Console.WriteLine("Main thread finished: And call t.Join()"); Console.WriteLine("Main thread tạm thời đang được dừng lại"); t.Join(); // Dừng tại đây // Sau khi ThreadProc hoàn tất Main thread tiếp tục công việc của nó // Tiếp tục thực thi 3 dòng lệnh tiếp theo Console.WriteLine("Thread.Join() has returned."); Console.WriteLine("Main đã làm xong việc"); Console.ReadLine(); } public static void ThreadProc() { for (int i = 0; i < 100; i++) { Console.WriteLine("ThreadProc: {0}", i); Thread.Sleep(0); } }Đối số cho Join() có thể là int hoặc TimeSpan, khoảng thời gian giới hạn mà Main thread có thể chờ được, ví dụt.Join(10000);nghĩa là, sau 10s mà ThreadProc chưa làm xong việc của nó thì Main thread không chờ nữa, tiếp tục công việc khác
NguyenThiLai (102C)Tổng số bài gửi : 12
Join date : 21/02/2011
LikeDislike

Re: Ví dụ về đa luồng
VoDucDacThong (I102C) 19/4/2011, 19:25
Bạn ơi! Ví dụ của bạn dài quá, mình đọc không xuể luôn. Đi thi thầy mà cho trúng câu này chắc mỉnh bỏ câu này không thì mình rớt mất. Hì hì. Dù sao cũng cám ơn bạn nhiều lắm, nếu đọc hết sẽ thấy rất bổ ích.
VoDucDacThong (I102C)Tổng số bài gửi : 92
Join date : 23/02/2011
LikeDislike

Re: Ví dụ về đa luồng
Sponsored content
Sponsored content

Re: Ví dụ về đa luồng
teo(i11c) 19/4/2011, 20:42
Đôi khi ứng dụng của chúng ta cần xử lý một tác vụ dài, trong thời gian ứng dụng xử lý tác vụ đó thì dường như ứng dụng của ta không có bất kỳ phản ứng gì đối với các thao tác của người dùng. Đó là do ứng dụng đã dành hết tài nguyên cho việc xử lý tác vụ. Tuy nhiên, đó là trường hợp ứng dụng không sử dụng đa luồng. Trong ứng dụng đa luồng thì câu chuyện khác hẳn, ứng dụng của chúng ta vừa có thể sử lý nhiều tác vụ một lúc chẳng hạn, vừa lưu tập tin, vừa kiểm tra chính tả, vừa download cập nhật. Vậy ứng dụng đa luồng là gì và điểm khác của nó với ứng dụng chỉ có một luồng là gì?Thông thường trong ứng dụng chỉ có 1 luồng chính thì tại 1 thời điểm, ứng dụng của bạn chỉ tập trung xử lý một tác vụ và điều này dẫn đến việc khi xử lý tác vụ dài thì ứng dụng do đang xử lý tác vụ nên không thể nhận bất cứ tương tác khác của người dùng, đây là một trải nghiệm xấu cho người dùng đồng thời làm phung phí tài nguyên hệ thống.Đối với ứng dụng có nhiều luồng thì bộ xử lý có thể xử lý đa tác vụ trong một lúc chẳng hạn vừa kiểm tra chính tả cho bạn, download một file, lưu thay đổi trong ứng dụng… tất cả cùng một lúc. Mặc dù thực chất thì ứng dụng vẫn chỉ xử lý một luồng trong mỗi đơn vị thời gian tuy nhiên khi có đa luồng thì nó lại phân chia mỗi luồng mỗi đơn vị thời gian nhỏ để xử lý để ta có cảm tưởng rằng các luồng đang chạy đồng thời với nhau.Source: mediafire.com /download.php?lnzazd66drkbycbDocument:http://www.mediafire.com/download.php?j2dqt1hirnlz3h9Sau đây sẽ làm một ví dụ về sử dụng luồng.Trong ví dụ này tôi sẽ xây dựng một bộ đếm, thông báo cho listener ở luồng chính về số lần đến hiện tại. Tôi có thể mô tả luồng đó như sau:” Thông báo cho tôi về số lần đếm sau mỗi x giây và dừng việc đếm sau khi đã đếm được đến z lần.” và sử dụng một listener để nhận lấy thông điệp đó.Lưu ý là ứng dụng này sẽ có 2 luồng gồm một luồng do chúng ta tự tạo ra thông qua lớp SecondsCounter và một luồng chính để chạy chương trình.Trong bada có 2 cách để tạo một luồng:- Truyền một đối tượng IRunnable vào thread và thực thi hàm Run()- Viết một class và cho kế thừa từ lớp Thread và thực thi hàm Run()Đồng thời có 2 loại luồng:- Worker thread: chạy một lần và dừng lại sau khi tác vụ hoàn tất- Event driven thread: chạy và không dừng lại sau khi tác vụ hoàn tất. Tiếp tục để đợi cho sự kiên hoặc một thông báo thoát.Và cả 2 loại luồng như trên đều đều thực thi hàm Run(), tuy nhiên:- Worker thread tự động hủy sau khi hàm Run() chạy xong.- Trong khi đó Event driven thread vẫn tiếp tục tồn tại để đợi sự kiện. Bạn phải tự hủy Event driven thread.Trong ví dụ dưới đây tôi sẽ sử dụng luồng bằng cách kế thừa lớp Thread và loại luồng được sử dụng là Worker thread.Việc đầu tiên chúng ta cần làm là viết một lớp listener:Mã:#ifndef SECONDSCOUNTERLISTENER_H_#define SECONDSCOUNTERLISTENER_H_#include <FBase.h>class SecondsCounterListener{public:virtual void OnCount(int times)=0;};#endif /* SECONDSCOUNTERLISTENER_H_ */Nó đơn giản chỉ là một interface để khai báo cho sự kiện của chúng ta. Sau đây chúng ta sẽ sử dụng vào việc một lớp kế thừa từ Thread.Mã:#ifndef SECONDSCOUNTER_H_#define SECONDSCOUNTER_H_#include <FBase.h>#include "SecondsCounterListener.h"class SecondsCounter:public Osp::Base::Runtime::Thread{public:SecondsCounter();virtual ~SecondsCounter();void Init(int seconds,int timeout);void AddSecondsCounterListener(SecondsCounterListener &listener);virtual Osp::Base::Object * Run(void);virtual bool OnStart(void);virtual void OnStop(void);protected:int seconds_;int timeout_;int times_;SecondsCounterListener * listener_;};#endif /* SECONDSCOUNTER_H_ */Trong lớp của chúng ta vừa viết, do lớp được kế thừa từ lớp Thead nên việc thực thi hàm Run() là bắt buộc. Đối với 2 hàm là OnStart và OnStop thì không bắt buộc, ta có thể sử dụng 2 hàm này vào việc thực hiện các câu lệnh khởi động/xóa tài nguyên cho chương trình.Sau đây chúng ta sẽ các hàm để thực thi lớp SecondsTimer:Mã:#include "SecondsCounter.h"using namespace Osp::Base;using namespace Osp::Base::Runtime;SecondsCounter::SecondsCounter(void){}SecondsCounter::~SecondsCounter(){}voidSecondsCounter::Init(int seconds,int timeout){this->Construct(THREAD_TYPE_WORKER);seconds_=seconds;timeout_=timeout;}boolSecondsCounter::OnStart(){times_=0;}voidSecondsCounter::OnStop(){listener_=NULL;}voidSecondsCounter::AddSecondsCounterListener(SecondsCounterListener &listener){listener_=&listener;}Osp::Base::Object *SecondsCounter::Run(){if(listener_) listener_->OnCount(times_);do{times_++;Thread::Sleep(seconds_*1000);if(listener_) listener_->OnCount(times_);}while(times_<timeout_);}Sau đây tôi tạo một luồng đếm ứng dụng lớp SecondsCount mà chúng ta vừa tạo vào form chính khi sự kiện nhấn nút OK xảy ra:Mã:voidMainForm::OnActionPerformed(const Osp::Ui::Control& source, int actionId){switch(actionId){case ID_BUTTON_OK:{//AppLog("OK Button is clicked! \n");delete counter_;counter_=new SecondsCounter;counter_->Init(3,60);counter_->AddSecondsCounterListener(*this);counter_->Start();}break;default:break;}}Diễn giải: khi sự kiện nhấn OK xảy ra, một thread đếm sẽ được tạo và thread này sẽ gọi hàm OnCount sau mỗi 3 giây và kết thúc khi đã đếm được đến 60.Đồng thời, MainForm thực thi hàm OnCount để nhận sự kiện đếm mỗi khi nó xảy ra.Mã:voidMainForm::OnCount(int times){String str="Count: ";str.Append(times);__pLabel->SetText(str);RequestRedraw(true);}Vậy là chương trình đã sẵn sàng để chạy. Khi bạn nút OK bạn sẽ thấy chương trình tự đếm đến 60 và thread sau đó sẽ tự hủy.Các có thể tải source code để xem toàn bộ câu lệnh cần thiết cho chương trình.Chúc bạn thành công
teo(i11c)Tổng số bài gửi : 42
Join date : 22/11/2010
LikeDislike

Re: Ví dụ về đa luồng
vongocminhhoang (102C) 20/4/2011, 10:49
chà source code dài quá, đọc xong tẩu hỏa nhập ma luôn mà không hiểu ý đồ làm gì, dù sao cũng cảm ơn các bạn đã có ví dụ. cho mình hỏi cái này là các bạn tự viết hay là tham khảo được từ trên mạng

(nếu tham khảo thì ghi rõ nguồn để mọi người lên đó xem cho dễ hiểu

)ps: bạn NguyenThiLai cho mình hỏi cái Thread.Sleep thì mình hiểu và biết cách dùng nó, nhưng mà Thread.Sleep(0) thì không hiểu để làm gì

, bạn nói rõ chỗ này mục đích gì được không vì mình đọc xong mà không hiểu code lắm, cảm ơn trước nhé
vongocminhhoang (102C)Tổng số bài gửi : 70
Join date : 17/02/2011
LikeDislike

Re: Ví dụ về đa luồng
QuachVanLoc_I92C 20/4/2011, 20:31
Hôm nay mình học bài đa luồng, mình hiểu thêm được một số câu lệnh trong code của thày nói về lập trình đa luồng.- SuspendThread(): tạm ngừng luồng đang chạy hiện hành.- ProductID1 và ProductID2: là các mã số định danh.- Số 0: luồng tiêu thụ đi vào vận hành ngay.- Số 4: luồng sản xuất ngủ luôn sau khi vừa được sinh ra.- CloseHandle: Đóng luồng với mục quản cho trước.- Sleep(1): Dừng lại 1mili giây để hoàn tất các tiến trình xong mới thực hiện tiếp lệnh ShowBuffer().
QuachVanLoc_I92CTổng số bài gửi : 64
Join date : 23/09/2010
LikeDislike

Re: Ví dụ về đa luồng
TruongThiMinhNgoc57(102C) 20/4/2011, 22:32
mình cũng vừa đọc bài viết này trên mạng . Nó ko như đoạn code trườu tượng như mình xem trên lớp, mà nó trở nên thực tế hơn về tính đa luồng.
TruongThiMinhNgoc57(102C)Tổng số bài gửi : 90
Join date : 17/02/2011
Đến từ : TPHCM
LikeDislike

Re: Ví dụ về đa luồng
Sponsored content
Sponsored content


Similar topics
Similar topics» tổng hợp Đa Luồng : tài liệu tham khảo về Luồng Windows 2000 và Luồng Linux và Luồng Java » Thảo luận Bài 5» Thảo luận Bài 5 (Đa luồng)» Những đặc điểm của Luồng (Thread) và so sánh giữa Luồng với Tiến trình ( Process).Những ưu việt của công nghệ đa luồng .» Thảo luận Bài 5
Tin học :: Your first category :: Hoàn chỉnh kiến thức 102C
Trang
1 trong tổng số
1 trang
Chuyển đến: Chọn Diễn Đàn||--Your first category |--Nhập môn CNPM |--Toán học rời rạc |--Nhập môn lập trình |--Phân tích thiết kế HTTT |--Lớp HLT3 |--Lớp I22A-I22B |--Lớp HC11TH3A |--Hoàn chỉnh kiến thức I12A |--Ôn thi Tốt nghiệp |--Hoàn chỉnh kiến thức I11C |--Hoàn chỉnh kiến thức 102C |--Hoàn chỉnh kiến thức I92C |--CNTT Phan Thiết (K1) |--Hoàn chỉnh kiến thức I91C |--Hoàn chỉnh kiến thức I82C |--Hoàn chỉnh kiến thức I83C
Permissions in this forum:Bạn
không có quyền trả lời bài viết
- Trang Chính
- Free forum | ©phpBB | Free forum support | Báo cáo lạm dụng | Thảo luận mới nhất