【问题标题】:Passing a struct to pthread_create()将结构传递给 pthread_create()
【发布时间】:2023-03-15 03:37:01
【问题描述】:

这是一个函数,它应该递归地找到更精确的 Pi 值,并拆分为用户定义的线程数量以同时执行递归。

void* quad(void* argis){
    struct args* arg=argis;

    double m=(arg->l+arg->r)/2;
    double fm=func(m);
    double larea=(arg->fl+fm)*(m-arg->l)/2;
    double rarea = (fm+arg->fr)*(arg->r-m)/2;

    struct args* arg1 = (struct args*)malloc(sizeof(struct args));
    arg1->l=arg->l;
    arg1->r=m;
    arg1->fl=arg->fl;
    arg1->fr=fm;
    arg1->area=larea;

    struct args* arg2 = (struct args*)malloc(sizeof(struct args));
    arg2->l=m;
    arg2->r=arg->r;
    arg2->fl=fm;
    arg2->fr=arg->fl;
    arg2->area=rarea;

    if(fabs((larea+rarea)-arg->area)>error){
        if(threads<=1){
            void* p1=quad((void*)arg1);
            void* p2=quad((void*)arg2);
            larea=*((double*)p1);
            rarea=*((double*)p2);
            free(p1);
            free(p2);


        }
        else{
            pthread_t thread1, thread2;
            pthread_mutex_lock(&lock1);
            threads--;
            pthread_mutex_unlock(&lock1);

            pthread_create(&thread1, NULL, &quad, (void*)&arg1);
            pthread_create(&thread2, NULL, &quad, (void*)&arg2);

            void* ptr1;
            void* ptr2;

            pthread_join(thread1,&ptr1);
            pthread_join(thread2,&ptr2);


            pthread_mutex_lock(&lock1);
            threads++;
            pthread_mutex_unlock(&lock1);

            larea=*(double*)ptr1;
            rarea=*(double*)ptr2;


        }
    }
    free(arg1);
    free(arg2);

    double ret= (larea+rarea);
    double* poin=(double*)malloc(sizeof(double));
    *poin=ret;

    return (void*)poin;
}

但是,它不起作用。经过调查,我发现问题似乎在这里:

pthread_create(&thread1, NULL, &quad, (void*)&arg1);
pthread_create(&thread2, NULL, &quad, (void*)&arg2);

struct arg1arg2 中的所有参数在传入新线程后才变为 0。 arg1arg2 不是本地的,它们在堆中,我很确定线程共享堆,所以这不是问题。这不是您将参数传递给pthread_create() 中的新线程的方式吗?

这是我第一次使用 pthreads,所以请耐心等待。但是任何帮助找出导致结构被重置的原因将不胜感激。谢谢!

【问题讨论】:

  • 发布的代码无法编译。它缺少main() 函数,缺少必要的#include 语句。它也是非常递归的,会生成很多很多线程。另请注意,退出线程应通过调用 pthread_exit()
  • 顺便说一句,在获取函数的地址时,“地址”(即&amp;)运算符是不必要的,所以pthread_create(&amp;thread1, NULL, quad, arg1)是首选。
  • @user3629249 pthread_exit 是可选的。 void * return 工作得很好。类比是main:它可以通过exit(1) 退出或只是return 1

标签: c multithreading debugging struct pthreads


【解决方案1】:

因为 arg1arg2 指针,您已经希望将它们传递给 pthread_create() “原样”:

  pthread_create(&thread1, NULL, &quad, arg1);

这里也不需要投射:

  void* p1=quad((void*)arg1);

只要做:

  void* p1=quad(arg1);

malloc() 相同,无需转换结果。

也不在这里:

  return (void*)poin;

在做

  return poin;

没问题。

在 C 中,任何指向/来自 void* 的指针的转换都是隐式完成的。

【讨论】:

  • 是的,就是这样!尽管两个线程的运行速度比一个线程慢。对此有什么想法?
  • 是的,一些想法:1) 线程需要上下文交换,这需要时间 2) 代码(当变量 threads 大于 1 时)是大量递归的并且产生更多线程。递归和产生更多线程需要时间
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-09-26
  • 2015-12-24
  • 2011-07-21
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多