题目链接:https://www.luogu.org/problem/P4783
题意:求矩阵的逆。
思路:高斯消元法求矩阵的逆,n为400,卡常,我是开了O2优化才AC的。。
AC代码:
#include<cstdio> #include<cctype> #include<algorithm> #define R register int using namespace std; const int maxn=405; const int MOD=1e9+7; int n; struct Matrix{ int m[maxn][maxn]; void SWAP(int x,int y){ //交换两行 for(R i=1;i<=n;++i) swap(m[x][i],m[y][i]); } void MUL(int x,int k){ //对一行乘上k for(R i=1;i<=n;++i) m[x][i]=(1LL*m[x][i]*k%MOD+MOD)%MOD; } void MULADD(int x,int y,int k){ //将第y行乘上k加到第x行上去 for(R i=1;i<=n;++i) m[x][i]=((m[x][i]+1LL*m[y][i]*k%MOD)%MOD+MOD)%MOD; } }A,B; int qpow(int a,int b){ //求逆元 int ret=1; while(b){ if(b&1) ret=1LL*ret*a%MOD; a=1LL*a*a%MOD; b>>=1; } return ret; } void Invmatrix(){ for(R i=1;i<=n;++i){ if(!A.m[i][i]){ for(R j=i+1;j<=n;++j) if(A.m[j][i]){ B.SWAP(i,j); A.SWAP(i,j); break; } } if(!A.m[i][i]){ //没有逆矩阵 puts("No Solution"); return; } int tmp=qpow(A.m[i][i],MOD-2); B.MUL(i,tmp); A.MUL(i,tmp); //系数化为1 for(R j=i+1;j<=n;++j){ //消元 tmp=-A.m[j][i]; B.MULADD(j,i,tmp); A.MULADD(j,i,tmp); } } for(R i=n-1;i>=1;--i) //回带 for(R j=i+1;j<=n;++j){ int tmp=-A.m[i][j]; B.MULADD(i,j,tmp); A.MULADD(i,j,tmp); } for(R i=1;i<=n;++i){ for(R j=1;j<=n;++j){ printf("%d",B.m[i][j]); if(j!=n) printf(" "); } printf(" "); } } int main(){ scanf("%d",&n); for(R i=1;i<=n;++i) for(R j=1;j<=n;++j) scanf("%d",&A.m[i][j]); for(R i=1;i<=n;++i){ for(R j=1;j<=n;++j) B.m[i][j]=0; B.m[i][i]=1; } Invmatrix(); return 0; }