2017-04-01 348 views
0

有人問我要不要使用rand()因爲他們不是「線程安全」,並每次也使用不同的種子值。我使用這樣的種子值發現在GitHub例子:如何使用rand_r()在C中創建線程安全的隨機數生成器?

unsigned int seed = time(NULL);

即僅具有由秒的精度。由於該程序在1秒內運行,我最終得到每個實例相同的隨機數。

我將如何解決這個問題的算法,以便它僅使用rand_r()或任何其他「線程安全」的方法來生成10張隨機數?

int main() 
{ 
    for(int i = 0; i < 10; i++){ 
     int random; 
     unsigned int seed = time(NULL); 
      random = 1 + (rand_r(&seed)% 10); 
     printf("%d\n",random); 
    } 
return 0; 
} 
+1

由於有這麼多類似的問題 - 唯一的種子** **一次。 –

+0

Huh ..odd。爲什麼播種多次導致數字完全相同? – btramisetty

+2

因爲'rand_r'是帶一個參數確定性函數 - seed'的'值。 –

回答

0

rand_r函數帶有一個指向狀態變量的指針。在第一次調用rand_r之前,它被設置爲種子值。然後,每次撥打rand_r時,都會傳遞此值的地址。

是線程安全的,每個線程都需要有自己的狀態變量。你不不過要用於每個線程的狀態變量相同的初始值,否則每個線程會產生僞隨機值相同的序列。

您需要與種子數據的狀態變量的不同之爲每個線程,諸如線程id,加上其他信息,諸如時間和/或PID。

例如:

// 2 threads, 1 state variable each 
unsigned int state[2]; 

void *mythread(void *p_mystate) 
{ 
    unsigned int *mystate = p_mystate; 
    // XOR multiple values together to get a semi-unique seed 
    *mystate = time(NULL)^getpid()^pthread_self(); 

    ... 
    int rand1 = rand_r(mystate); 
    ... 
    int rand2 = rand_r(mystate); 
    ... 
    return NULL; 
} 

int main() 
{ 
    pthread_t t1, t2; 

    // give each thread the address of its state variable 
    pthread_create(&t1, NULL, mythread, &state[0]); 
    pthread_create(&t2, NULL, mythread, &state[1]); 
    ... 
    pthread_join(t1, NULL); 
    pthread_join(t2, NULL); 
    return 0; 
} 
相關問題