一、线性方程组
【线性方程组】
线性方程组是由n个m元一次方程共同构成。比如n = 3,m = 3时,有线性方程组:
如果把系数拿出来,就构成系数矩阵:

将系数和常数项拿出来,就构成增广矩阵:

二、高斯消元法
【高斯消元法】
高斯消元法是求解线性方程组的经典方法。除了用于线性方程组的求解之外,还可以用于行列式的计算、求矩阵的逆以及其他计算机工程方面。
高斯发现,在求解线性方程组时,当未知数排列整齐后,求解的过程只与系数和常数项有关。因此,只需要对增广矩阵执行相应操作即可。
其中,对增广矩阵执行下述三类操作,不会影响方程组的解:
1、交换两行;
2、某一行所有元素乘以一个数k,其中k不等于0;
3、将某一行所有元素的k倍加到另一行对应元素上。
这三种操作被称为矩阵的初等行变换。
【代码实现】

cpp
const int N = 110;
const double eps = 1e-7;
int n;
double a[N][N];
inline bool zero(double x)
{
return fabs(x) < eps;
}
int gauss()
{
for(int i = 1; i <= n; i++)
{
int aim = i;
// 找出第i列中,未确定主元的行中的最大行
for(int j = 1; j <= n; j++)
{
// 判断是否确定主元
if(j < i && !zero(a[j][j]))
continue;
if(fabs(a[j][i]) > fabs(a[aim][i]))
aim = j;
}
if(zero(a[aim][i]))
continue;
// 交换aim行和i行
for(int j = 1; j <= n + 1; j++)
swap(a[aim][j], a[i][j]);
// a[i][i] 置为1
for(int j = n + 1; j >= i; j--)
a[i][j] /= a[i][i];
// 第i列除了第i行,全部消为0
for(int j = 1; j <= n; j++)
{
if(j == i)
continue;
double t = a[j][i] / a[i][i];
for(int k = i; k <= n + 1; k++)
{
a[j][k] -= a[i][k] * t;
}
}
}
// 判断解
int ret = 1; // 唯一解
for(int i = 1; i <= n; i++)
{
if(zero(a[i][i]) && !zero(a[i][n + 1]))
{
ret = 0; // 无解
break;
}
if(zero(a[i][i]))
ret = 2; // 无数解
}
return ret;
}
三、矩阵求逆


cpp
#define _CRT_SECURE_NO_WARNINGS 1
#include <iostream>
#include <algorithm>
using namespace std;
const int N = 410, mod = 1e9 + 7;
const double eps = 1e-7;
typedef long long LL;
int n;
LL a[N][N + N];
LL qpow(LL a, LL b, LL p)
{
LL ret = 1;
while (b)
{
if (b & 1)
ret = ret * a % p;
b >>= 1;
a = a * a % p;
}
return ret;
}
int gauss()
{
for (int i = 1;i <= n;i++)
{
int aim = i;
for (int j = 1;j <= n;j++)
{
if (j < i && a[j][j] != 0)
continue;
if (a[j][i] > a[aim][i])
aim = j;
}
if (a[aim][i] == 0)
return 0;
for (int j = 1;j <= n + n;j++)
swap(a[aim][j], a[i][j]);
LL t = qpow(a[i][i], mod - 2, mod);
for (int j = n + n;j >= i;j--)
a[i][j] = a[i][j] * t % mod;
for (int j = 1;j <= n;j++)
{
if (i == j)
continue;
t = a[j][i];
for (int k = i;k <= n + n;k++)
{
a[j][k] -= a[i][k] * t;
a[j][k] = (a[j][k] % mod + mod) % mod;
}
}
}
return 1;
}
int main()
{
cin >> n;
for (int i = 1;i <= n;i++)
{
for (int j = 1;j <= n;j++)
{
cin >> a[i][j];
}
}
for (int i = 1;i <= n;i++)
a[i][i + n] = 1;
int ret = gauss();
if (ret == 0)
cout << "No Solution" << endl;
else
{
for (int i = 1;i <= n;i++)
{
for (int j = n + 1;j <= n + n;j++)
{
cout << a[i][j] << " ";
}
cout << endl;
}
}
return 0;
}