2011-01-21 95 views
1

我真正需要的是便攜式比較和打印* nix pthread標識符(pthread_t)。 pthread_equal函數存在比較兩個線程ID的相等性,但它不可能與運算符< < => =>(可移植我的意思當然),因爲在某些實現pthread_t是一個指向結構的指針。所以我找到了我想分享和討論它的便攜性的解決方案。便攜式打印和比較pthread_t

假設我們有thred_id類包裝器,它應該少於可比,平等可比,當然可打印。我在做模板類有兩個偏特 - 一個指針和一個算術類型

template <typename T, bool A = is_arithmetic<T>::value> 
struct hash 
{ 
    static unsigned long calculate(T thread_id) 
    { 
     return hash<T*, A>::calculate(&thread_id); 
    } 
}; 

template <typename T> 
struct hash<T*, false> 
{ 
    static unsigned long calculate(T* thread_id) 
    { 
     std::size_t hash = 0; 
     if (char* data = reinterpret_cast<char*>(thread_id)) 
     { 
      for (int i = 0; i < sizeof(T); ++i) 
      { 
       hash = (hash << 6)^(hash >> 26)^data[i]; 
      } 
     } 
     return hash; 
    } 
}; 

template <typename T> 
struct hash<T, true> 
{ 
    static unsigned long calculate(T thread_id) 
    { 
     return static_cast<unsigned long>(thread_id); 
    } 
}; 

那麼它是怎樣工作的。如果我們需要比較兩個線程ID,我們只是簡單地調用

pthread_equal(tid1, tid2); 

但對於運營商<我們使用哈希比較

hash<pthread_t>::calculate(tid1) < hash<pthread_t>::calculate(tid2) 

所以這裏

如果pthread_t作爲指針實現,那麼我們將爲指出的對象計算散列值。

如果是算術類型,那麼我們將嘗試將其轉換爲無符號整型。

如果它是作爲結構實現的 - 我們將計算結構對象本身的哈希值。

哈希值將僅用於運算符較少和線程ID輸出。

您對此有何看法?這種解決方案的便攜性如何,還有什麼更好的呢?

謝謝大家。

+0

爲什麼你想強制執行一個固有的無法編輯的命令?你試圖完成什麼概念? – FooF 2013-07-12 04:53:19

回答

1

而不是試圖比較pthread_t你可以封裝線程創建,並將新線程添加到一個map<some_id, pthread_t>其中id是生成和唯一的。然後你總是通過id引用線程,你可以對它們進行排序,排序,然後根據你的喜好進行比較。的pthread_t的

+0

其實我不需要在一個容器中存儲線程,我需要ti寫入thread_id包裝,它可以存儲在關聯容器中,進行比較和打印。當然,我可以在線程創建時設置處理程序,並將其存儲在某個全局映射中,但這不是我正在尋找的解決方案,在大多數情況下,pthread_t是唯一表示系統中線程的artithmetical值,我不喜歡使用代理ID。 – axe 2011-01-21 18:51:30

0

數據類型不是通過標準的固定,threfore我想提供pthread_compare()

在我的應用程序中,我還將pthread_t映射到某個唯一的ID,如Mark所建議的那樣。

here

+1

我知道它不是固定的。這是我正在努力解決的。沒有函數pthread_compare,有pthread_equal,它只檢查兩個線程ID是否相等。我在說的是與POSIX不提供的運算符(運算符<)相比較少,所以我試圖做一些。 – axe 2011-01-22 08:33:26

1

的pthread_t也未必是標量數據類型,標準說,這應該是一個不透明的類型,它可能是一個結構或聯合或位字段。

除此之外,的pthread_t,包括標量的pthread_t,可以含有填充比特,將介紹的「噪聲」影響散列結果。目前沒有通用的便攜方式來比較用戶級別的pthread_t。

事實上,在系統pthread_equal其中的pthread_t是一個指針可以返回平等即使兩個ARGS實際上是指不同的線程,例如一個線程可以退出和一個新的線程可以創建具有相同的指針值和由此的pthread_t值。

映射的唯一ID技術將工作,您不需要執行反向查找,因爲映射可能是1:n。如果您連續退出並創建線程,地圖也會變得非常大。