2015-06-19 34 views
0

我有一個關於計時器的問題。間隔時間是否計算回調執行的時間?我的意思是例如 - 我有一個定時器設置爲每15秒觸發一次,並執行一個持續大約3秒鐘的回調函數。當下次計時器會發射?在18秒內(回撥完成後)或15秒後(無需等待回叫)? 在此先感謝System.Threading.Timer ...下一次火災的時間?

+1

計時器與其回調無關。它會在15秒內觸發 –

+0

,所以回調將在另一個線程中執行? –

+1

http://blog.stackoverflow.com/2011/12/dont-be-afraid-to-use-the-science/ –

回答

3

無論回調執行時間如何,它都會每隔15秒觸發一次。如果您希望它包含回調執行時間,您可以掛起並重新啓動回調中的定時器,如下所示;

在開始:

someTimer.Change(Timeout.Infinite, Timeout.Infinite)

..和結尾,改回用同樣的方法:

someTimer.Change(TimeSpan.FromSeconds(15), TimeSpan.FromSeconds(15))

+1

您不需要在開始時更改計時器,只是從不指定時間段,因此計時器只會觸發一次。通過這種方式,回調端的'Change'調用將重置定時器 –

0

將火每隔15秒。任何回調延遲都不會影響計時器。該回調在單獨的ThreadPool線程上執行。來自docs

該方法不會在創建定時器的線程上執行;它在系統提供的ThreadPool線程上執行。

如果你想採取的處理時間考慮進去,你就必須自己管理的計時器 - 開始一個單火定時器,從回調中重新設置,如:

TimerCallback tcb = MyCallBack; 
//Start the timer once after 15 secs 
_timer=new Timer(tcb,null,TimeSpan.FromSeconds(15),TimeSpan.Infinite); 

... 
void MyCallBack(Object stateInfo) 
{ 
    .... 
    //Reset the timer 
    _timer.Change(TimeSpan.FromSeconds(15),TimeSpan.Infinite); 
} 

的更簡單更簡潔的方法是在每次異步執行後使用async/await等待X秒。例如,下面的代碼將最後一次執行後15秒執行的方法:

while(...) 
{ 
    await Task.Delay(TimeSpan.FromSeconds(15)); 
    var response=await Task.Run(()=>someMethod()); 
    ... 
} 

,或者,如果要執行的代碼,已經是異步

while(...) 
{ 
    await Task.Delay(TimeSpan.FromSeconds(15)); 
    await myHttpClient.GetStringAsync(someURL); 
} 

引擎蓋下,Task.Delay創建單火計時器,並在計時器結束時完成。這與手動操作幾乎完全相同。