如何使用pthread,pthread_exit将*转换为double / float

时间:2018-11-20 14:31:38

标签: c unix pthreads pthread-join pthread-exit

我需要创建一个程序来计算递归(对于某些序列)。当我使用int并清除一个递归时,它将计算不带浮点数的值(例如fibonacci序列,该值仅返回中性数),它可以工作。但是,当尝试使用基于除法的序列(带有浮点数)时,会显示如下错误:

错误:无法转换为浮动类型 pthread_exit((void *)(float)wynik;

我应该如何更改代码(或者实际上是一个* ciag函数,因为那是问题所在),使其可以接受浮点数?

正常工作的函数(带有int)

int* fibo(int n){

   int wynik;
   int* n1;
   if (n==0) wynik=0;
   else if (n==1) wynik=1;
   else wynik =(int)fibo((int)(n-1))+(int)fibo((int)(n-2));
   return (int*)wynik;
   pthread_exit((void*)wynik);
}

我遇到的问题(使用浮点数,但是当我尝试使用double时也会发生同样的情况)

    #include <unistd.h>

#include <pthread.h>
#include <stdio.h>

#define COUNT 2

float *ciag(int n) {
    float wynik;

    if(n == 0)
        wynik = -1;
    else
        wynik = ((float)ciag(n - 1)*(n + 1))/(float)ciag(n - 1)*(float)ciag(n - 1)*(float)ciag(n - 1);

    return(float *)wynik;
    pthread_exit((void *)wynik);
}

void *drugi_watek(void* wynik) {
    int i = 1;  

        while(i == 0) {
        printf("#");
        fflush(stdout);
        usleep(300000);
        pthread_exit((void*)wynik);
    }
}

int main() {
    pthread_t watek_1, watek_2;
    int n;
    float wynik;
    printf("Podaj numer ciagu: ");
    scanf("%d", &n); 

    pthread_create(&watek_1, NULL,(void*)&ciag, n);
    pthread_create(&watek_2, NULL, &drugi_watek, NULL);

    if(!pthread_join(watek_1,(void**)&wynik))
    {
    pthread_cancel(watek_2);
    }

    printf("Element numer %f ciagu: %f\n", &n, &wynik);


    return 0;
}

1 个答案:

答案 0 :(得分:1)

您不能直接将float转换为void *,反之亦然。

最干净的方法是为float分配空间(从堆或在调用者的堆栈上),并使线程函数将float的值存储到指针中-to变量(float * 易于与void *进行转换)。如果使用此路由并在堆栈上分配值,则需要确保在线程完成之前,调用方的堆栈框架仍然存在。

由于您要调用的函数是递归的,因此将其作为线程函数太麻烦了。最好使它成为一个单独的(普通)函数,该函数接受一个int参数并返回一个float。然后制作一个包装函数,将其作为pthread_create的目标。

并且由于您还需要将参数int传递给函数,因此最简单的方法是分配一个struct来包含参数和返回值(union也可以工作,因为您(实际上并不需要同时返回参数)。这是演示该模式的示例程序:

#include <pthread.h>
#include <stdio.h>

static float ciag(int n)
{
    float wynik;

    if(n == 0)
        wynik = -1;
    else
        wynik = (ciag(n - 1)*(n + 1))/ciag(n - 1)*ciag(n - 1)*ciag(n - 1);

    return wynik;
}

typedef struct {
    int i;
    float f;
} if_t;

static void *ciag_thread(void *vp)
{
    if_t *ifp = vp;
    // Obtain argument from the structure and put the result back into the structure
    ifp->f = ciag(ifp->i);
    return vp;
}

int main()
{
    pthread_t watek_1;

    int n = 4;

    // Obtain n however you like. Then place argument into structure allocated 
    // on the stack
    if_t arg;
    arg.i = n;

    // Pointer to structure is implicitly convertible to (void *)
    pthread_create(&watek_1, NULL, ciag_thread, &arg);
    pthread_join(watek_1, NULL);
    printf("Thread returned %f\n", arg.f);
    return 0;
}

另一个说明。您的代码似乎表明第一个线程上的pthread_join有时可能会失败。这不会在这里发生。尽管对于较大的n值,由于函数的二次性质,可能需要很长时间才能完成。