- 相關(guān)推薦
Linux多線(xiàn)程:線(xiàn)程的分離與結合
在任何一個(gè)時(shí)間點(diǎn)上,線(xiàn)程是可結合的(joinable),或者是分離的(detached)。一個(gè)可結合的線(xiàn)程能夠被其他線(xiàn)程收回其資源和殺死;在被其他線(xiàn)程回收之前,它的存儲器資源(如棧)是不釋放的。相反,一個(gè)分離的線(xiàn)程是不能被其他線(xiàn)程回收或殺死的,它的存儲器資源在它終止時(shí)由系統自動(dòng)釋放。
線(xiàn)程的分離狀態(tài)決定一個(gè)線(xiàn)程以什么樣的方式來(lái)終止自己。在上面的例子中,我們采用了線(xiàn)程的默認屬性,即為非分離狀態(tài)(即可結合的,joinable,需要回收),這種情況下,原有的線(xiàn)程等待創(chuàng )建的線(xiàn)程結束;只有當pthread_join()函數返回時(shí),創(chuàng )建的線(xiàn)程才算終止,才能釋放自己占用的系統資源。而分離線(xiàn)程不是這樣子的,它沒(méi)有被其他的線(xiàn)程所等待,自己運行結束了,線(xiàn)程也就終止了,馬上釋放系統資源。程序員應該根據自己的需要,選擇適當的分離狀態(tài)。
設置線(xiàn)程分離狀態(tài)的函數為pthread_attr_setdetachstate(pthread_attr_t *attr, int detachstate)。第二個(gè)參數可選為PTHREAD_CREATE_DETACHED(分離線(xiàn)程)和PTHREAD _CREATE_JOINABLE(非分離線(xiàn)程)。這里要注意的一點(diǎn)是,如果設置一個(gè)線(xiàn)程為分離線(xiàn)程,而這個(gè)線(xiàn)程運行又非?,它很可能在pthread_create函數返回之前就終止了,它終止以后就可能將線(xiàn)程號和系統資源移交給其他的線(xiàn)程使用,這樣調用pthread_create的線(xiàn)程就得到了錯誤的線(xiàn)程號。要避免這種情況可以采取一定的同步措施,最簡(jiǎn)單的方法之一是可以在被創(chuàng )建的線(xiàn)程里調用pthread_cond_timewait函數,讓這個(gè)線(xiàn)程等待一會(huì )兒,留出足夠的時(shí)間讓函數pthread_create返回。設置一段等待時(shí)間,是在多線(xiàn)程編程里常用的方法。但是注意不要使用諸如wait()之類(lèi)的函數,它們是使整個(gè)進(jìn)程睡眠,并不能解決線(xiàn)程同步的問(wèn)題。
另外一個(gè)可能常用的屬性是線(xiàn)程的優(yōu)先級,它存放在結構sched_param中。用函數pthread_attr_getschedparam和函數pthread_attr_setschedparam進(jìn)行存放,一般說(shuō)來(lái),我們總是先取優(yōu)先級,對取得的值修改后再存放回去。
線(xiàn)程等待——正確處理線(xiàn)程終止
#include
void pthread_exit(void *retval);
void pthread_join(pthread_t th,void *thread_return);//掛起等待th結束,*thread_return=retval;
int pthread_detach(pthread_t th);
如果線(xiàn)程處于joinable狀態(tài),則只能只能被創(chuàng )建他的線(xiàn)程等待終止。
在Linux平臺默認情況下,雖然各個(gè)線(xiàn)程之間是相互獨立的,一個(gè)線(xiàn)程的終止不會(huì )去通知或影響其他的線(xiàn)程。但是已經(jīng)終止的線(xiàn)程的資源并不會(huì )隨著(zhù)線(xiàn)程的終止而得到釋放,我們需要調用 pthread_join() 來(lái)獲得另一個(gè)線(xiàn)程的終止狀態(tài)并且釋放該線(xiàn)程所占的資源。(說(shuō)明:線(xiàn)程處于joinable狀態(tài)下)
調用該函數的線(xiàn)程將掛起,等待 th 所表示的線(xiàn)程的結束。 thread_return 是指向線(xiàn)程 th返回值的指針。需要注意的是 th 所表示的線(xiàn)程必須是 joinable 的,即處于非 detached(游離)狀態(tài);并且只可以有唯一的一個(gè)線(xiàn)程對 th 調用 pthread_join() 。如果 th 處于 detached 狀態(tài),那么對 th 的 pthread_join() 調用將返回錯誤。
如果不關(guān)心一個(gè)線(xiàn)程的結束狀態(tài),那么也可以將一個(gè)線(xiàn)程設置為 detached 狀態(tài),從而讓操作系統在該線(xiàn)程結束時(shí)來(lái)回收它所占的資源。將一個(gè)線(xiàn)程設置為detached 狀態(tài)可以通過(guò)兩種方式來(lái)實(shí)現。一種是調用 pthread_detach() 函數,可以將線(xiàn)程 th 設置為 detached 狀態(tài)。另一種方法是在創(chuàng )建線(xiàn)程時(shí)就將它設置為 detached 狀態(tài),首先初始化一個(gè)線(xiàn)程屬性變量,然后將其設置為 detached 狀態(tài),最后將它作為參數傳入線(xiàn)程創(chuàng )建函數 pthread_create(),這樣所創(chuàng )建出來(lái)的線(xiàn)程就直接處于 detached 狀態(tài)。
創(chuàng )建 detach 線(xiàn)程:
pthread_t tid;
pthread_attr_t attr;
pthread_attr_init(&attr);
pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED);
pthread_create(&tid, &attr, THREAD_FUNCTION, arg);
總之為了在使用 pthread 時(shí)避免線(xiàn)程的資源在線(xiàn)程結束時(shí)不能得到正確釋放,從而避免產(chǎn)生潛在的內存泄漏問(wèn)題,在對待線(xiàn)程結束時(shí),要確保該線(xiàn)程處于 detached 狀態(tài),否著(zhù)就需要調用 pthread_join() 函數來(lái)對其進(jìn)行資源回收。
【Linux多線(xiàn)程:線(xiàn)程的分離與結合】相關(guān)文章:
java多線(xiàn)程面試題201710-03
sun認證考試經(jīng)驗:多線(xiàn)程的幾種實(shí)現方法詳解07-24
sun認證考試輔導:java關(guān)于多線(xiàn)程的部分操作07-27
AndroidApp中使用SurfaceView制作多線(xiàn)程動(dòng)畫(huà)的實(shí)例講解09-05
Java線(xiàn)程同步的方法10-25
Linux認證概念10-29
Linux認證優(yōu)勢06-10