2010-11-07 68 views
2

是否存在,而在Linux GCC使用pthread.h保持局部變量線程功能的方法:保持並行線程局部變量

int i = 42; // global instance of i  

int main() { 
    pthread_t threads[2]; 
    long t; 
    pthread_create(&threads[t], NULL, ThreadFunction, (void *) t; 
    pthread_create(&threads[t], NULL, ThreadFunction2, (void *) t; 
} 

我不知道是否有在POSIX函數中的參數創建新的線程並保持局部變量:

void *ThreadFunction(void *threadid) 
{ 
    int i=0; 
    i++; // this is a local instance of i 
    printf("i is %d", i); // as expected: 1 
} 

void *ThreadFunction2(void *threadid) 
{ 
    i += 3; // another local instance -> problem 
} 

事後哪裏是i 42.就算我已經定義了一個i以前我想這i不要被我的線程中。

+2

你的問題是什麼?代碼中的所有'i's都是局部變量。結果42證實了這一點。 – 2010-11-07 18:04:03

+0

恩,這個例子很糟糕...我明白了。我想我在線程1是1,在線程2是3,並保持那樣...必須編輯。 – wishi 2010-11-07 18:09:07

+0

@Duck:你可以修改哪些代碼?簡單的解決方案是在本地聲明第二個'i'。 – kennytm 2010-11-07 18:18:11

回答

3

全局變量總是在整個編譯單元中可用(如果使用外部聲明,甚至可以使用更多編譯單元)。這與線程無關,它是C/C++的默認行爲。推薦的解決方案是不使用全局變量 - 全局變量是邪惡的。如果您仍然需要使用全局變量,那麼您可能需要爲它們加前綴,例如g_i。另一個解決方案是將你的線程函數放入另一個編譯單元(c文件)。

2

示例代碼錯誤(本身)並且具有未定義的行爲。您正嘗試讀取四次未讀初始化的變量t - 兩次以在一個演員表達式中編入索引並兩次 - 並根據&threads[t]的含義(未定義),函數pthread_create可能會導致更多的UB。

此外,它顯然不是您使用的代碼,因爲pthread_create函數缺少關閉括號。

關於變量i:聲明一個新的變量i(即int i = 0)在局部範圍內的更廣泛的範圍內隱藏任何可能i的 - 所以不應該使用i本地AS內部的變量名的任何問題功能。

+0

+1很棒但我認爲這不是一個真正的答案;) – 2010-11-07 18:19:37

5

GCC中,你可以做一個全局變量線程局部使用__thread符:

__thread int i = 42; 

不要那樣做。有更好的解決方案,取決於你想要做的。

1

phtread具有線程本地存儲的概念,gcc通過__thread存儲類爲其提供了一個簡單的接口。這些變量受到全局變量的所有問題的困擾,然後還有更多。但有時它們很方便,因爲所有其他解決方案在上下文中都較差。