c - 在 MPI C 中将矩阵和向量相乘
问题描述
我当前的 MPI 类有一个任务,我必须乘以 2x3 矩阵
1 2 3
4 5 6
由 3x1 向量 7 8 9
我被告知假设我们只有 2 个处理器。
我有以下实现,但我陷入僵局,我不知道为什么。
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <mpi.h>
int main(void)
{
int comm_sz; /* number of processes*/
int my_rank; /* my process rank */
int m, n;
double* Matrix;
double* Vector;
double* Result;
double* localMatrix;
MPI_Comm comm;
FILE *fptr = fopen("mv-data.txt", "r");
MPI_Init(NULL, NULL);
comm = MPI_COMM_WORLD;
MPI_Comm_size(comm, &comm_sz);
MPI_Comm_rank(comm, &my_rank);
if (my_rank == 0)
{
fscanf(fptr,"%d", m);
fscanf(fptr, "%d", n);
}
MPI_Bcast(m, 1, MPI_INT, 0, comm);
MPI_Bcast(n,1,MPI_INT, 0, comm);
if (my_rank==0)
{
Matrix = malloc(m*n * sizeof(double));
for(int i = 0; i<m; i++)
for(int j=0; j< n; j++)
fscanf(fptr, "%lf", &Matrix[i*n+j]);
Vector = malloc(n*sizeof(double));
for (int i = 0; i < n; i++)
fscanf(fptr,"%lf", &Vector[i]);
Result = malloc(m * sizeof(double));
for (int row = 0; row < m; row++)
{
localMatrix = malloc(m*sizeof(double));
for(int column = 0; column < n; column++)
localMatrix[column] = Matrix[row*n + column];
MPI_Send(localMatrix, n, MPI_DOUBLE, row % comm_sz, 0, comm);
}
}
MPI_Bcast(Vector, n, MPI_DOUBLE, 0,comm);
MPI_Recv(localMatrix, n, MPI_DOUBLE, 0, 0, comm, MPI_STATUS_IGNORE);
Result[my_rank] = 0;
for(int i = 0; i < n; i++)
{
Result[my_rank] += localMatrix[i] * Vector[i];
}
if (my_rank = 0)
{
for (int i = 0; i < m; i++)
printf("%d", Result[i]);
}
return 0;
}
我想不出任何其他方法可以将此进程发送到主处理器而不会导致死锁。任何帮助,将不胜感激。
解决方案
在rank 0
中,您正在使用阻塞MPI_Send
。然后其他进程调用一个集合MPI_Bcast
而不是匹配MPI_Recv
。这可能会导致死锁(缓冲可以在内部发生MPI_Send
,也可以避免死锁)。见下文:
if (my_rank==0)
{
for (int row = 0; row < m; row++)
{
MPI_Send(localMatrix, n, MPI_DOUBLE, row % comm_sz, 0, comm);
}
}
MPI_Bcast(Vector, n, MPI_DOUBLE, 0,comm); // COLLECTIVE - PROCESS MAY GET STUCK HERE
MPI_Recv(localMatrix, n, MPI_DOUBLE, 0, 0, comm, MPI_STATUS_IGNORE);
你可以试试这样的
if (my_rank==0)
{
for (int row = 0; row < m; row++)
{
MPI_Send(localMatrix, n, MPI_DOUBLE, row % comm_sz, 0, comm);
}
} else
{
MPI_Recv(localMatrix, n, MPI_DOUBLE, 0, 0, comm, MPI_STATUS_IGNORE);
}
MPI_Bcast(Vector, n, MPI_DOUBLE, 0,comm);
这肯定会避免死锁。此外,您的代码中存在问题。例如,
MPI_Recv(localMatrix, n, MPI_DOUBLE, 0, 0, comm, MPI_STATUS_IGNORE);
将导致分段错误,因为localMatrix
未分配内存。访问Result
以及也会导致分段错误,因为除了rank 0Vector
之外,您还没有在其他进程中为它分配内存(例如:rank 1 到 N-1)。
推荐阅读
- reverse-proxy - 为 cloudflare 设置自定义规则以阻止针对特定规则的攻击 IP
- regex - Firestore 规则 - 匹配 E.164 电话模式
- javascript - 使用 JSON 和 JQuery 合并和分组表
- python-3.x - AsyncSSH 创建 SFTP 客户端错误 - 太多值无法解压
- java - Sparql 查询获取超时异常
- excel - 在 excel 单元格的渲染/显示值上使用公式
- android - 如何使用改造和.net核心从android上传几张图片?
- angular - 模板解析错误:无法绑定到“任务”,因为它不是“任务列表”的已知属性
- shell - 什么shell命令将单词分成变量?
- python - Plotly中同一X轴和Y轴上的多个条形图