簡體   English   中英

為while循環創建超時的最簡潔方法是什么?

[英]What is the cleanest way to create a timeout for a while loop?

Windows API / C / C ++

1. ....  
2. ....
3. ....    
4.    while (flag1 != flag2)
5.    {
6.      SleepEx(100,FALSE);   
        //waiting for flags to be equal (flags are set from another thread).
7.    }
8. .....
9. .....  

如果標志在7秒后不相等,我想繼續第8行。

任何幫助表示贊賞。 謝謝。

如果您正在等待設置特定標志或達到時間,則更清潔的解決方案可能是使用自動/手動重置事件。 這些設計用於線程之間的信令條件,並且具有在其上設計的非常豐富的API。 例如,您可以使用WaitForMultipleObjects API,它采用顯式超時值。

不要輪詢要更改的標志。 即使在循環期間出現睡眠或產量,這也只會浪費CPU周期。

相反,獲取設置標志的線程會發出信號通知您已經更改過,可能是使用了一個事件 你等待事件需要超時,你可以調整以允許等待7秒。

例如:

Thread1:

 flag1 = foo;
 SetEvent(hEvent);


 Thread2:

 DWORD timeOutTotal = 7000;  // 7 second timeout to start.
 while (flag1 != flag2 && timeOutTotal > 0)
 {
     // Wait for flags to change
     DWORD start = GetTickCount();

     WaitForSingleObject(hEvent, timeOutTotal);

     DWORD end = GetTickCount();

    // Don't let timeOutTotal accidently dip below 0.
    if ((end - start) > timeOutTotal)
    {
        timeOutTotal = 0;
    }
    else
    {
       timeOutTotal -= (end - start);
    }

 }

您可以使用WinAPI中的QueryPerformanceCounter 在開始之前檢查它,並查詢是否已經過了一段時間。 但是,這是一個高分辨率計時器。 對於較低分辨率,請使用GetTickCount (毫秒)。

所有這些都取決於您是在積極等待(做某事)還是被動地等待外部過程。 如果是后者,則使用Sleep的以下代碼將更容易:

int count = 0;
while ( flag1 != flag2 && count < 700 )
{
   Sleep( 10 ); // wait 10ms
   ++count;
}

如果您不使用Sleep(或Yield)並且您的應用程序不斷檢查某個條件,那么您將使應用程序運行的CPU膨脹。

如果您廣泛使用WinAPI,您應該嘗試更原生的解決方案,閱讀有關WinAPI的同步功能

你沒有提到如果標志相等將會發生什么。

此外,如果您只是在沒有內存屏障的情況下測試它們,那么您無法保證看到其他線程所做的任何寫入。

最好的辦法是使用一個Event,並使用WaitForSingleObject函數,超時時間為7000毫秒。

確保你在那里做一個sleep()yield() ,否則你會吃掉所有整個CPU(或核心)等待。

我會說“檢查時間,如果七秒鍾后沒有發生任何事情,那么就打破循環。

如果您的應用程序執行某些網絡工作,請查看POSIX select()調用,尤其是超時功能!

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM