我正在使用CURAND库在CUDA中编写随机代码。我读到的关于随机生成的内容让我相信,如果我使用相同的种子,我将获得相同的随机数集。但是当我测试它时并非如此。请解释我做错了什么。我粘贴下面的代码供参考:
curandGenerator_t rand_gen;
status = curandCreateGenerator (&rand_gen ,CURAND_RNG_PSEUDO_DEFAULT );
if(status != CURAND_STATUS_SUCCESS){
printf("Error encountered in generating handle\n");
}
status = curandSetPseudoRandomGeneratorSeed (rand_gen ,1234ULL);
if(status != CURAND_STATUS_SUCCESS){
printf("Error encountered in setting seed\n");
}
for(j=0; j<2; j++){
status = curandGenerate(rand_gen,a_d,N);
if(status != CURAND_STATUS_SUCCESS){
printf("Error encountered in generating random numbers\n");
}
cudaMemcpy ( a_h , a_d , N * sizeof(unsigned int),cudaMemcpyDeviceToHost);
for(i = 0; i < N; i++){
printf("%d : %u\n",i,a_h[i]);
}
printf("-----------%d----------------------\n",j);
}
status = curandDestroyGenerator(rand_gen);
if(status != CURAND_STATUS_SUCCESS){
printf("Error encountered in destroying handle\n");
}
输出:
0 : 624778773 1 : 3522650202 2 : 2363946744 3 : 1266286439 4 : 3928747533 5 : 3732235839 6 : 1382638835 7 : 3362343509 8 : 48542993 9 : 1225999208 -----------0---------------------- 0 : 3356973615 1 : 1004333919 2 : 2916556602 3 : 1213079917 4 : 2705410958 5 : 520650207 6 : 1860816870 7 : 1645310928 8 : 2205755199 9 : 1282999252 -----------1----------------------
有一种伪随机发生器的“状态”概念。例如,Mersenne twister的大小约为1024个单词,而默认的一个XORWOW的状态大小只有几个单词(但它的周期也小得多)。
每当调用'setPseudoRandomGeneratorSeed'时,都会初始化生成器的状态。然后随后调用curandGenerate将更新这个状态(即从一个随机数转到下一个,状态需要重新计算),因此将生成随机序列的不同部分。
您也可以尝试使用驱动程序API - 这里curandInit()初始化每个线程的状态,这可能非常昂贵。然后对curand()或curandUniform()等的后续调用将重用此状态。实际上,每个线程都是从随机序列的不同偏移开始的
线程的调用是非常随机的,因此即使种子在主机上设置,每次运行都会生成不同的序列。