Untitled

 avatar
unknown
plain_text
3 years ago
3.6 kB
7
Indexable
#include <stdio.h>
#include <stdlib.h>
#include <sys/time.h>
#include <string.h>
#include <math.h>
#include <omp.h>


int main(int argc, char *argv[]){  	

    int n = 1024;			// Dimensiune matrice
    int p = 1;				// Numar thread-uri
    int mod = 0;			// Mod 0: partitionare pe linii
    int max_rep = 1;			// Numar de repetari ale executiei

    float **a, *b, *c; 		// Matricele de date
    int i, j, k, t, f, d, rep;
    char *text_mod;
	
    struct timeval t1, t2;	
    float tp;   
    char *fn = "Res_Matrix_Mult_OpenMP.txt";	    
    FILE *fp;

    // Citire parametri        
    if (argc >= 2)  n = atoi(argv[1]);
    if (argc >= 3)  p = atoi(argv[2]);        
    if (argc >= 4)  mod = atoi(argv[3]);
    if (argc >= 5)  max_rep = atoi(argv[4]);

    // Testare parametri
    if (n < 2){
        printf("Eroare: n < 2 \n");
        exit(0);
    }
    if (p < 1){
        printf("Eroare: p < 1 \n");
        exit(0);
    }
    if (max_rep < 1){
        printf("Eroare: max_rep < 1 \n");
        exit(0);
    }
    // La partitionare in blocuri: p patrat perfect, n divizibil cu sqrt(p)
    if (mod == 5){  	
        if (sqrt(p) != (int)sqrt(p)) {
            printf("Eroare: partitionare in blocuri (mod = %d) si p nu este patrat perfect\n",mod);
            exit(0);
        }
        if (n % (int)sqrt(p) != 0) {
            printf("Eroare: partitionare in blocuri (mod = %d) si n nu este divizibil cu sqrt(p)\n",mod);
            exit(0);        
        }
    }
    f = sqrt(p);
    d = n/f;

    // Alocarea datelor
    a = (float**)malloc(sizeof(float*)*n);
    b = (float*)malloc(sizeof(float)*n);
    c = (float*)malloc(sizeof(float)*n);
 
    for (i = 0; i < n; i++){
        a[i] = (float*)malloc(sizeof(float)*n);
    }      
    // Initializare matrice a, b
    for (i = 0; i < n; i++){
        b[i] = 1;
        for (j = 0; j < n; j++) {
            a[i][j] = 1;     
        } 
    }
    
    gettimeofday(&t1, NULL);

    for (rep = 0; rep < max_rep; rep++){

        if (p == 1) { 	
        // Adunarea secventiala a doua matrice 
            text_mod = "Adunare secventiala";     
            for (i = 0; i < n; i++){
                c[i]= 0;
                for (j = 0; j < n; j++){
                    c[i] += a[i][j] * b[j];
                }
            }
       } 
       // Adunarea paralela a doua matrice
        else if (mod == 0) {  
            text_mod = "mod 0: Adunare paralela cu partitionare pe linii cu 1 regiune paralela";      
    	    #pragma omp parallel num_threads(p) shared (a, b, c, n) private (i, j)
    	    {        
    	        #pragma omp for        
      	        for (i = 0; i < n; i++){
                    c[i]= 0;
                    for (j = 0; j < n; j++){
                        c[i] += a[i][j] * b[j];
                    }
                }
            } 
        }
        else {
	        printf("Eroare: mod %d - inexistent\n", mod);
            exit (0);
      }

    }   // end for (rep) 

    gettimeofday(&t2, NULL);
    tp = ((float)(t2.tv_sec - t1.tv_sec) + 0.000001*(t2.tv_usec - t1.tv_usec))/max_rep;
	
    // Scriere timp de executie in fisier
    fp = fopen(fn, "a");
    if (p == 1) fprintf(fp, "\n%f  ",tp);
    else fprintf(fp, "%f  ",tp);
    fclose(fp);

    // Afisare timp executie mediat pe max_rep teste repetate
    printf("%s \n", text_mod);
    printf("%d rep, n = %d, p = %d, t = %f sec\n", max_rep, n, p, tp);
    
    // Afisare rezultate 
    if (n <= 16)
    {
	    for (i = 0; i < n; i++){ 
	        printf("%4.0f  ", c[i]);
        }
        printf("\n");

    }
    return 0; 
}
Editor is loading...