#include "lib_matriz.h" #include "elim_gauss.h" #include "string.h" #define PROMPT "> " /* Comandos */ #define AJUDA "ajuda" #define CRIA "cria" #define DESTROI "destroi" #define LER "ler" #define IMPRIME "imprime" #define SOMACONST "somaconst" #define MULTCONST "multconst" #define SOMA "soma" #define MULT "mult" #define PIVOTEIA "pivoteia" #define GAUSSELIM "gausselim" #define RESOLVE "resolve" #define HILBERT "hilbert" #define RANDOM "random" #define RESIDUO "residuo" #define SAIR "sair" #define CHI "\033[0;1m" #define CLO "\033[0m" #define GREETINGS "Projeto de MS211\nGrupo:\n\tGustavo Sverzut Barbieri\tRA: 008849\n\tIvens Prates Telles Alves\tRA: 008908\n\tDanilo ???????????\tRA:00????\n\nDigite " CHI AJUDA CLO " para obter ajuda\n\n" typedef struct matarr { Matriz *m; struct matarr *prev; struct matarr *next; } MatArr; void Ajuda(void); void Cria(MatArr **m); void Imprime(MatArr **m); void Ler(MatArr **m); void SomaConst(MatArr **m); void MultConst(MatArr **m); void Soma(MatArr **m); void Multiplica(MatArr **m); void Destroi(MatArr **m); void Hilbert(MatArr **m); void Random(MatArr **m); void Pivoteia(MatArr **m); void Eliminacao(MatArr **m); void Resolve(MatArr **m); void ResiduoSis(MatArr **m); MatArr *matarrCria(); void matarrDestroi(MatArr **m); void matarrInsere(MatArr ***m, int nl, int nc, char nome[]); void matarrPosiciona(MatArr ***m, char nome[]); void (*ImprimeMatriz)(); int main(void) { MatArr *matriz; char opcao[255]; matriz = matarrCria(); fprintf(stderr,GREETINGS); fprintf(stderr,"Tipo de terminal(ascii/latex): "); scanf("%s",opcao); if (strcmp(opcao,"latex")==0) ImprimeMatriz = matImprimeLatex; else ImprimeMatriz = matImprime; strcpy(opcao,""); while (strcmp(opcao,SAIR) != 0) { if (strcmp(opcao,AJUDA) == 0) Ajuda(); else if (strcmp(opcao,CRIA) == 0) Cria(&matriz); else if (strcmp(opcao,IMPRIME) == 0) Imprime(&matriz); else if (strcmp(opcao,LER) == 0) Ler(&matriz); else if (strcmp(opcao,SOMACONST) == 0) SomaConst(&matriz); else if (strcmp(opcao,MULTCONST) == 0) MultConst(&matriz); else if (strcmp(opcao,SOMA) == 0) Soma(&matriz); else if (strcmp(opcao,MULT) == 0) Multiplica(&matriz); else if (strcmp(opcao,DESTROI) == 0) Destroi(&matriz); else if (strcmp(opcao,HILBERT) == 0) Hilbert(&matriz); else if (strcmp(opcao,RANDOM) == 0) Random(&matriz); else if (strcmp(opcao,PIVOTEIA) == 0) Pivoteia(&matriz); else if (strcmp(opcao,GAUSSELIM) == 0) Eliminacao(&matriz); else if (strcmp(opcao,RESOLVE) == 0) Resolve(&matriz); else if (strcmp(opcao,RESIDUO) == 0) ResiduoSis(&matriz); fprintf(stderr,PROMPT); scanf("%s",opcao); } matarrDestroi(&matriz); return 0; } void Ajuda(void) { fprintf(stderr,"AJUDA:\n" CHI CRIA " " CLO " - Cria matriz nula com linhas e colunas\n" CHI DESTROI " " CLO " - Destroi matriz \n" CHI LER " " CLO " - Lê a matriz da stdin\n" CHI IMPRIME " " CLO " - Imprime a matriz \n" CHI SOMA " " CLO " - Faz igual à soma as matrizes e \n" CHI MULT " " CLO " - Faz igual à multiplicação das matrizes e \n" CHI SOMACONST " " CLO " - Faz igual à soma da constante à matriz \n" CHI MULTCONST " " CLO " - Faz igual à multiplicação da matriz pelo constante \n" CHI SAIR CLO " - sai do programa\n" CHI HILBERT " " CLO " - cria matriz de Hilbert de dimensões x\n" CHI RANDOM " " CLO " - cria matriz de dimensões x com elementos aleatórios entre e \n" CHI PIVOTEIA " " CLO " - pivoteia as matrizes e simultaneamente, sendo NxN e Nx1\n" CHI GAUSSELIM " " CLO " - faz a Eliminação de Gauss em e simultaneamente, sendo NxN e Nx1\n" CHI RESOLVE " " CLO " - Cria a matriz que é a solução do Sistema *=, sendo e previamente submetidas à Eliminação de Gauss\n" CHI RESIDUO " " CLO " - retorna resíduo do sistema *=\n" "\nAtenção:\n\tOs nomes das matrizes devem ter, no máximo, 10 letras.\n"); } void Cria(MatArr **m) { int nl, nc; char nome[10]; MatArr *tmp; scanf("%s",nome); scanf("%i",&nl); scanf("%i",&nc); if (*m != NULL) { matarrPosiciona(&m,nome); if (strcmp((*m)->m->nome,nome)==0) { /* Matriz já existe */ if ( (*m)->prev == (*m)->next ) { free(*m); *m = NULL; } else { ((*m)->prev)->next = (*m)->next; ((*m)->next)->prev = (*m)->prev; tmp = *m; *m = tmp->next; free(tmp); tmp = NULL; } } } matarrInsere(&m,nl,nc,nome); ImprimeMatriz((*m)->m,"% .3lf "); } void Hilbert(MatArr **m) { int n; char nome[10]; MatArr *tmp; scanf("%s",nome); scanf("%i",&n); if (*m != NULL) { matarrPosiciona(&m,nome); if (strcmp((*m)->m->nome,nome)==0) { /* Matriz já existe */ if ( (*m)->prev == (*m)->next ) { free(*m); *m = NULL; } else { ((*m)->prev)->next = (*m)->next; ((*m)->next)->prev = (*m)->prev; tmp = *m; *m = tmp->next; free(tmp); tmp = NULL; } } } matarrInsere(&m,1,1,nome); free((*m)->m); (*m)->m = matHilbert(n,nome); ImprimeMatriz((*m)->m,"% .3lf "); } void Random(MatArr **m) { int nl, nc; double x0, x1; char nome[10]; MatArr *tmp; scanf("%s",nome); scanf("%i",&nl); scanf("%i",&nc); scanf("%lf",&x0); scanf("%lf",&x1); if (*m != NULL) { matarrPosiciona(&m,nome); if (strcmp((*m)->m->nome,nome)==0) { /* Matriz já existe */ if ( (*m)->prev == (*m)->next ) { free(*m); *m = NULL; } else { ((*m)->prev)->next = (*m)->next; ((*m)->next)->prev = (*m)->prev; tmp = *m; *m = tmp->next; free(tmp); tmp = NULL; } } } matarrInsere(&m,1,1,nome); free((*m)->m); (*m)->m = matRandom(nl,nc,nome,x0,x1); ImprimeMatriz((*m)->m,"% .3lf "); } void Destroi(MatArr **m) { char nome[10]; MatArr *tmp; scanf("%s",nome); if (*m != NULL) { matarrPosiciona(&m,nome); if (strcmp((*m)->m->nome,nome)==0) { /* Matriz já existe */ if ( (*m)->prev == (*m)->next ) { free(*m); *m = NULL; } else { ((*m)->prev)->next = (*m)->next; ((*m)->next)->prev = (*m)->prev; tmp = *m; *m = tmp->next; free(tmp); tmp = NULL; } } } } void Imprime(MatArr **m) { char nome[10]; scanf("%s",nome); if (*m != NULL) { matarrPosiciona(&m,nome); if (strcmp((*m)->m->nome,nome)==0) ImprimeMatriz((*m)->m,"% .3lf "); else fprintf(stderr,"Matriz '%s' não existe!\n",nome); } else fprintf(stderr,"Matriz '%s' não existe!\n",nome); } void Ler(MatArr **m) { char nome[10]; scanf("%s",nome); matarrPosiciona(&m,nome); if (*m != NULL) { if (strcmp((*m)->m->nome,nome)==0) { matLer((*m)->m); ImprimeMatriz((*m)->m,"% .3lf "); } else fprintf(stderr,"Matriz '%s' não existe!\n",nome); } } void SomaConst(MatArr **m) { char nome[10]; char nome2[10]; Matriz *soma; MatArr *tmp; double cons; scanf("%s",nome); scanf("%s",nome2); scanf("%lf",&cons); if (*m != NULL) { matarrPosiciona(&m,nome2); if (strcmp((*m)->m->nome,nome2)==0) { soma = matSomaEscalar((*m)->m,cons,nome); matarrPosiciona(&m,nome); if (strcmp((*m)->m->nome,nome)==0) { /* Matriz já existe */ if ( (*m)->prev == (*m) ) { free(*m); *m = NULL; } else { ((*m)->prev)->next = (*m)->next; ((*m)->next)->prev = (*m)->prev; tmp = *m; *m = tmp->next; free(tmp); tmp = NULL; } } matarrInsere(&m,0,0,nome); free((*m)->m); (*m)->m = soma; ImprimeMatriz((*m)->m,"% .3lf "); } else fprintf(stderr,"Matriz '%s' não existe!\n",nome2); } else fprintf(stderr,"Matriz '%s' não existe!\n",nome2); } void MultConst(MatArr **m) { char nome[10]; char nome2[10]; Matriz *mult; MatArr *tmp; double cons; scanf("%s",nome); scanf("%s",nome2); scanf("%lf",&cons); if (*m != NULL) { matarrPosiciona(&m,nome2); if (strcmp((*m)->m->nome,nome2)==0) { mult = matMultiplicaEscalar((*m)->m,cons,nome); matarrPosiciona(&m,nome); if (strcmp((*m)->m->nome,nome)==0) { /* Matriz já existe */ if ( (*m)->prev == (*m) ) { free(*m); *m = NULL; } else { ((*m)->prev)->next = (*m)->next; ((*m)->next)->prev = (*m)->prev; tmp = *m; *m = tmp->next; free(tmp); tmp = NULL; } } matarrInsere(&m,0,0,nome); free((*m)->m); (*m)->m = mult; ImprimeMatriz((*m)->m,"% .3lf "); } else fprintf(stderr,"Matriz '%s' não existe!\n",nome2); } else fprintf(stderr,"Matriz '%s' não existe!\n",nome2); } void Soma(MatArr **m) { char nome[10]; char nome2[10]; char nome3[10]; Matriz *soma; MatArr *tmp; scanf("%s",nome); scanf("%s",nome2); scanf("%s",nome3); if (*m != NULL) { matarrPosiciona(&m,nome2); if (strcmp((*m)->m->nome,nome2)==0) { tmp = (*m); matarrPosiciona(&m,nome3); if (strcmp((*m)->m->nome,nome3)==0) { soma = matSoma(tmp->m,(*m)->m,nome); matarrPosiciona(&m,nome); if (strcmp((*m)->m->nome,nome)==0) { /* Matriz já existe */ if ( (*m)->next == (*m) ) { free(*m); *m = NULL; } else { ((*m)->prev)->next = (*m)->next; ((*m)->next)->prev = (*m)->prev; tmp = *m; *m = tmp->next; free(tmp); tmp = NULL; } } if ( soma != NULL) { matarrInsere(&m,0,0,nome); free((*m)->m); (*m)->m = soma; ImprimeMatriz((*m)->m,"% .3lf "); } } else fprintf(stderr,"Matriz '%s' não existe!\n",nome3); } else fprintf(stderr,"Matriz '%s' não existe!\n",nome2); } else fprintf(stderr,"Matriz '%s' não existe!\n",nome2); } void Multiplica(MatArr **m) { char nome[10]; char nome2[10]; char nome3[10]; Matriz *mult; MatArr *tmp; scanf("%s",nome); scanf("%s",nome2); scanf("%s",nome3); if ( *m != NULL) { matarrPosiciona(&m,nome2); if (strcmp((*m)->m->nome,nome2)==0) { tmp = (*m); matarrPosiciona(&m,nome3); if (strcmp((*m)->m->nome,nome3)==0) { mult = matMultiplica(tmp->m,(*m)->m,nome); matarrPosiciona(&m,nome); if (strcmp((*m)->m->nome,nome)==0) { /* Matriz já existe */ if ( (*m)->next == (*m) ) { free(*m); *m = NULL; } else { ((*m)->prev)->next = (*m)->next; ((*m)->next)->prev = (*m)->prev; tmp = *m; *m = tmp->next; free(tmp); tmp = NULL; } } if (mult != NULL) { matarrInsere(&m,0,0,nome); free((*m)->m); (*m)->m = mult; ImprimeMatriz((*m)->m,"% .3lf "); } } else fprintf(stderr,"Matriz '%s' não existe!\n",nome3); } else fprintf(stderr,"Matriz '%s' não existe!\n",nome2); } else fprintf(stderr,"Matriz '%s' não existe!\n",nome2); } void Pivoteia(MatArr **m) { char nomeA[10]; char nomeB[10]; MatArr *tmp; scanf("%s",nomeA); scanf("%s",nomeB); if ( *m != NULL) { matarrPosiciona(&m,nomeA); if (strcmp((*m)->m->nome,nomeA)==0) { tmp = (*m); matarrPosiciona(&m,nomeB); if (strcmp((*m)->m->nome,nomeB)==0) { if ( ((*m)->m->nc == 1) && ((*m)->m->nl == tmp->m->nl) ) { PivoteamentoParcial(tmp->m,(*m)->m); ImprimeMatriz(tmp->m,"% .3lf "); ImprimeMatriz((*m)->m,"% .3lf "); } else fprintf(stderr,"Matrizes '%s' e '%s' incompatíveis para Pivoteamento!\n",nomeA,nomeB); } else fprintf(stderr,"Matriz '%s' não existe!\n",nomeB); } else fprintf(stderr,"Matriz '%s' não existe!\n",nomeA); } else fprintf(stderr,"Matriz '%s' não existe!\n",nomeA); } void Eliminacao(MatArr **m) { char nomeA[10]; char nomeB[10]; MatArr *tmp; scanf("%s",nomeA); scanf("%s",nomeB); if ( *m != NULL) { matarrPosiciona(&m,nomeA); if (strcmp((*m)->m->nome,nomeA)==0) { tmp = (*m); matarrPosiciona(&m,nomeB); if (strcmp((*m)->m->nome,nomeB)==0) { if ( ((*m)->m->nc == 1) && ((*m)->m->nl == tmp->m->nl) ) { EliminacaoGauss(tmp->m,(*m)->m); ImprimeMatriz(tmp->m,"% .3lf "); ImprimeMatriz((*m)->m,"% .3lf "); } else fprintf(stderr,"Matrizes '%s' e '%s' incompatíveis para Eliminacao!\n",nomeA,nomeB); } else fprintf(stderr,"Matriz '%s' não existe!\n",nomeB); } else fprintf(stderr,"Matriz '%s' não existe!\n",nomeA); } else fprintf(stderr,"Matriz '%s' não existe!\n",nomeA); } void Resolve(MatArr **m) { char nome[10]; char nomeA[10]; char nomeB[10]; Matriz *res; MatArr *tmp; scanf("%s",nome); scanf("%s",nomeA); scanf("%s",nomeB); if ( *m != NULL) { matarrPosiciona(&m,nomeA); if (strcmp((*m)->m->nome,nomeA)==0) { tmp = (*m); matarrPosiciona(&m,nomeB); if (strcmp((*m)->m->nome,nomeB)==0) { if ( ((*m)->m->nc == 1) && ((*m)->m->nl == tmp->m->nl) ) { res = ResolveSistemaTriangularSuperior(tmp->m,(*m)->m,nome); matarrPosiciona(&m,nome); if (strcmp((*m)->m->nome,nome)==0) { /* Matriz já existe */ if ( (*m)->prev == (*m)->next ) { free(*m); *m = NULL; } else { ((*m)->prev)->next = (*m)->next; ((*m)->next)->prev = (*m)->prev; tmp = *m; *m = tmp->next; free(tmp); tmp = NULL; } } if (res != NULL) { matarrInsere(&m,0,0,nome); free((*m)->m); (*m)->m = res; ImprimeMatriz((*m)->m,"% .3lf "); } } else fprintf(stderr,"Matrizes '%s' e '%s' incompatíveis para Resolução!\n",nomeA,nomeB); } else fprintf(stderr,"Matriz '%s' não existe!\n",nomeB); } else fprintf(stderr,"Matriz '%s' não existe!\n",nomeA); } else fprintf(stderr,"Matriz '%s' não existe!\n",nomeA); } void ResiduoSis(MatArr **m) { char nomeA[10]; char nomeX[10]; char nomeB[10]; MatArr *tmp1; MatArr *tmp2; scanf("%s",nomeA); scanf("%s",nomeX); scanf("%s",nomeB); if ( *m != NULL) { matarrPosiciona(&m,nomeA); if (strcmp((*m)->m->nome,nomeA)==0) { tmp1 = (*m); matarrPosiciona(&m,nomeX); if (strcmp((*m)->m->nome,nomeX)==0) { tmp2 = (*m); matarrPosiciona(&m,nomeB); if (strcmp((*m)->m->nome,nomeB)==0) { if ( ((*m)->m->nc == 1) && (tmp2->m->nc ==1) && ((*m)->m->nl == tmp1->m->nl) && (tmp2->m->nl == tmp1->m->nl) ) { printf("Resíduo: %.3e\n",Residuo(tmp1->m,tmp2->m,(*m)->m)); } else fprintf(stderr,"Matrizes '%s' e '%s' incompatíveis para Resíduo!\n",nomeA,nomeB); } else fprintf(stderr,"Matriz '%s' não existe!\n",nomeB); } else fprintf(stderr,"Matriz '%s' não existe!\n",nomeX); } else fprintf(stderr,"Matriz '%s' não existe!\n",nomeA); } else fprintf(stderr,"Matriz '%s' não existe!\n",nomeA); } /*---- Funcoes para Manipulaçao da Lista de Matrizes ------------------------------------------------------*/ MatArr *matarrCria() { return NULL; } void matarrDestroi(MatArr **m) { MatArr *tmp1, *tmp2; if (*m != NULL) { tmp1 = (*m)->next; while ( tmp1 != (*m) ) { tmp2 = tmp1; tmp1 = tmp1->next; free(tmp2); } free(*m); } } void matarrInsere(MatArr ***m,int nl, int nc, char nome[]) { MatArr *tmp = NULL; MatArr *aux; if ((tmp=(MatArr *) calloc(1,sizeof(MatArr))) == NULL) { fprintf(stderr,MSG0 "matarrInsereOk"); exit; } else { tmp->m = matCria(nl,nc,nome); if ( **m == NULL) { tmp->next = tmp; tmp->prev = tmp; } else { aux = (**m)->next; (**m)->next = tmp; tmp->next = aux; tmp->next->prev = tmp; tmp->prev = (**m); } **m = tmp; } } /* Posiciona o ponteiro m para o noh com a matriz 'nome' */ void matarrPosiciona(MatArr ***m, char nome[]) { MatArr *inicio; if (**m != NULL) { inicio = (**m)->prev; while ( (**m != inicio) && (strcmp((**m)->m->nome,nome)!=0) ) (**m)=(**m)->next; } }