/*multiplica duas matrizes e guarda o resultado em uma matriz resultante*/ void multiplica_matrizes(void) { Matriz matriz_A = {NULL,1,1}, matriz_B = {NULL,1,1}, matriz_Mult = {NULL,1,1}; ushort i,j,k; uchar flag = TRUE; while(flag) { ler_matriz(&matriz_A);/*le valores para linha e coluna e aloca memoria para a matriz*/ ler_matriz(&matriz_B);/*le valores para linha e coluna e aloca memoria para a matriz*/ if(matriz_A.col != matriz_B.row)/*verifica se a multiplicaccao e possivel*/ { printf("\nErro o numero de linhas de colunas de A tem que ser igual ao numero de linhas de B\n"); libera_matriz(matriz_A.address, &(matriz_A.row));/*libera a memoria alocada anteriormente*/ libera_matriz(matriz_B.address, &(matriz_B.row));/*libera a memoria alocada anteriormente*/ } else flag = FALSE; } preenche_matriz(&matriz_A);/*preenche as entradas da matriz com valores via teclado*/ preenche_matriz(&matriz_B);/*preenche as entradas da matriz com valores via teclado*/ matriz_Mult.row = matriz_A.row; matriz_Mult.col = matriz_B.col; matriz_Mult.address = aloca_matriz(&(matriz_Mult.row),&(matriz_Mult.col));/*aloca memoria para a matriz_Mult*/ inicializa_matriz(&matriz_Mult); for(i = 0; i < matriz_Mult.row; i++) for(j = 0; j < matriz_Mult.col; j++) for(k = 0; k < matriz_A.col; k++)/*k < matriz_B->row tambem esta correto*/ *(*(matriz_Mult.address + i) + j) += (*(*(matriz_A.address + i) + k)) * (*(*(matriz_B.address + k) + j)); imprime_matriz(&matriz_A); imprime_matriz(&matriz_B); imprime_matriz(&matriz_Mult); libera_matriz(matriz_A.address,&(matriz_A.row)); libera_matriz(matriz_B.address,&(matriz_B.row)); libera_matriz(matriz_Mult.address,&(matriz_Mult.row)); }
int main(void) { menu(); inicializa_matriz(); imprime_matriz(); printf("\n"); return 0; }
int main() { char command; int pais, partido, n_votos; inicializa_matriz(matriz_v, NRPAISES); while ((command = getchar()) != 'x') { switch (command) { case '+': /* Chama a funcao responsavel pela execucao do comando + */ scanf("%d%d%d",&pais,&partido,&n_votos); adiciona_votos(pais, partido, n_votos); break; case 'm': /* Chama a funcao responsavel pela execucao do comando m */ scanf("%d",&pais); inicializa_matriz(matriz_f, NRPAISES+1); full_dhondt(); imprime_especifico(pais); break; case 'e': /* Chama a funcao responsavel pela execucao do comando e */ inicializa_matriz(matriz_f, NRPAISES+1); full_dhondt(); imprime_matriz_f(); break; default: printf("ERRO: Comando desconhecido\n"); } getchar(); } return 0; }
main() { int nprocs = 4; //tempo struct timeval iniciotmp, finaltmp; int tempogasto; int pidf,id_wait; void dt_shareG(); mc_var_inic (); def_task (0, "inicializa_matriz", sizeof (__inicializa_matriz__)); def_task (1, "multiplica_matriz", sizeof (__multiplica_matriz__)); id_wait=sem_wait_inic(2); alloc_proc(nprocs); pidf = exec_task (0, nprocs); /* --- rs30() - create --- */ if (pidf == 0) { inicializa_matriz(); end_task(); /* --- rs31() - create --- */ } wait_all(); gettimeofday(&iniciotmp, NULL); pidf = exec_task (1, nprocs); /* --- rs30() - create --- */ if (pidf == 0) { multiplica_matriz(); end_task(); /* --- rs31() - create --- */ } wait_all(); gettimeofday(&finaltmp, NULL); tempogasto = (int) (1000 * (finaltmp.tv_sec - iniciotmp.tv_sec) + (finaltmp.tv_usec - iniciotmp.tv_usec) / 1000); printf("Tempo decorrido: %d\n", tempogasto); wait_all(); /* --- rs307() */ end_program(); remove_semaforo(id_wait); return 0; }
int main(int argc, char *argv[]){ srand (time(NULL)); int myrank, size; int i, j, z, x, y, k; int f = 200, c = f; int completados = 0; int res; int *resRow; int *rowA; MPI_Status status; MPI_Request request; int suma; double startwtime, endwtime; int filasEnviadas = 0, filasRecibidas = 0; int receptor = 0; MPI_Init(&argc, &argv); MPI_Comm_size(MPI_COMM_WORLD, &size); MPI_Comm_rank(MPI_COMM_WORLD, &myrank); int **matrizA = get_matriz(f,c);//reserva, pero no inicializa int **matrizB = get_matriz(c,f);//reserva, pero no inicializa int **matrizC = get_matriz(f,f);//reserva, pero no inicializa rowA = malloc((1+((f*c)/size)) * sizeof(int));//mandamos resRow = malloc((1+((f*c)/size)) * sizeof(int));//recibimos if (myrank== 0){ //inicializamos inicializa_matriz(matrizA, f, c); inicializa_matriz(matrizB, c, f); if(c <= 8 && f <= 8) { print_matriz(matrizA, f, c); print_matriz(matrizB, c, f); } if((f % size) != 0 ){ printf("Necesita tener un numero par (correcto) de procesos\n"); return 0; } while(filasEnviadas < f-(f/size)){//el proceso coordinador va enviar un trozo de la matriz a cada uno(excepto a el mismo) for(i = 0; i < (f/size); i++){ for(j = 0; j < c; j++){ rowA[i*f+j] = matrizA[(filasEnviadas+i)][j]; } } rowA[((f*c)/size)] = filasEnviadas;//apuntamos que fila estamos mandando(puede ser mas de una pero estan seguidas) receptor++; MPI_Send(&rowA[0], f*c/size+1, MPI_INT, receptor, 2, MPI_COMM_WORLD);//etiqueta 2 filasEnviadas += f/size; } for(i = 0; i < (f/size); i++){ for(j = 0; j < c; j++){ rowA[i*f+j] = matrizA[(filasEnviadas+i)][j]; } } rowA[((f*c)/size)] = filasEnviadas;//apuntamos que fila estamos mandando(puede ser mas de una pero estan seguidas) } else{//el coordinador no recibe nada MPI_Recv(&rowA[0], c*f/size+1, MPI_INT, 0, 2, MPI_COMM_WORLD, &status); } res = MPI_Bcast(&matrizB[0][0], c*f, MPI_INT, 0, MPI_COMM_WORLD); startwtime = MPI_Wtime(); //Procesamiento for (k = 0; k < f/size; k++){ for(i = 0; i < c; i++){//numero de columnas de B suma = 0; for(j = 0; j < f; j++){ suma += (rowA[k*f + j] * matrizB[j][i]); } resRow[k*f +i] = suma; } } resRow[((f*c)/size)] = rowA[((f*c)/size)]; endwtime = MPI_Wtime(); if(myrank != 0){//solo los trabajadores mandan MPI_Send(&resRow[0], c*f/size+1, MPI_INT, 0, 1, MPI_COMM_WORLD);//send } else{//cordinador recibe y los coloca en matrizC int fila = rowA[c*f/size];//la fila que vamos a tratar de la matriz A for(i = 0; i < (f/size); i++){ for(j = 0; j < c; j++){ matrizC[fila+i][j] = resRow[i*f+j]; } } while(filasRecibidas < (f-(f/size))){ MPI_Recv(&resRow[0], c*f/size+1, MPI_INT, MPI_ANY_SOURCE, 1, MPI_COMM_WORLD, &status); int fila = resRow[c*f/size];//la fila que vamos a tratar de la matriz A for(i = 0; i < (f/size); i++){ for(j = 0; j < c; j++){ matrizC[fila+i][j] = resRow[i*f+j]; } } filasRecibidas += f/size; } } if(myrank == 0) { if(c <= 8 && f <= 8) print_matriz(matrizC,f,f); printf("Tiempo de ejecucion: %f, usando %d+1 maquinas\n", endwtime - startwtime, size - 1); } if (matrizA!=NULL) free(matrizA); if (matrizB!=NULL) free(matrizB); if (matrizC!=NULL) free(matrizC); if (resRow!=NULL) free(resRow); if (rowA!=NULL) free(rowA); MPI_Finalize(); return 0; }
int main(int argc, char *argv[]){ srand (time(NULL)); int myrank, size; int i, j, z, x, y, k; int f = 16, c = 16; int completados = 0; int res; int *resRow; int *rowA; MPI_Status stats; MPI_Request request; int suma; double startwtime, endwtime; int filasEnviadas = 0, filasRecibidas = 0; int receptor; MPI_Init(&argc, &argv); MPI_Comm_size(MPI_COMM_WORLD, &size); MPI_Comm_rank(MPI_COMM_WORLD, &myrank); int restantes = (f*c)%size;//elementos restantes int *cantidadMandados;//array de elementos enviados a cada trabajador int *desplazamiento;//desplazamiento entre los envios (total datos / size) int sum = 0; int **matrizA = get_matriz(f,c);//reserva, pero no inicializa int **matrizB = get_matriz(c,f);//reserva, pero no inicializa int **matrizC = get_matriz(f,f);//reserva, pero no inicializa cantidadMandados = malloc(sizeof(int)*size); desplazamiento = malloc(sizeof(int)*size); if (myrank== 0){ //inicializamos inicializa_matriz(matrizA,f,c); inicializa_matriz(matrizB,c,f); if(c <= 8 && f <= 8) { print_matriz(matrizA, f, c); print_matriz(matrizB, c, f); } } for (i = 0; i < size; i++) { cantidadMandados[i] = (f*c - sum)/(size - i); if((cantidadMandados[i] % f) != 0){//es decir no tiene la ultima fila completa cantidadMandados[i] += (f - (cantidadMandados[i] % f)); } desplazamiento[i] = sum; sum += cantidadMandados[i]; } rowA = malloc(cantidadMandados[myrank] * sizeof(int)); resRow = malloc(cantidadMandados[myrank] * sizeof(int)); /*if (0 == myrank) { for (i = 0; i < size; i++) { printf("cantidadMandados[%d] = %d\tdesplazamiento[%d] = %d\n", i, cantidadMandados[i], i, desplazamiento[i]); } }*/ res = MPI_Bcast(&matrizB[0][0], c*f, MPI_INT, 0, MPI_COMM_WORLD); MPI_Scatterv(&matrizA[0][0], cantidadMandados, desplazamiento, MPI_INT, &rowA[0], cantidadMandados[myrank], MPI_INT, 0, MPI_COMM_WORLD); if(myrank == 0) startwtime = MPI_Wtime(); //Procesamiento for (k = 0; k < cantidadMandados[myrank]/f; k++){ for(i = 0; i < c; i++){//numero de columnas de B suma = 0; for(j = 0; j < f; j++){ suma += (rowA[k*f + j] * matrizB[j][i]); } resRow[k*f +i] = suma; } } if(myrank == 0) endwtime = MPI_Wtime(); MPI_Gatherv(&resRow[0], cantidadMandados[myrank], MPI_INT, &matrizC[0][0], cantidadMandados, &desplazamiento[myrank], MPI_INT, 0, MPI_COMM_WORLD);//5º parametro es int *recvcount MPI_Finalize(); if(myrank == 0) { if(c <= 8 && f <= 8) print_matriz(matrizC,f,f); printf("Tiempo de ejecucion: %f, usando %d+1 maquinas\n", endwtime - startwtime, size - 1); } if (matrizA!=NULL) free(matrizA); if (matrizB!=NULL) free(matrizB); if (matrizC!=NULL) free(matrizC); if (resRow!=NULL) free(resRow); if (rowA!=NULL) free(rowA); return 0; }
void multigrid(malla * u, malla *f, matriz *op, double * max) { int i,j; if(u->nivel==1) { /* Escalar el operador al nivel */ matriz op_n; /* Inicializamos el operador */ inicializa_matriz(&op_n,3); copia_matriz(op,&op_n); escala_matriz(&op_n,pow((u->dimension-1),2)); /* Construimos el sistema a resolver */ double A[3][3]; A[0][0]=op_n.v[1][1]; A[0][1]=op_n.v[2][1]; A[0][2]=op_n.v[2][2]; A[1][0]=op_n.v[0][1]; A[1][1]=op_n.v[1][1]; A[1][2]=op_n.v[1][2]; A[2][0]=op_n.v[0][0]; A[2][1]=op_n.v[1][0]; A[2][2]=op_n.v[1][1]; double B[3]; B[0] = f->v[2][1]-op_n.v[1][2]*u->v[2][2] -op_n.v[0][1]*u->v[1][1] -op_n.v[0][0]*u->v[1][0] -op_n.v[1][0]*u->v[2][0]; B[1] = f->v[3][1]-op_n.v[0][0]*u->v[2][0] -op_n.v[1][0]*u->v[3][0] -op_n.v[2][1]*u->v[4][1]; B[2] = f->v[3][2]-op_n.v[0][1]*u->v[2][2] -op_n.v[1][2]*u->v[3][3] -op_n.v[2][2]*u->v[4][3] -op_n.v[2][1]*u->v[4][2]; /* Hacemos eliminación gausiana */ A[1][1]=A[1][1]-A[0][1]*A[1][0]/A[0][0]; A[1][2]=A[1][2]-A[0][2]*A[1][0]/A[0][0]; B[1]=B[1]-B[0]*A[1][0]/A[0][0]; A[2][1]=A[2][1]-A[0][1]*A[2][0]/A[0][0]; A[2][2]=A[2][2]-A[0][2]*A[2][0]/A[0][0]; B[2]=B[2]-B[0]*A[2][0]/A[0][0]; A[2][2]=A[2][2]-A[1][2]*A[2][1]/A[1][1]; B[2]=B[2]-B[1]*A[2][1]/A[1][1]; /* Resolvemos */ u->v[3][2]=B[2]/A[2][2]; u->v[3][1]=(B[1]-A[1][2]*u->v[3][2])/A[1][1]; u->v[2][1]=(B[0]-A[0][2]*u->v[3][2]-A[0][1]*u->v[3][1])/A[0][0]; } else { /* Escalar el operador al nivel */ matriz op_n; /* Definicion de las mallas */ malla d; /* Para almacenar el defecto */ malla d_; /* Para almacenar el defecto restringido */ malla v; malla v_; /* Inicializacióm mallas*/ inicializa_malla_c(&d,u->nivel); inicializa_malla_c(&d_,u->nivel-1); inicializa_malla_c(&v,u->nivel); inicializa_malla_c(&v_,u->nivel-1); inicializa_matriz(&op_n,3); copia_matriz(op,&op_n); printf("sf=pow(%d,2)",u->dimension-1); escala_matriz(&op_n,pow((u->dimension-1),2)); /* Suavizado */ muestra_malla(u); printf("After smooth %f\n ",op_n.v[1][1]); suaviza_r(u,f,&op_n); suaviza_g(u,f,&op_n); suaviza_b(u,f,&op_n); muestra_malla(u); /* Defecto */ defecto(u,f,&d,&op_n); printf("After defect %f\n ",op_n.v[1][1]); muestra_malla(&d); /* Restringimos */ restringe(&d,&d_); /* Rellamada a multigrid */ multigrid(&v_,&d_,op,max); /* Interpolamos */ interpola(&v_,&v); /* Sumamos */ suma_mallas(u,&v); /* Postsuavizamos */ suaviza_r(u,f,&op_n); suaviza_g(u,f,&op_n); suaviza_b(u,f,&op_n); /* En la malla mas alta, comprobamos cómo va la cosa */ if(u->nivel==2) { /* Calculamos el defecto */ defecto(u,f,&d,&op_n); for(i=0;i<u->dimension;i++) { for(j=0;j<i;j++) { if(fabs(d.v[i][j])>max[0]) { max[0]=fabs(d.v[i][j]); } } } } /* Liberacion de recursos */ libera_matriz(&op_n); libera_malla(&d); libera_malla(&d_); libera_malla(&v); libera_malla(&v_); } }
int bt(int ** tablero, int dimension, int filini, int colini, int * peso_solucion, par * soa) { /* primero todas las variables que necesitamos!!!!!!!!!! * PXS * sandrita, se me va la cabeza :$ por ti! */ /* como la solucion final estara en soa, en vez de considerar * el parametro de la funcion como s, lo consideramos como soa */ par * s; int ** recorridos; par * paresmov; int voa; int peso; int nivel; int * mov; int i; /* procedemos a inicilizar todas las variables que hemos declarado */ /* memoria para s y soa */ s = (par *)malloc(MAXNIVEL*sizeof(par)); /* vamos a inicializar estas dos variables anterios, cada par tendra * el valor de (-1,-1) */ inicializa_pares(s, -1, dimension); inicializa_pares(soa, -1, dimension); /* y la de movimientos! que son inicializados a -1 */ mov = (int *)malloc(MAXNIVEL*sizeof(int)); for (i = 0; i < MAXNIVEL; i++) { mov[i] = -1; } /* creamos el array que tiene codificados los 4 movimientos */ paresmov = (par *)malloc(3*sizeof(par)); inicializa_paresmov(paresmov); /* tambien inicializamos recorridos */ recorridos = inicializa_matriz(dimension, 0); /* inicializacion de las variables! */ voa = 0xffff; recorridos[filini][colini] = 1; s[0].f = filini; s[0].c = colini; nivel = 0; /* peso almacena el peso del camino que vamos a formar */ peso = tablero[s[0].f][s[0].c]; /* el cuerpo de nuestro programa */ do { /*pinta_s(s, dimension);*/ if (solucion_bt(s, nivel, dimension)) { if (peso < voa) { voa = peso; /*printf("Nueva solucion optima\n"); pinta_s(s, dimension);*/ asigna_pares(s, soa); } } if (criterio(recorridos, s, peso, voa, nivel, dimension)) { nivel++; generar(tablero, mov, recorridos, s, nivel, &peso, paresmov); } else { while ((nivel != 0) && (!mashermanos(mov, nivel))) { retroceder(tablero, recorridos, mov, s, &nivel, &peso); } if (nivel != 0) { generar(tablero,mov,recorridos,s,nivel,&peso,paresmov); } } } while (nivel != 0); *peso_solucion = voa; return 0; }