Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- #include<stdio.h>
- #include<stdlib.h>
- #include<mpi.h>
- #include<unistd.h>
- #include<math.h>
- double func(double x) {
- return x*x;
- }
- double integrate(double (*func)(double), double begin, double end, int num_points) {
- double result = 0.0;
- double step = (end - begin) / (double)num_points;
- double y;
- for (int i=1; i<=num_points; i++) {
- y = func(begin + i * step);
- result += y * step;
- }
- return result;
- }
- int main(int argc, char **argv) {
- MPI_Init(NULL, NULL);
- int world_rank;
- MPI_Comm_rank(MPI_COMM_WORLD, &world_rank);
- int world_size;
- MPI_Comm_size(MPI_COMM_WORLD, &world_size);
- int tag = 5;
- int destination = world_size-1; // destination process
- if (destination >= world_size) {
- MPI_Abort(MPI_COMM_WORLD, 1); // destination process must be under the number of processes created, otherwise abort
- }
- // double *partial_sums = malloc((world_size-1) * sizeof(double) );
- double partial_sums[world_size-1];
- double begin = argc > 1 ? atof(argv[1]) : 0;
- double end = argc > 2 ? atof(argv[2]) : 2;
- int num_points = argc > 3 ? atoi(argv[3]) : 10000;
- double step = (end - begin) / num_points;
- MPI_Request request = MPI_REQUEST_NULL;
- MPI_Status status;
- int additional = num_points % world_size;
- int elements_number = (int)floor(num_points / world_size);
- double range_begin, partial_sum;
- if (world_rank < additional) {
- range_begin = elements_number * world_rank;
- elements_number++;
- } else {
- range_begin = (elements_number + 1) * additional + (world_rank - additional) * elements_number;
- }
- range_begin *= step;
- double range_end = range_begin + (elements_number * step);
- // printf("rank %d\n", world_rank);
- if (world_rank == destination) {
- double result = integrate(func, range_begin, range_end, elements_number);
- // odbieramy wyniki
- for (int i = 0; i < world_size; i++) {
- MPI_Wait(&request, &status);
- // if(i == destination)
- // break;
- partial_sum = partial_sums[i-1];
- MPI_Irecv(&partial_sum, 1, MPI_DOUBLE, i, tag, MPI_COMM_WORLD, &request);
- result += partial_sum;
- }
- // for (int i=0; i<world_size-1; i++)
- // MPI_Irecv(&partial_sum, 1, MPI_DOUBLE, i, tag, MPI_COMM_WORLD, &request);
- // for (int i=0; i<world_size; i++) result += partial_sums[i];
- printf("Wynik całkowania funkcji y = x^2: %g\n", result);
- } else {
- // obliczamy wyniki cząstkowe
- partial_sums[world_rank-1] = integrate(func, range_begin, range_end, elements_number);
- MPI_Isend(&partial_sums[world_rank-1], 1, MPI_DOUBLE, destination, tag, MPI_COMM_WORLD, &request);
- printf("part res %g\n", partial_sums[world_rank-1]);
- }
- // if (partial_sums != NULL) {
- // free(partial_sums);
- // partial_sums = NULL;
- // }
- MPI_Finalize();
- }
- // metoda prostokątów
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement