Công cụ bảo vệ mã nguồn .NET mạnh nhất, không thể unpack, miễn phí cho các khách hàng đầu tiên đăng ký.
Từ 1 tới 3 trên tổng số 3 kết quả

Đề tài: [SourceCode] Timer(Stopwatch) Multithreaded program C++

  1. #1
    Ngày gia nhập
    01 2013
    Nơi ở
    TP.HCM
    Bài viết
    7

    Talking [SourceCode] Timer(Stopwatch) Multithreaded program C++

    Ngồi mày mò mãi mới được cái này, post lên để ae cùng tham khảo
    Mình cũng là new bie, để cho các bạn đỡ mất công kiếm source code và học lập trình multithreaded nhanh hơn thui
    Tài liệu hướng dẫn :
    Multithread - ĐH KHTN

    TIMER
    Code:
    #include <iostream>
    #include <string>
    #include "conio.h"
    #include "windows.h"
    
    using namespace std;
    
    int minisec = 0;
    int sec = 0;
    int minute = 0;
    int hour = 0;
    
    bool bESCPressed = 0;
    
    DWORD WINAPI CounterThread(LPVOID)
    {
    	while (true)
    	{
    		system("cls");
    		minisec++;
    		if (minisec == 60)
    		{
    			minisec = 0;
    			sec++;
    			if (sec == 60)
    			{
    				sec = 0;
    				minute++;
    				if (minute == 60)
    				{
    					minute = 0;
    					hour++;
    				}
    			}
    		}
    
    		string sHour = (hour > 9) ? to_string(hour) : ("0" + to_string(hour));
    		string sMinute = (minute > 9) ? to_string(minute) : ("0" + to_string(minute));
    		string sSec = (sec > 9) ? to_string(sec) : ("0" + to_string(sec));
    		string sMinisec = (minisec > 9) ? to_string(minisec) : ("0" + to_string(minisec));
    		cout << "************* TIME **************" << endl;
    		cout << "*          " << sHour << ":" << sMinute << ":" << sSec << ":" << sMinisec << "          *" << endl;
    		cout << "*********************************" << endl;
    		Sleep(1);
    
    	}
    	return 0;
    }
    
    DWORD WINAPI OutThreadESC(LPVOID)
    {
    
    	do {
    		bESCPressed = (_getch() == 27);
    	} while (!bESCPressed);
    
    	return 0;
    }
    
    int main()
    {
    	DWORD dwThreadIdCounter;
    	DWORD dwThreadIdOutESC;
    
    	HANDLE hThreadCounter;
    	HANDLE hThreadOutESC;
    
    	hThreadCounter = CreateThread(NULL, 0, CounterThread, NULL, 0, &dwThreadIdCounter);
    	hThreadOutESC = CreateThread(NULL, 0, OutThreadESC, NULL, 0, &dwThreadIdOutESC);
    
    	while (!bESCPressed);	// Chuong trinh dung lai de cho: neu khong thread chinh tat thi cac thread con cung tat theo
    
    	return 0;
    }
    CodePad : http://codepad.org/OC7zdemM
    Công cụ bảo vệ mã nguồn .NET mạnh nhất hiện tại, miễn phí cho các khách hàng đầu tiên đăng ký.

  2. #2
    Ngày gia nhập
    11 2007
    Nơi ở
    Hà Nội
    Bài viết
    520

    Chương trình của bạn có một số chỗ chưa hợp lý như sau:

    1.Sử dụng biến toàn cục mà không có locking hay mutex: Khi dùng thread để xử lý , các biến toàn cục khi được tham chiếu đều phải lock, tránh đụng độ. Do các biến như int, bool có tính nguyên tố, nên trong trường hợp này có thể tạm coi là chấp nhận được.

    2.Không dừng thread đúng cách: 1 thread dừng lại khi bản thân nó thoát khỏi vòng lặp xử lý, không phụ thuộc vào thread khác. Giả sử thread đang mở các tài nguyên như mở file, ghi file, hoặc kết nối mạng, nếu dừng thread không đúng cách sẽ phát sinh lỗi.

    3.Không CloseHandle đối với các handle mới tạo ra, gây ra leak handle. Tuy là ví dụ nhưng mình nghĩ nên viết chuẩn, để người khác đọc không bị thiếu sót.

    4. Main thread sử dụng lệnh sau để đợi các thread khác hoạt động xong:
    C Code:
    1. while (!bESCPressed);   // Chuong trinh dung lai de cho: neu khong thread chinh tat thi cac thread con cung tat theo

    cách này được gọi là busy polling. Cách này thường gây lãng phí tài nguyên của máy tính, được khuyến cáo là không nên dùng.


    Mình viết 1 ứng dụng nhỏ để làm rõ hơn các ý mình vừa nói. Đây là code của mình:
    Trước khi tạo thread, mình tạo một Event, đặt tên là stopEvent.
    Mục đích của Event này là báo cho thread Counter biết khi nào cần dừng lại.
    Khi nhấn ESC, OutThreadESC sẽ thiết lập event này, để CounterThread biết và stop đúng cách.

    Main thread sẽ đợi khi cả 2 thread dừng lại mới kết thúc, thông qua hàm WaitForMultipleObjects
    Visual C++ Code:
    1. #include <stdio.h>
    2. #include <conio.h>
    3. #include <Windows.h>
    4.  
    5. enum
    6. {
    7.     CounterThreadIndex = 0,
    8.     OutThreadESCIndex = 1
    9. };
    10.  
    11. DWORD WINAPI CounterThread (__in_opt LPVOID lpParam)
    12. {
    13.     SYSTEMTIME sysTime = {};
    14.     int printedChar = 0;
    15.  
    16.     if (lpParam == NULL)
    17.         return 0;
    18.  
    19.     HANDLE hStopEvent = *(HANDLE*)lpParam;
    20.  
    21.     printf("Current time: ");
    22.     while( WaitForSingleObject(hStopEvent, 0) == WAIT_TIMEOUT) // check stop-event
    23.     {
    24.         // get current time
    25.         GetSystemTime(&sysTime);
    26.         GetLocalTime(&sysTime);
    27.         // print current time
    28.         printedChar = printf(
    29.             "%02d/%02d/%04d %02d:%02d:%02d",
    30.             sysTime.wDay, sysTime.wMonth, sysTime.wYear,
    31.             sysTime.wHour, sysTime.wMinute, sysTime.wSecond
    32.             );
    33.  
    34.  
    35.         // sleep 1 second
    36.         Sleep(1000);
    37.         // clear screen
    38.         for (int i = 0; i < printedChar; ++i)
    39.             printf("\b");
    40.     }
    41.     delete (HANDLE*)lpParam;
    42.     return 0;
    43. }
    44.  
    45. DWORD WINAPI OutThreadESC (__in_opt LPVOID lpParam)
    46. {
    47.     BOOL bESCPressed  = FALSE;
    48.  
    49.     // check parameter
    50.     if (lpParam == NULL)
    51.         return 0;
    52.  
    53.     // get stop event handle
    54.     HANDLE hStopEvent = *(HANDLE*)lpParam;
    55.  
    56.     // wait for ESC
    57.     do {
    58.         bESCPressed = (_getch() == 27);
    59.     } while (!bESCPressed);
    60.  
    61.     // set stop-event
    62.     SetEvent(hStopEvent);
    63.     printf("\n\nStopping counter thread...\n");
    64.     delete (HANDLE*)lpParam;
    65.     return 0;
    66. }
    67.  
    68. int main(int argc, char **argv)
    69. {
    70.     HANDLE hStopEvent = NULL;
    71.     HANDLE hThread[2];
    72.  
    73.  
    74.     hStopEvent = CreateEvent(
    75.         NULL, // security attrib
    76.         TRUE, //manual reset
    77.         FALSE, // Initial state
    78.         NULL // No-name
    79.         );
    80.  
    81.     // error
    82.     if (hStopEvent == NULL)
    83.         return 1;
    84.  
    85.     hThread[CounterThreadIndex] = CreateThread(
    86.         NULL, // thread attrib
    87.         0, // stack size
    88.         CounterThread, //
    89.         new HANDLE(hStopEvent), // stop event handle cloned
    90.         0, // creation flag
    91.         NULL // pointer to thread id
    92.         );
    93.     if (hThread[CounterThreadIndex] == NULL)// failed
    94.     {
    95.         CloseHandle(hStopEvent); // release event
    96.         return 1;
    97.     }
    98.  
    99.     hThread[OutThreadESCIndex] = CreateThread(
    100.         NULL, // thread attrib
    101.         0, // stack size
    102.         OutThreadESC, //
    103.         new HANDLE(hStopEvent), // stop event handle cloned
    104.         0, // creation flag
    105.         NULL // pointer to thread id
    106.         );
    107.  
    108.     if (hThread[OutThreadESCIndex] == NULL)// failed
    109.     {
    110.         SetEvent(hStopEvent);// stop thread
    111.  
    112.         if (WAIT_TIMEOUT == WaitForSingleObject(hThread[CounterThreadIndex], 5000))// wait
    113.             TerminateThread(hThread[CounterThreadIndex], 0);
    114.  
    115.         // release event
    116.         CloseHandle(hThread[CounterThreadIndex]);
    117.         CloseHandle(hStopEvent);
    118.         return 1;
    119.     }
    120.  
    121.     // wait all threads
    122.     WaitForMultipleObjects(2, hThread, TRUE, INFINITE);
    123.  
    124.     // close all Handles
    125.     for (unsigned int i = 0; i < 2; ++i)
    126.         CloseHandle(hThread[i]);
    127.    
    128.     CloseHandle(hStopEvent);
    129.  
    130.     printf("\n\nStopped!\n");
    131.     getch();
    132.     return 0;
    133. }
    Đã được chỉnh sửa lần cuối bởi quangnh89 : 18-11-2013 lúc 07:43 AM.

  3. #3
    Ngày gia nhập
    01 2013
    Nơi ở
    TP.HCM
    Bài viết
    7

    Cảm ơn bạn đã góp ý, tks so much !
    Công cụ bảo vệ mã nguồn .NET mạnh nhất hiện tại, miễn phí cho các khách hàng đầu tiên đăng ký.
    Một ngày mới mà bạn không biết thêm điều gì mới thì đó chính là ngày cuối đời của bạn !

