Random Cuda随机数生成

Random Cuda随机数生成,random,cuda,nvidia,thrust,Random,Cuda,Nvidia,Thrust,我想知道通过使用curand或其他方法,生成一个0到49k之间的伪随机数的最佳方法是什么,每个线程都是相同的 我更喜欢在内核中生成随机数,因为我必须一次生成一个随机数,但大约要生成10k次 我可以使用介于0.0和1.0之间的浮动,但我不知道如何使我的PRN对所有线程都可用,因为大多数文章和示例显示了如何为每个线程使用不同的PRN 谢谢也许你只需要学习一下,尤其是对于。为每个线程获得相同序列的关键是为每个线程创建状态(大多数示例都这样做),然后为每个线程将相同的序列号传递给init函数。在中,参数

我想知道通过使用curand或其他方法,生成一个0到49k之间的伪随机数的最佳方法是什么,每个线程都是相同的

我更喜欢在内核中生成随机数,因为我必须一次生成一个随机数,但大约要生成10k次

我可以使用介于0.0和1.0之间的浮动,但我不知道如何使我的PRN对所有线程都可用,因为大多数文章和示例显示了如何为每个线程使用不同的PRN


谢谢

也许你只需要学习一下,尤其是对于。为每个线程获得相同序列的关键是为每个线程创建状态(大多数示例都这样做),然后为每个线程将相同的序列号传递给init函数。在中,参数的顺序如下所示:

curand_init(seed, subsequence number, offset, state)
通过为每个init调用设置相同的种子,我们为每个线程生成相同的序列。通过将子序列和偏移量设置为相同,我们在该序列中为每个线程选择相同的起始值

下面是要演示的代码:

// compile with: nvcc -arch=sm_20 -lcurand -o t89 t89.cu
#include <stdio.h>
#include <curand.h>
#include <curand_kernel.h>

#define SCALE 49000
#define DSIZE 5000
#define nTPB 256

#define cudaCheckErrors(msg) \
    do { \
        cudaError_t __err = cudaGetLastError(); \
        if (__err != cudaSuccess) { \
            fprintf(stderr, "Fatal error: %s (%s at %s:%d)\n", \
                msg, cudaGetErrorString(__err), \
                __FILE__, __LINE__); \
            fprintf(stderr, "*** FAILED - ABORTING\n"); \
            exit(1); \
        } \
    } while (0)

__device__ float getnextrand(curandState *state){

  return (float)(curand_uniform(state));
}

__device__ int getnextrandscaled(curandState *state, int scale){

  return (int) scale * getnextrand(state);
}


__global__ void initCurand(curandState *state, unsigned long seed){
    int idx = threadIdx.x + blockIdx.x * blockDim.x;
    curand_init(seed, 0, 0, &state[idx]);
}

__global__ void testrand(curandState *state, int *a1, int *a2){
    int idx = threadIdx.x + blockIdx.x * blockDim.x;

    a1[idx] = getnextrandscaled(&state[idx], SCALE);
    a2[idx] = getnextrandscaled(&state[idx], SCALE);
}

int main() {

    int *h_a1, *h_a2, *d_a1, *d_a2;
    curandState *devState;

    h_a1 = (int *)malloc(DSIZE*sizeof(int));
    if (h_a1 == 0) {printf("malloc fail\n"); return 1;}
    h_a2 = (int *)malloc(DSIZE*sizeof(int));
    if (h_a2 == 0) {printf("malloc fail\n"); return 1;}
    cudaMalloc((void**)&d_a1, DSIZE * sizeof(int));
    cudaMalloc((void**)&d_a2, DSIZE * sizeof(int));
    cudaMalloc((void**)&devState, DSIZE * sizeof(curandState));
    cudaCheckErrors("cudamalloc");



     initCurand<<<(DSIZE+nTPB-1)/nTPB,nTPB>>>(devState, 1);
     cudaDeviceSynchronize();
     cudaCheckErrors("kernels1");
     testrand<<<(DSIZE+nTPB-1)/nTPB,nTPB>>>(devState, d_a1, d_a2);
     cudaDeviceSynchronize();
     cudaCheckErrors("kernels2");
     cudaMemcpy(h_a1, d_a1, DSIZE*sizeof(int), cudaMemcpyDeviceToHost);
     cudaMemcpy(h_a2, d_a2, DSIZE*sizeof(int), cudaMemcpyDeviceToHost);
     cudaCheckErrors("cudamemcpy");
     printf("1st returned random value is %d\n", h_a1[0]);
     printf("2nd returned random value is %d\n", h_a2[0]);

     for (int i=1; i< DSIZE; i++){
       if (h_a1[i] != h_a1[0]) {
         printf("mismatch on 1st value at %d, val = %d\n", i, h_a1[i]);
         return 1;
         }
       if (h_a2[i] != h_a2[0]) {
         printf("mismatch on 2nd value at %d, val = %d\n", i, h_a2[i]);
         return 1;
         }
       }
     printf("thread values match!\n");

}
//编译时使用:nvcc-arch=sm_20-lcurand-o t89 t89.cu
#包括
#包括
#包括
#定义比例尺49000
#定义DSIZE 5000
#定义nTPB 256
#定义cudaCheckErrors(msg)\
做{\
cudaError\u t\u err=cudaGetLastError()\
如果(_err!=cudaSuccess){\
fprintf(标准,“致命错误:%s(%s位于%s:%d)\n”\
msg,cudaGetErrorString(_err)\
__文件(行)\
fprintf(stderr,“***失败-中止\n”)\
出口(1)\
} \
}而(0)
__设备\uuuuu浮点getnextrand(curandState*状态){
返回(浮动)(curand_统一(州));
}
__设备\uuuuu int getnextrandscaled(curandState*状态,int比例){
返回(int)刻度*getnextrand(状态);
}
__全局\uuuuvoid initCurand(curandState*状态,无符号长种子){
int idx=threadIdx.x+blockIdx.x*blockDim.x;
curand_init(种子、0、0和状态[idx]);
}
__全局无效测试随机数(curandState*state,int*a1,int*a2){
int idx=threadIdx.x+blockIdx.x*blockDim.x;
a1[idx]=getnextrandscaled(&state[idx],比例);
a2[idx]=getnextrandscaled(&state[idx],比例);
}
int main(){
int*h_a1、*h_a2、*d_a1、*d_a2;
库兰州*devState;
h_a1=(int*)malloc(DSIZE*sizeof(int));
如果(h_a1==0){printf(“malloc fail\n”);返回1;}
h_a2=(int*)malloc(DSIZE*sizeof(int));
如果(h_a2==0){printf(“malloc fail\n”);返回1;}
cudamaloc((void**)和d_a1,DSIZE*sizeof(int));
cudamaloc((void**)和d_a2,DSIZE*sizeof(int));
Cudamaloc((无效**)和devState,DSIZE*sizeof(库兰州));
cudaCheckErrors(“Cudamaloc”);
初始值(devState,1);
cudaDeviceSynchronize();
cudaCheckErrors(“内核1”);
testrand(devState,d_a1,d_a2);
cudaDeviceSynchronize();
cudaCheckErrors(“内核2”);
cudaMemcpy(h_a1,d_a1,DSIZE*sizeof(int),cudamemcpydevicetoost);
cudaMemcpy(h_a2,d_a2,DSIZE*sizeof(int),cudamemcpydevicetoost);
cudaCheckErrors(“cudamemcpy”);
printf(“第一个返回的随机值是%d\n”,h_a1[0]);
printf(“第二个返回的随机值是%d\n”,h_a2[0]);
对于(int i=1;i