gpt4 book ai didi

c - C 中的多线程使用线程安全随机数

转载 作者:行者123 更新时间:2023-11-30 15:26:44 26 4
gpt4 key购买 nike

我一直试图让它通过 valgrind 泄漏检查,并传入 20 亿个随机数并在线程之间划分它们。一旦我获得 10 亿个随机数,我就会不断遇到段错误。我哪里分配错了或者我做错了什么?

struct thread
{
long long int threadID; //The thread id
long long int operations; //The number of threads
};

void *generateThreads(void *ptr)
{
struct thread *args = ptr;
struct random_data *rdata = (struct random_data *) calloc(args->operations*64,sizeof(struct random_data));
char *statebuf = (char*) calloc(args->operations*64,BUFSIZE);
long long int i;
int32_t value;

for(i = 0; i < args->operations; i++)
{
initstate_r(args->threadID,&statebuf[i],BUFSIZE,&rdata[i]);
random_r(rdata,&value);
}

if(DEBUG > 1)
printf("I am thread %lld with thread id %X\n", args->threadID, (unsigned int) pthread_self());

free(rdata);
free(statebuf);
pthread_exit(NULL);
}

int main(int argc, char **argv)
{
long long int numRandoms;
long long int numThreads;
double timeStart = 0;
double timeElapsed = 0;
pthread_t *tid;
struct thread args;

if (argc != 3)
{
fprintf(stderr, "Usage: %s <Number of Randoms> <Number of Threads>\n" ,argv[0]);
exit(1);
}

/* Assign the arg values to appropriate variables */
sscanf(argv[1],"%lld",&numRandoms); /* lld for long long int */
sscanf(argv[2],"%lld",&numThreads); /* lld for long long int */

/* Number of threads must be less than or equal to the number of random numbers */
if(numRandoms < numThreads)
{
fprintf(stderr,"Number of threads must be less than or equal to the number of random numers.\n");
exit(1);
}

/*Start*/
long long int i;
args.operations = numRandoms/numThreads;
timeStart = getMilliSeconds();
tid = (pthread_t *) calloc(numThreads,sizeof(pthread_t));

/* value is the thread id, creating threads */
for(i = 0; i < numThreads; i++)
{
args.threadID = i;
pthread_create(&tid[i],NULL,generateThreads,(void *) &args);
}

/* Joining the threads */
for(i = 0; i < numThreads; i++)
{
pthread_join(tid[i],NULL);
}

/*Output*/
timeElapsed = getMilliSeconds() - timeStart;
printf("%lf\n",(double)(timeElapsed/1000.0));
free(tid);
fflush(stdout);
exit(0);
}

最佳答案

好的,我明白你想做什么。问题在于,无论您从中复制什么代码,都使用 main 中的 initstate_r 来设置所有线程的状态。它为每个线程调用一次 initstate_r 来为该线程设置 rng。但是您将该循环复制到每个线程中,因此每个线程多次调用 initstate_r ,这是无用的。 *64 最初的目的是使每个状态占用 64 个字节,以便将它们保留在单独的缓存行上。您可能指的是 to this stackoverflow question

这是您重写的函数,使其更有意义:

void *generateThreads(void *ptr)
{
struct thread *args = ptr;
struct random_data *rdata = calloc(1,sizeof(struct random_data));
char statebuf[BUFSIZE];
long long int i;
int32_t value;

initstate_r((int) pthread_self(),statebuf,BUFSIZE,rdata);
for(i = 0; i < args->operations; i++)
{
random_r(rdata,&value);
if(DEBUG > 1)
printf("%d\n", value);
}

if(DEBUG > 1)
printf("I am thread %lld with thread id %X\n", args->threadID, (unsigned int) pthread_self());

free(rdata);
pthread_exit(NULL);
}

顺便说一句,您将参数传递给线程的方式是错误的。您将相同的 args 传递给每个线程,这意味着它们共享相同的 args 结构,这意味着它们每个共享相同的 args->threadID。您应该向每个线程传递其自己的 args 结构。

关于c - C 中的多线程使用线程安全随机数,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/27306873/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com