您可以在同一个函数中使用多个互斥锁 lock/unlock 和不同的键来计算数据结构中的平均值吗?
Can you use multiple mutex lock/unlock with non-identical keys within the same function to calculate average in a data structure?
假设我想计算大小为 N 的 数组 X 中值的平均值。假设我们使用 T 个线程,其中 T 是 N 的一部分,所以我们是多线程。
是否可以声明两个唯一的互斥键并无误地执行以下操作?
编辑:关于如何计算平均值、最大值、最小值等的任何想法?
见下文:
#include <stdio.h>
#include <pthread.h>
void* sum(void* arg);
int sum = 0;
int average = 0;
int x[N];
int main()
{
int i;
pthread_t threads[T];
for(i=0; i<T; i++)
pthread_create(&x[i], NULL, sum, (void *)i);
for(i=0; i<T; i++)
pthread_join(x[i], NULL);
}
void* sum(void* arg)
{
int counter = 0;
int *id = (int *) arg;
pthread_mutex_t key1;
pthread_mutex_t key2;
int size = N/T;
int start = id * size;
int end = id * size + size;
for(i=start; i<end; i++)
{
counter = counter + x[i];
}
pthread_mutex_lock(&key1);
sum += counter;
pthread_mutex_unlock(&key1);
pthread_mutex_lock(&key2);
average = sum / counter;
pthread_mutex_lock(&key2);
return NULL;
}
不,这是一场灾难。每个线程将调用 sum
并且它们将各自获得自己的互斥锁。这意味着一个线程可以锁定其 key2
,同时另一个线程可以锁定其 key2
。所以两个线程可以同时访问average
。
您只需要一个互斥锁来保护 average
。否则,它实际上并没有受到保护。
(此外,您同时拥有一个函数和一个名为 sum
的全局变量。这会导致痛苦和混乱。)
你还有一个问题。每个线程都使用共享 sum
并将其除以其私有 counter
。那根本没有任何意义。 sum
变量需要除以它求和的条目总数以获得平均值,而不是该特定线程添加的条目数。
我建议进行两项更改:
- 只有一个互斥锁。使其成为全球性的。
- 没有
sum
函数接触 average
变量。加入所有线程后,只需执行 average = sum / N;
.
假设我想计算大小为 N 的 数组 X 中值的平均值。假设我们使用 T 个线程,其中 T 是 N 的一部分,所以我们是多线程。
是否可以声明两个唯一的互斥键并无误地执行以下操作?
编辑:关于如何计算平均值、最大值、最小值等的任何想法?
见下文:
#include <stdio.h>
#include <pthread.h>
void* sum(void* arg);
int sum = 0;
int average = 0;
int x[N];
int main()
{
int i;
pthread_t threads[T];
for(i=0; i<T; i++)
pthread_create(&x[i], NULL, sum, (void *)i);
for(i=0; i<T; i++)
pthread_join(x[i], NULL);
}
void* sum(void* arg)
{
int counter = 0;
int *id = (int *) arg;
pthread_mutex_t key1;
pthread_mutex_t key2;
int size = N/T;
int start = id * size;
int end = id * size + size;
for(i=start; i<end; i++)
{
counter = counter + x[i];
}
pthread_mutex_lock(&key1);
sum += counter;
pthread_mutex_unlock(&key1);
pthread_mutex_lock(&key2);
average = sum / counter;
pthread_mutex_lock(&key2);
return NULL;
}
不,这是一场灾难。每个线程将调用 sum
并且它们将各自获得自己的互斥锁。这意味着一个线程可以锁定其 key2
,同时另一个线程可以锁定其 key2
。所以两个线程可以同时访问average
。
您只需要一个互斥锁来保护 average
。否则,它实际上并没有受到保护。
(此外,您同时拥有一个函数和一个名为 sum
的全局变量。这会导致痛苦和混乱。)
你还有一个问题。每个线程都使用共享 sum
并将其除以其私有 counter
。那根本没有任何意义。 sum
变量需要除以它求和的条目总数以获得平均值,而不是该特定线程添加的条目数。
我建议进行两项更改:
- 只有一个互斥锁。使其成为全球性的。
- 没有
sum
函数接触average
变量。加入所有线程后,只需执行average = sum / N;
.