2017-10-05 62 views
2

這是一個非常簡單的例子,所以請多多包涵了一會兒....爲什麼我的代碼會中斷一個線程泄漏?

#include <boost/thread/thread.hpp> 
struct foo { 
    boost::thread t; 
    void do_something() { std::cout << "foo\n"; } 

    void thread_fun(){ 
     try { 
      boost::this_thread::sleep(boost::posix_time::seconds(2)); 
      { 
       boost::this_thread::disable_interruption di; 
       do_something(); 
      } 
     } catch (boost::thread_interrupted& e) {} 
    } 
    void interrupt_and_restart() { 
     t.interrupt(); 
     //if (t.joinable()) t.join(); // X 
     t = boost::thread(&foo::thread_fun,this);   
    } 
}; 

int main(){ 
    foo f; 
    for (int i=0;i<1000;i++){ 
     f.interrupt_and_restart(); 
     boost::this_thread::sleep(boost::posix_time::seconds(3)); 
    } 
} 

當我在Linux上運行的代碼,並期待在內存消耗與top我看到在虛擬持續增加內存使用(和我的實際代碼崩潰在某個時刻)。只有在中斷它之後加入線程,內存使用率纔會保持不變。這是爲什麼?

+2

所有的線程都需要一些內存來記帳(比如存儲* real *線程函數的返回值)。如果你不「加入」這個線程,那麼這個內存永遠不會被回收。 –

+0

@Someprogrammerdude出於某種原因,我的印象是,如果線程用'thread_fun'完成,它會乾淨地終止我是否加入它。我已經知道這是錯誤的,但不完全明白它 – user463035818

+0

@Someprogrammerdude offtopic這個問題:我也觀察到,這個特定的線程(我的意思是在真正的代碼中的一個,但它看起來很相似),我的驚喜使用更多內存比我的系統中的任何其他線程,我知道的唯一區別是我打斷它,但這將是一個完全不同的問題... – user463035818

回答

1

您沒有加入線程:因此,需要一些資源來跟蹤線程保持分配狀態。

未加入的線程仍使用一些系統資源,即使它已被終止(例如其線程ID仍然有效)。此外,系統可能會對同時分配的線程數量施加限制,而未加入的線程則會計入該限制。 在我的Linux VM上使用cat /proc/sys/kernel/threads-max會給我23207個線程。

當你銷燬一個可連接的線程對象時,最新版本的boost實際上應該會崩潰,而舊版本則很樂意遵守銷燬請求。