#include <mpi.h>
#include <iostream>
#include <vector>
const int SIZE = 20;
// Fungsi untuk mengisi matriks dengan bilangan ganjil mulai dari 1
void fillMatrixA(std::vector<std::vector<int>> &matrix) {
int value = 1;
for (int i = 0; i < SIZE; ++i) {
for (int j = 0; j < SIZE; ++j) {
matrix[i][j] = value;
value += 2;
}
}
}
// Fungsi untuk mengisi matriks dengan bilangan genap mulai dari 2
void fillMatrixB(std::vector<std::vector<int>> &matrix) {
int value = 2;
for (int i = 0; i < SIZE; ++i) {
for (int j = 0; j < SIZE; ++j) {
matrix[i][j] = value;
value += 2;
}
}
}
// Fungsi utama
int main(int argc, char *argv[]) {
MPI_Init(&argc, &argv);
int rank, size;
MPI_Comm_rank(MPI_COMM_WORLD, &rank);
MPI_Comm_size(MPI_COMM_WORLD, &size);
std::vector<std::vector<int>> A(SIZE, std::vector<int>(SIZE));
std::vector<std::vector<int>> B(SIZE, std::vector<int>(SIZE));
std::vector<std::vector<int>> C(SIZE, std::vector<int>(SIZE, 0));
if (rank == 0) {
// Proses utama mengisi matriks A dan B
fillMatrixA(A);
fillMatrixB(B);
}
// Broadcast matriks B ke semua proses
for (int i = 0; i < SIZE; ++i) {
MPI_Bcast(B[i].data(), SIZE, MPI_INT, 0, MPI_COMM_WORLD);
}
// Bagian dari matriks A yang akan dihitung oleh setiap proses
std::vector<int> localA(SIZE * SIZE / size);
// Scatter matriks A ke semua proses
MPI_Scatter(A[0].data(), SIZE * SIZE / size, MPI_INT, localA.data(), SIZE * SIZE / size, MPI_INT, 0, MPI_COMM_WORLD);
// Hasil lokal untuk bagian dari matriks C
std::vector<int> localC(SIZE * SIZE / size, 0);
// Hitung hasil lokal
int rowsPerProcess = SIZE / size;
for (int i = 0; i < rowsPerProcess; ++i) {
for (int j = 0; j < SIZE; ++j) {
for (int k = 0; k < SIZE; ++k) {
localC[i * SIZE + j] += localA[i * SIZE + k] * B[k][j];
}
}
}
// Gabungkan hasil dari semua proses ke proses utama
MPI_Gather(localC.data(), SIZE * SIZE / size, MPI_INT, C[0].data(), SIZE * SIZE / size, MPI_INT, 0, MPI_COMM_WORLD);
if (rank == 0) {
// Cetak hasil matriks C
std::cout << "Hasil perkalian matriks A dan B adalah:\n";
for (int i = 0; i < SIZE; ++i) {
for (int j = 0; j < SIZE; ++j) {
std::cout << C[i][j] << " ";
}
std::cout << "\n";
}
}
MPI_Finalize();
return 0;
}
I2luY2x1ZGUgPG1waS5oPgojaW5jbHVkZSA8aW9zdHJlYW0+CiNpbmNsdWRlIDx2ZWN0b3I+Cgpjb25zdCBpbnQgU0laRSA9IDIwOwoKLy8gRnVuZ3NpIHVudHVrIG1lbmdpc2kgbWF0cmlrcyBkZW5nYW4gYmlsYW5nYW4gZ2FuamlsIG11bGFpIGRhcmkgMQp2b2lkIGZpbGxNYXRyaXhBKHN0ZDo6dmVjdG9yPHN0ZDo6dmVjdG9yPGludD4+ICZtYXRyaXgpIHsKICAgIGludCB2YWx1ZSA9IDE7CiAgICBmb3IgKGludCBpID0gMDsgaSA8IFNJWkU7ICsraSkgewogICAgICAgIGZvciAoaW50IGogPSAwOyBqIDwgU0laRTsgKytqKSB7CiAgICAgICAgICAgIG1hdHJpeFtpXVtqXSA9IHZhbHVlOwogICAgICAgICAgICB2YWx1ZSArPSAyOwogICAgICAgIH0KICAgIH0KfQoKLy8gRnVuZ3NpIHVudHVrIG1lbmdpc2kgbWF0cmlrcyBkZW5nYW4gYmlsYW5nYW4gZ2VuYXAgbXVsYWkgZGFyaSAyCnZvaWQgZmlsbE1hdHJpeEIoc3RkOjp2ZWN0b3I8c3RkOjp2ZWN0b3I8aW50Pj4gJm1hdHJpeCkgewogICAgaW50IHZhbHVlID0gMjsKICAgIGZvciAoaW50IGkgPSAwOyBpIDwgU0laRTsgKytpKSB7CiAgICAgICAgZm9yIChpbnQgaiA9IDA7IGogPCBTSVpFOyArK2opIHsKICAgICAgICAgICAgbWF0cml4W2ldW2pdID0gdmFsdWU7CiAgICAgICAgICAgIHZhbHVlICs9IDI7CiAgICAgICAgfQogICAgfQp9CgovLyBGdW5nc2kgdXRhbWEKaW50IG1haW4oaW50IGFyZ2MsIGNoYXIgKmFyZ3ZbXSkgewogICAgTVBJX0luaXQoJmFyZ2MsICZhcmd2KTsKCiAgICBpbnQgcmFuaywgc2l6ZTsKICAgIE1QSV9Db21tX3JhbmsoTVBJX0NPTU1fV09STEQsICZyYW5rKTsKICAgIE1QSV9Db21tX3NpemUoTVBJX0NPTU1fV09STEQsICZzaXplKTsKCiAgICBzdGQ6OnZlY3RvcjxzdGQ6OnZlY3RvcjxpbnQ+PiBBKFNJWkUsIHN0ZDo6dmVjdG9yPGludD4oU0laRSkpOwogICAgc3RkOjp2ZWN0b3I8c3RkOjp2ZWN0b3I8aW50Pj4gQihTSVpFLCBzdGQ6OnZlY3RvcjxpbnQ+KFNJWkUpKTsKICAgIHN0ZDo6dmVjdG9yPHN0ZDo6dmVjdG9yPGludD4+IEMoU0laRSwgc3RkOjp2ZWN0b3I8aW50PihTSVpFLCAwKSk7CgogICAgaWYgKHJhbmsgPT0gMCkgewogICAgICAgIC8vIFByb3NlcyB1dGFtYSBtZW5naXNpIG1hdHJpa3MgQSBkYW4gQgogICAgICAgIGZpbGxNYXRyaXhBKEEpOwogICAgICAgIGZpbGxNYXRyaXhCKEIpOwogICAgfQoKICAgIC8vIEJyb2FkY2FzdCBtYXRyaWtzIEIga2Ugc2VtdWEgcHJvc2VzCiAgICBmb3IgKGludCBpID0gMDsgaSA8IFNJWkU7ICsraSkgewogICAgICAgIE1QSV9CY2FzdChCW2ldLmRhdGEoKSwgU0laRSwgTVBJX0lOVCwgMCwgTVBJX0NPTU1fV09STEQpOwogICAgfQoKICAgIC8vIEJhZ2lhbiBkYXJpIG1hdHJpa3MgQSB5YW5nIGFrYW4gZGloaXR1bmcgb2xlaCBzZXRpYXAgcHJvc2VzCiAgICBzdGQ6OnZlY3RvcjxpbnQ+IGxvY2FsQShTSVpFICogU0laRSAvIHNpemUpOwoKICAgIC8vIFNjYXR0ZXIgbWF0cmlrcyBBIGtlIHNlbXVhIHByb3NlcwogICAgTVBJX1NjYXR0ZXIoQVswXS5kYXRhKCksIFNJWkUgKiBTSVpFIC8gc2l6ZSwgTVBJX0lOVCwgbG9jYWxBLmRhdGEoKSwgU0laRSAqIFNJWkUgLyBzaXplLCBNUElfSU5ULCAwLCBNUElfQ09NTV9XT1JMRCk7CgogICAgLy8gSGFzaWwgbG9rYWwgdW50dWsgYmFnaWFuIGRhcmkgbWF0cmlrcyBDCiAgICBzdGQ6OnZlY3RvcjxpbnQ+IGxvY2FsQyhTSVpFICogU0laRSAvIHNpemUsIDApOwoKICAgIC8vIEhpdHVuZyBoYXNpbCBsb2thbAogICAgaW50IHJvd3NQZXJQcm9jZXNzID0gU0laRSAvIHNpemU7CiAgICBmb3IgKGludCBpID0gMDsgaSA8IHJvd3NQZXJQcm9jZXNzOyArK2kpIHsKICAgICAgICBmb3IgKGludCBqID0gMDsgaiA8IFNJWkU7ICsraikgewogICAgICAgICAgICBmb3IgKGludCBrID0gMDsgayA8IFNJWkU7ICsraykgewogICAgICAgICAgICAgICAgbG9jYWxDW2kgKiBTSVpFICsgal0gKz0gbG9jYWxBW2kgKiBTSVpFICsga10gKiBCW2tdW2pdOwogICAgICAgICAgICB9CiAgICAgICAgfQogICAgfQoKICAgIC8vIEdhYnVuZ2thbiBoYXNpbCBkYXJpIHNlbXVhIHByb3NlcyBrZSBwcm9zZXMgdXRhbWEKICAgIE1QSV9HYXRoZXIobG9jYWxDLmRhdGEoKSwgU0laRSAqIFNJWkUgLyBzaXplLCBNUElfSU5ULCBDWzBdLmRhdGEoKSwgU0laRSAqIFNJWkUgLyBzaXplLCBNUElfSU5ULCAwLCBNUElfQ09NTV9XT1JMRCk7CgogICAgaWYgKHJhbmsgPT0gMCkgewogICAgICAgIC8vIENldGFrIGhhc2lsIG1hdHJpa3MgQwogICAgICAgIHN0ZDo6Y291dCA8PCAiSGFzaWwgcGVya2FsaWFuIG1hdHJpa3MgQSBkYW4gQiBhZGFsYWg6XG4iOwogICAgICAgIGZvciAoaW50IGkgPSAwOyBpIDwgU0laRTsgKytpKSB7CiAgICAgICAgICAgIGZvciAoaW50IGogPSAwOyBqIDwgU0laRTsgKytqKSB7CiAgICAgICAgICAgICAgICBzdGQ6OmNvdXQgPDwgQ1tpXVtqXSA8PCAiICI7CiAgICAgICAgICAgIH0KICAgICAgICAgICAgc3RkOjpjb3V0IDw8ICJcbiI7CiAgICAgICAgfQogICAgfQoKICAgIE1QSV9GaW5hbGl6ZSgpOwogICAgcmV0dXJuIDA7Cn0K