/*
CALCULADOR de DETERMINANTES de orden n
Autor: Antonio López Vivar
Fecha: 1 de diciembre de 2003
Revisión: final 1.0
*/
#include <stdio.h>
#include <stdlib.h>
#include <math.h>
#include <conio.h>
//Prototipos
float Determinante (float **, int);
void Adjunta (float **, float **, int, int);
//Principal
void main()
{
int n, i, f, c;
float **matriz;
char comando;
for(i=0; i<3; i++)
{
printf("\n\n\tBienvenido al CaLcuLaDOR de DeTERminanTes de orden n marca MIKASA");
sleep(500);
system("cls");
printf("\n\n\tBienvenido al CaLcuLaDOR de DeTERminanTes de orden n marca MIKASA");
printf("\n\n\n\n\n\n\n\t\t\tUna utilidad de Antonio Lopez Vivar");
sleep(500);
system("cls");
}
do{
do{
system("cls");
printf("\n\n\tNota--> Este programa utiliza una funcion recursiva. Abstenerse de introducir matrices de orden elevado (mayor de 10), puesto que el consumo de RAM puede ser bestial");
printf("\n\n\tORDEN?>\t");
scanf("%d", &n);
}while(n<1);
//Petición de memoria dinámica para la matriz
matriz=(float**)calloc(n, sizeof(float*));
if(matriz==NULL)
printf("ERROR, FALTA MEMORIA PARA LA MATRIZ. Introduzca un orden MUCHO mas pequeño");
else
{
for(i=0; i<n; i++)
matriz[i]=(float*)calloc(n, sizeof(float));
//Lectura por teclado de la matriz
for(f=0; f<n; f++)
for(c=0; c<n; c++)
{printf("\nIntroduce el elemento %d de la fila %d --->\t", c+1, f+1);
scanf("%f", &matriz[f][c]);
}
//Se muestra la matriz al usuario
system("cls");
printf("\n\n\n");
for(f=0; f<n; f++)
{
printf("\t\t");
for(c=0; c<n; c++)
printf("%12.1f ", matriz[f][c]);
printf("\n");
}
printf("\n\n\n\t\tCalculando el determinante, por favor espere...\n\t\t(Para abortar el calculo pulse CTRL+C)\n");
printf("\n\n\n\n\n\t\t\tEl determinante es:");
printf("\n\n\n\t\t\t\t%.1f\n\n\n\n\n\t\t", Determinante(matriz, n));
//Se libera la memoria solicitada
free(matriz);
}
printf("Pulsa INTRO para calcular OTRO determinante, o pulsa S para SALIR");
fflush(stdin);
comando=getch();
}while(comando!='s' && comando!='S');
}
/*
Esta función recursiva se encarga del cálculo del determinante propiamente dicho.
Recibe:
- La matriz (referencia).
- Orden de la matriz (valor).
Devuelve:
- El determinante (valor).
*/
float Determinante (float **mat, int orden)
{
float det;
int h;
float **auxiliar;
//Caso básico
if(orden<=2)
{
if(orden==2)
det=mat[0][0]*mat[1][1]-(mat[1][0]*mat[0][1]);
else
det=mat[0][0];
}
//Se calculan n determinantes de orden "n-1".
else
{
//Petición de memoria dinámica para la matriz auxiliar
auxiliar=(float**)calloc(orden-1, sizeof(float*));
for(h=0; h<orden-1; h++)
auxiliar[h]=(float*)calloc(orden-1, sizeof(float));
//Se usa un acumulador para ir sumando los determinantes de orden n-1
det=0;
for(h=0; h<orden; h++)
{ Adjunta(mat, auxiliar, orden, h);
det+=pow(-1, h)*mat[h][0]*Determinante(auxiliar, orden-1);
}
//Se libera la memoria auxiliar solicitada
free(auxiliar);
}
return(det);
}
/*
Esta función se encarga de calcular la matriz resultante de tachar la primera columna y alguna de las n filas de la matriz inicial.
Recibe:
- La matriz inicial (referencia).
- El orden de la matriz inicial(valor).
- La fila que hay que tachar de la matriz inicial (valor).
Devuelve:
- La matriz auxiliar que se usará para calcular los determinates de orden n-1 (referencia).
*/
void Adjunta (float **mat, float **aux, int orden, int pos)
{
int fila, columna, j, i;
for(j=0, fila=0; fila<orden-1; j++, fila++)
{
if(j==pos)
fila--;
else
for(i=1, columna=0; columna<orden-1; i++, columna++)
aux[fila][columna]=mat[j][i];
}
}
Nota: lo que en el código aparece como adjunta NO ES LA MATRIZ DE ADJUNTOS.