#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define N 4 //行列式的维数
//声明一个计算矩逆矩阵的函数
unsigned char Calculate_InverseMatrix(double mB[N][N],double invB[N][N]);
int main(void)
{
double matrixA[N][N]; //N*N矩阵
double invA[N][N]; //逆矩阵
int k=0,n=0,m=0;
unsigned char IsMatrixInversible; //矩阵是否可逆
double muAA[N][N];
//矩阵初始化为全0
memset(matrixA,0,sizeof(matrixA));
memset(invA,0,sizeof(invA));
//逐行输入矩阵的值
for(k=0;k<N;k++)
{
printf("\n 请输入第 %d 行各个元素的值(%d个):\n",k+1,N);
for(n=0;n<N;n++)
scanf("%lf",&matrixA[k][n]);
}
IsMatrixInversible=Calculate_InverseMatrix(matrixA,invA);
if(IsMatrixInversible==0)
printf("\n 对不起,输入的矩阵不可逆!!!\n");
else
{
printf("\n 逆矩阵为:\n");
for(k=0;k<N;k++)
{
for(m=0;m<N;m++)
printf(" %12.6f\t ",invA[k][m]);
printf("\n");
}
//校验是不是逆矩阵,看两个矩阵的乘积
memset(muAA,0,sizeof(muAA));
for(k=0;k<N;k++)
{
for(n=0;n<N;n++)
{
muAA[k][n]=0;
for(m=0;m<N;m++)
muAA[k][n]+=matrixA[k][m]*invA[m][n];
}
}
//打印乘积矩阵,应该为单位矩阵
printf("\n 矩阵乘积为:\n");
for(k=0;k<N;k++)
{
for(m=0;m<N;m++)
printf(" %12.6f\t ",muAA[k][m]);
printf("\n");
}
}
return 0;
}
//计算矩阵的逆矩阵,返回值表示矩阵是否可逆
unsigned char Calculate_InverseMatrix(double mB[N][N],double invB[N][N])
{
int k=0,m=0,n=0; //定义行列式的三个索引
double tempForExchange=0; //临时变量,交换数据使用
double extB[N][2*N]; //扩展矩阵
unsigned char IsMatrixInversible=1; //默认矩阵可逆
//填充扩展矩阵
memset(extB,0,sizeof(extB));
for(k=0;k<N;k++)
{
for(n=0;n<N;n++)
extB[k][n]=mB[k][n];
extB[k][k+N]=1.0;
}
//对扩展矩阵进行行变换
for(k=0;k<N;k++)
{
//首先判断extB[k][k]是不是等于0
if(extB[k][k]==0)
{
//如果为0,找出第k列不为0的行
for(m=k+1;m<N;m++)
{
//如果找到,交换两行
if(extB[m][k]!=0)
{
for(n=k;n<2*N;n++)
{
tempForExchange=extB[k][n];
extB[k][n]=extB[m][n];
extB[m][n]=tempForExchange;
}
//已经找到,不再找了,跳出循环
break;
}
}
//如果该元素仍然还是0,说明没找到,矩阵不可逆
if(extB[k][k]==0)
{
IsMatrixInversible=0;
return 0;
}
}
//extB[k][k]不为零,则把第K行进行归一化,该行的每一个元素都除以extB[k][k];
tempForExchange=extB[k][k];
for(n=k;n<2*N;n++)
extB[k][n]/=tempForExchange;
//上面的各行进行行变换
for(m=0;m<k;m++)
{
//如果第m行第k列的元素已经是0,不需要进行变换了
if(extB[m][k]==0)
continue;
//否则进行行变换
tempForExchange=extB[m][k];
for(n=k;n<2*N;n++)
extB[m][n]-=tempForExchange*extB[k][n];
}
//下面的各行进行行变换
for(m=k+1;m<N;m++)
{
//如果第m行第k列的元素已经是0,不需要进行变换了
if(extB[m][k]==0)
continue;
//否则进行行变换
tempForExchange=extB[m][k];
for(n=k;n<2*N;n++)
extB[m][n]-=tempForExchange*extB[k][n];
}
}
//已经完成求解,扩展矩阵的右半部分即为逆矩阵
for(k=0;k<N;k++)
{
for(n=0;n<N;n++)
invB[k][n]=extB[k][N+n];
}
return IsMatrixInversible;
}