我已经使用pthreads构建了此代码。目标是建立一个数组X[N][D]
并为其分配随机值。您可以读取此数组的元素作为某些点的系数。
在下一步中,我试图计算一个数组distances[N]
,该数组保存最后一个元素(第N
个)与每个其他元素之间的所有距离。使用pthreads
执行距离计算。
#include <stdio.h>
#include <stdlib.h>
#include <pthread.h>
#include <math.h>
#define N 10
#define D 2 //works for any d
#define NUM_THREADS 8
//double *distances;
//int global_index = 0;
pthread_mutex_t lock;
double *X;
typedef struct
{
//int thread_id;
double *distances;
int *global_index ;
pthread_mutex_t lock;
double *X;
}parms;
void *threadDistance(void *arg)
{
parms *data = (parms *) arg;
double *distances = data->distances;
double *X = data->X;
int *global_idx = data -> global_index;
int idx,j;
//long id = (long)arg;
pthread_mutex_lock(&lock);
while(*global_idx<N)
{
//printf("Thread #%ld , is calculating\n", id);
idx = *(global_idx);
(*global_idx)++;
pthread_mutex_unlock(&lock);
for(j=0 ; j<D; j++)
{
distances[idx] = pow(X[(j+1)*N-1]-X[j*N+idx], 2);
//printf("dis[%d]= ", dis);
//printf("%f\n",distances[idx]);
}
//printf("global : %d\n", *global_idx);
}
pthread_exit(NULL);
}
void calcDistance(double * X, int n, int d)
{
int i;
int temp=0;
pthread_t threads[NUM_THREADS];
double *distances = malloc(n * sizeof(double));
parms arg;
arg.X = X;
arg.distances = distances;
arg.global_index = &temp;
for (i=0 ; i<NUM_THREADS ; i++)
{
pthread_create(&threads[i], NULL, threadDistance, (void *) &arg);
}
for(i = 0 ; i<NUM_THREADS; i++)
{
pthread_join(threads[i], NULL);
}
/*----print dstances[] array-------*/
printf("--------\n");
for(int i = 0; i<N; i++)
{
printf("%f\n", distances[i]);
}
/*------------*/
free(distances);
}
int main()
{
srand(time(NULL));
//allocate the proper space for X
X = malloc(D*N*(sizeof(double)));
//fill X with numbers in space (0,1)
for(int i = 0 ; i<N ; i++)
{
for(int j=0; j<D; j++)
{
X[i+j*N] = (double) (rand() / (RAND_MAX + 2.0));
}
}
calcDistance(X, N, D);
return 0;
}
问题是代码仅在N=100000
时才完全执行。如果N!=100000
代码只是挂起,我发现问题的根源是pthread_join()
函数。首先,我不明白为什么挂起取决于N
的值。
[第二,我尝试printf()
设置global_index
的值(如您所见,在此特定代码示例中已将其注释掉)。取消注释printf("global : %d\n", *global_idx);
命令后,无论N
的值如何,程序都会停止挂起。
在我看来这很疯狂,因为挂起和不挂起之间的差异是如此无关紧要。
关于:
pthread_mutex_lock(&lock);
while(*global_idx<N)
{
// ...
pthread_mutex_unlock(&lock);
结果是,在循环的第一次迭代之后,互斥锁始终处于解锁状态。建议将呼叫移至pthread_mutex_lock()
到循环顶部。
在进行了上述更正之后,我将N
设置为10000。然后重新编译,依此类推。结果是段错误事件,因此互斥锁的错误处理不是唯一的问题。
关于:
* First of all I cannot understand why the hang depends on the value of N.*
似乎程序实际上由于段错误事件而崩溃,没有挂起