Linux下精確計時

2021-09-23 07:45:42 字數 2916 閱讀 4096

1.低精度計時

**1.1sleep 和 usleep **

sleep(int x) 系統呼叫,讓程序等待x秒鐘。其精度以秒為單位的。

usleep( int x)系統呼叫,讓程序等待x 納秒,但實際其精度一般是10ms,再低的達不到。

這兩個函式的優點是簡單,缺點程序被阻塞。

1.2alarm鬧鐘

alarm也稱為鬧鐘函式,它可以在程序中設定乙個定時器,當定時器指定的時間到時,它向程序傳送sigalrm訊號。alarm函式原型如下:

unsigned int alarm(unsigned int seconds);

返回值:

出錯:-1

1.3select

int select(int maxfdp,fd_set *readfds,fd_set *writefds,fd_set *errorfds,struct timeval*timeout); 

引數解釋如下:

int maxfdp:是乙個整數值,是指集合中所有檔案描述符的範圍,即所有檔案描述符的最大值加1;

fd_set* readfds:是指向fd_set結構的指標,這個集合中應該包括檔案描述符,我們是要監視這些檔案描述符的讀變化的,即我們關心是否可以從這些檔案中讀取資料了,如果這個集合中有乙個檔案可讀,select就會返回乙個大於0的值,表示有檔案可讀,如果沒有可讀的檔案,則根據timeout引數再判斷是否超時,若超出timeout的時間,select返回0,若發生錯誤返回負值。可以傳入null值,表示不關心任何檔案的讀變化;

fd_set* writefds:是指向fd_set結構的指標,這個集合中應該包括檔案描述符,我們是要監視這些檔案描述符的寫變化的,即我們關心是否可以向這些檔案中寫入資料了,如果這個集合中有乙個檔案可寫,select就會返回乙個大於0的值,表示有檔案可寫,如果沒有可寫的檔案,則根據timeout再判斷是否超時,若超出timeout的時間,select返回0,若發生錯誤返回負值。可以傳入null值,表示不關心任何檔案的寫變化;

fe_set* errorfds:同上面兩個引數的意圖,用來監視檔案錯誤異常;

struct timeval* timeout:是select的超時時間,這個引數至關重要,它可以使select處於三種狀態,如下:

第一:若將null以形參傳入,即不傳入時間結構,就是將select置於阻塞狀態,一定等到監視檔案描述符集合中某個檔案描述符發生變化為止;

第二:若將時間值設為0秒0毫秒,就變成乙個純粹的非阻塞函式,不管檔案描述符是否有變化,都立刻返回繼續執行,檔案無變化返回0,有變化返回乙個正值;

第三:timeout的值大於0,這就是等待的超時時間,即select在timeout時間內阻塞,超時時間之內有事件到來就返回了,否則在超時後不管怎樣一定返回。

select一般在在socket程式設計中還是比較重要的,可是對於初學socket的人來說都不太愛用select寫程式,他們只是習慣寫諸如connect、accept、recv或recvfrom這樣的阻塞程式(所謂阻塞方式block,顧名思義,就是程序或是執行緒執行到這些函式時必須等待某個事件的發生,如果事件沒有發生,程序或執行緒就被阻塞,函式不能立即返回)。可是使用select就可以完成非阻塞(所謂非阻塞方式non-block,就是程序或執行緒執行此函式時不必非要等待事件的發生,一旦執行肯定返回,以返回值的不同來反映函式的執**況,如果事件發生則與阻塞方式相同,若事件沒有發生則返回乙個**來告知事件未發生,而程序或執行緒繼續執行,所以效率較高)方式工作的程式,它能夠監視我們需要監視的檔案描述符的變化情況——讀寫或是異常。

2.高精度計時

2.1 忙等

實時讀取當前的系統時間,與需要延時的時間做對比,對於系統消耗比較大。示例**如下:

struct timespec now ;

clock_gettime(clock_realtime,&now);

now.tv_sec += 需要等待的秒數;

now.tv_nsec +=需要等待的納妙數;

while(1)

2.2setitimer函式

在linux下如果對定時要求不太精確的話,使用alarm()和signal()就行了,但是如果想要實現精度較高的定時功能的話,就要使用setitimer函式。setitimer()為linux的api,並非c語言的standard library,setitimer()有兩個功能,一是指定一段時間後,才執行某個function,二是每間格一段時間就執行某個function。函式原型如下:

int setitimer(int which, const struct itimerval *new_value,struct itimerval *old_value);

struct itimerval ;

struct timeval ;

引數解釋如下:

which:引數表示型別,可選的值有:

itimer_real:以系統真實的時間來計算,它送出sigalrm訊號;

itimer_virtual:以該程序在使用者態下花費的時間來計算,它送出si**talrm訊號;

itimer_prof:以該程序在使用者態下和核心態下所費的時間來計算,它送出sigprof訊號;

new_value:引數用來對計時器進行設定,it_interval為計時間隔,it_value為延時時長;

settimer工作機制是,先對it_value倒計時,當it_value為零時觸發訊號,然後重置為it_interval,繼續對it_value倒計時,一直這樣迴圈下去。假如it_value為0是不會觸發訊號的,所以要能觸發訊號,it_value得大於0;如果it_interval為零,只會延時,不會定時(也就是說只會觸發一次訊號)。

用rdtsc實現linux下的精確計時

在linux開發版最長問到的問題之一就是在linux下如何得到更精確的計時。其實有很多辦法,比如以前就有人用select。不過現在有更精確的實時時鐘可以用,這就是用clock process cputime id做引數通過timer create來建立timer。通過clock getres可以得到...

windows下的C C 精確計時

由於我要測試線性篩法的速度,用上了c c 精確計時.此時傳統的clock 方法不夠用了,我們需要另一種測量的辦法,即cputicks cpufreq.如何實現呢?include large integer freq,start,stop queryperformancefrequency freq ...

c 準確計時 C 精確計時

include large integer m freq,m timestart,m timenow queryperformancefrequency m freq queryperformancecounter m timestart double time double m timestart...