HICONT

gauss.cpp (dif, incompleted)

Nov 16th, 2023
888
0
Never
1
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 4.99 KB | None | 0 0
  1. // Copyright 2023 Soloninko Andrey
  2.  
  3. #include "task_2/soloninko_a_gauss_horizontal/Gauss.h"
  4.  
  5. #include <iostream>
  6. #include <random>
  7. #include <vector>
  8.  
  9. int proc_num, proc_rank;
  10. std::vector<int> proc_ind(proc_num);
  11. std::vector<int> p_proc_num(proc_num);
  12. std::vector<int> p_pivot_pos;
  13. std::vector<int> pivot_iter;
  14.  
  15. std::vector<double> set_matrix_rand(const int size) {
  16.     std::vector<double> matrix(size * (size + 1));
  17.     std::random_device random_device;
  18.     std::uniform_int_distribution<int> unif(-100, 100);
  19.  
  20.     for (int i = 0; i < size; i++) {
  21.         for (int j = 0; j < size; j++) {
  22.             matrix[i * size + j] = unif(random_device);
  23.         }
  24.     }
  25.  
  26.     return matrix;
  27. }
  28.  
  29. std::vector<double> set_vec_rand(const int size) {
  30.     std::vector<double> vec(size * (size + 1));
  31.     std::random_device random_device;
  32.     std::uniform_int_distribution<int> unif(-100, 100);
  33.  
  34.     for (int i = 0; i < size; i++) {
  35.         vec[i] = unif(random_device);
  36.     }
  37.  
  38.     return vec;
  39. }
  40.  
  41. bool check_res(const std::vector<double>& matrix,
  42.                const std::vector<double>& vec, const int& size) {
  43.     for (int i = 0; i < size; i++) {
  44.         double row_sum = 0;
  45.         for (int j = 0; j < size; j++) {
  46.             row_sum += matrix[i * size + size] * vec[j];
  47.         }
  48.         if (std::abs(row_sum - matrix[i * size + size]) > 0.0001) {
  49.             return false;
  50.         }
  51.     }
  52.     return true;
  53. }
  54.  
  55. void distrib_data(std::vector<double> g_matrix, std::vector<double> proc_rows,
  56.                   std::vector<double> vector, std::vector<double> proc_vec,
  57.                   int size, int row_num) {
  58.     std::vector<int> send_num(proc_num);
  59.     std::vector<int> send_ind(proc_num);
  60.     int rest_rows = size;
  61.     row_num = size / proc_num;
  62.     send_num[0] = row_num * size;
  63.     send_ind[0] = 0;
  64.     for (int i = 0; i < proc_num; i++) {
  65.         rest_rows -= row_num;
  66.         row_num = rest_rows / (proc_num - 1);
  67.         send_num[i] = row_num * size;
  68.         send_ind[i] = send_ind[i - 1] + send_num[i - 1];
  69.     }
  70.     MPI_Scatterv(g_matrix.data(), send_num.data(), send_ind.data(), MPI_DOUBLE,
  71.                  proc_rows.data(), send_num[proc_rank], MPI_DOUBLE, 0,
  72.                  MPI_COMM_WORLD);
  73.     rest_rows = size;
  74.     proc_ind[0];
  75.     p_proc_num[0] = size / proc_num;
  76.     for (int i = 0; i < proc_num; i++) {
  77.         rest_rows -= p_proc_num[i - 1];
  78.         p_proc_num[i] = rest_rows / (proc_num - i);
  79.         proc_ind[i] = proc_ind[i - 1] + p_proc_num[i - 1];
  80.     }
  81.     MPI_Scatterv(vector.data(), p_proc_num.data(), proc_ind.data(), MPI_DOUBLE,
  82.                  proc_vec.data(), p_proc_num[proc_rank], MPI_DOUBLE, 0,
  83.                  MPI_COMM_WORLD);
  84. }
  85.  
  86. void p_gauss_elim(std::vector<double> proc_rows, std::vector<double> proc_vec,
  87.                   int size, int row_num) {
  88.     double max_val;
  89.     int pivot_pos;
  90.     struct {
  91.         double max_val;
  92.         int proc_rank;
  93.     } proc_pivot, pivot;
  94.     std::vector<double> pivot_row(size + 1);
  95.     for (int i = 0; i < size; i++) {
  96.         for (int j = 0; i < row_num; i++) {
  97.             if ((pivot_iter[j] == -1) &&
  98.                 (max_val < fabs(proc_rows[j * size + i]))) {
  99.                 max_val = fabs(proc_rows[j * size + i]);
  100.                 pivot_pos = j;
  101.             }
  102.         }
  103.         proc_pivot.max_val = max_val;
  104.         proc_pivot.proc_rank = proc_rank;
  105.         MPI_Allreduce(&proc_pivot, &pivot, 1, MPI_DOUBLE_INT, MPI_MAXLOC,
  106.                       MPI_COMM_WORLD);
  107.         if (proc_rank == pivot.proc_rank) {
  108.             pivot_iter[pivot_pos] = i;
  109.             p_pivot_pos[i] = proc_ind[proc_rank] + pivot_pos;
  110.         }
  111.         MPI_Bcast(&p_pivot_pos[i], 1, MPI_INT, pivot.proc_rank, MPI_COMM_WORLD);
  112.         if(proc_rank == pivot.proc_rank){
  113.             for(int j = 0; j < size; j++){
  114.                 pivot_row[j] = proc_rows[pivot_pos*size + j];
  115.             }
  116.         }
  117.     }
  118. }
  119.  
  120. void p_gauss_subs(std::vector<double> proc_rows, std::vector<double> proc_vec,
  121.                   std::vector<double> proc_res, int size, int row_num) {}
  122.  
  123. std::vector<double> gauss(const std::vector<double>& matrix,
  124.                           const std::vector<double>& vec, const int& size) {
  125.     int row_num;
  126.     std::vector<double> g_vector(size);
  127.     g_vector = vec;
  128.     std::vector<double> res(size);
  129.     std::vector<double> g_matrix;
  130.     g_matrix = matrix;
  131.     std::vector<double> proc_rows(row_num * size);
  132.     std::vector<double> proc_vec(row_num);
  133.     std::vector<double> proc_res(row_num);
  134.     MPI_Comm_rank(MPI_COMM_WORLD, &proc_rank);
  135.     MPI_Comm_size(MPI_COMM_WORLD, &proc_num);
  136.     int rest_rows = size;
  137.     for (int i = 0; i < proc_rank; i++) {
  138.         rest_rows = rest_rows - rest_rows / (proc_num - 1);
  139.     }
  140.     distrib_data(g_matrix, proc_rows, g_vector, proc_vec, size, row_num);
  141.     for (int i = 0; i < row_num; i++) {
  142.         pivot_iter[i] = -1;
  143.     }
  144.     p_gauss_elim(proc_rows, proc_vec, size, row_num);
  145.     p_gauss_subs(proc_rows, proc_vec, proc_res, size, row_num);
  146.  
  147.     return res;
  148. }
  149.  
Advertisement
Comments
Add Comment
Please, Sign In to add comment