CUDA:PRNG发电机和州

时间:2014-01-19 16:11:02

标签: random cuda

我一直在玩cuRAND库来理解发电机和状态的概念。 state一词令我感到困惑,所以我希望借助一些代码澄清我的理解。

int main () {

float *hData, *dData;
curandState *devState;

size_t nThreads = 4;
size_t nRows    = 10;
size_t n        = nRows * nThreads;

hData = new float[n];
cudaMalloc((void**)&dData, n * sizeof(float));
cudaMemset(dData, 0, n * sizeof(float));

cudaMalloc((void**)&devState, nThreads * sizeof(curandState));
initCurand <<< 1, nThreads >>> (devState, 1234);
cudaDeviceSynchronize();

testrand <<< 1, nThreads >>> (devState, dData, nRows);
cudaDeviceSynchronize();
cudaMemcpy(hData, dData, n*sizeof(int), cudaMemcpyDeviceToHost);

cudaFree(devState);
cudaFree(dData);
free(hData);
}

以下是内核。

__global__ void initCurand(curandState *state, unsigned long seed)
{
    curand_init(seed, threadIdx.x, 0, &state[threadIdx.x]);
}

__global__ void testrand(curandState *state, float *d1, int rows)
{

    int idx    = threadIdx.x;
    int stride = blockDim.x;
    for (int i = 0; i < rows; i++)
    {
        d1[idx + i * stride] = curand_uniform(&state[idx]);
    }
}

简单地说,线程数量和状态一样多。每个线程消耗来自其各自状态的10个随机数。这是输出:

0.145468 0.820181 0.550399 0.294830 
0.434899 0.926417 0.811845 0.308556 
0.870710 0.511765 0.782640 0.620706 
0.455165 0.537594 0.742539 0.535606 
0.857093 0.809246 0.541354 0.497212 
0.582418 0.017524 0.195556 0.898062 
0.201404 0.449338 0.006050 0.041652 
0.786745 0.799349 0.093755 0.994597 
0.300772 0.136307 0.648018 0.970036 
0.366787 0.377424 0.096621 0.495483 

因此,我可以断定国家实际上是一个发电机吗?每个发生器/状态产生随机数的均匀分布,并且不同状态保持一定距离,使得产生的数字不重复。 ==&GT; Q1

从cuRAND指南中,我了解到创建很多状态都是计算密集型的。也试验了看。如何使用单个state(变量)生成随机数,使得每个线程从给定(单个)分布中消耗不同的随机数(或下一个随机数是队列)。 ==&GT; Q2

e.g。我有四个线程和单个状态变量,它产生一个(假设的)随机数分布如下:

2 6 100 26 81 72 78 21 33 57 19 32 ...

--------第一周期------第二周期------

线程_1: - 2 --------- 81 -
Thread_2: - 6 --------- 72 -
Thread_3: - 100 ------ 78 -
Thread_4: - 26 -------- 21 -

这是否可以使用单个状态变量?

1 个答案:

答案 0 :(得分:0)

Q1: state是数据。它代表生成随机数所需的所有数据(如种子,序列位置,子序列位置等)。

generator是一个功能。它在state的实例上运行,并创建一个随机数(根据生成器类型),并更新(修改)state

Q2: 我们生成多个状态,以便多个线程可以同时生成随机数。如果线程并行生成随机数,那么谈论服务多个线程的单个状态是没有意义的。由于在RNG过程中状态由生成器更新(参见Q1),您将有一些线程从状态读取,其他线程写入状态,这将是竞争条件,并可能导致状态损坏

您所描述的内容,第1-4个线程在第一个周期中从单个state生成2,6,100和26的位置是不可能的。