Các đề tài tương tự

  1. Hướng dẫn viết game Dò mìn (Minesweeper) bằng C# + sourcecode
    Gửi bởi Yin Yang trong diễn đàn Tutorials và Thủ thuật lập trình C#, ASP.NET
    Trả lời: 23
    Bài viết cuối: 04-03-2013, 09:55 PM
  2. Mã nguồn C++ C++ :: SourceCode thuật toán A* (A sao) tìm đường đi ngắn nhất.
    Gửi bởi AnhPham trong diễn đàn Thủ thuật, Tutorials và Mã nguồn C/C++/C++0x
    Trả lời: 9
    Bài viết cuối: 09-12-2012, 04:55 PM
  3. Làm sao để thực thi sourcecode sinh bằng codedom cùng với các sourcecode khác?
    Gửi bởi blumbebe trong diễn đàn Thắc mắc lập trình C#
    Trả lời: 0
    Bài viết cuối: 20-01-2012, 09:33 PM
  4. SourceCode bán vé tàu mô hình 3 layers
    Gửi bởi Mandy trong diễn đàn Dự án & Source code C#, ASP.NET
    Trả lời: 0
    Bài viết cuối: 19-11-2011, 04:49 PM
  5. làm sao để timer chờ cho button thực hiện hết lệnh rồi thì timer lặp tiếp
    Gửi bởi chitviv trong diễn đàn Thắc mắc lập trình C#
    Trả lời: 4
    Bài viết cuối: 19-07-2011, 04:14 PM

Quyền hạn của bạn

  • Bạn không thể gửi đề tài mới
  • Bạn không thể gửi bài trả lời
  • Bạn không thể gửi các đính kèm
  • Bạn không thể chỉnh sửa bài viết của bạn