题目大意
求解线性方程组,比如:
的解。
解题思路
使用高斯消元法,步骤模拟如下。
(1) 合二为一: 将系数矩阵与结果向量合并得到:
(2) 以如下策略消元, (假设有个变元):
- 当消去第个元时,选取大于等于行中第个变元系数绝对值最大的一行作为基准。如果最大绝对值为0,则无解或有无穷解.
- 将第行与基准行交换。
- 将第行归一化。
- 使用归一化后的第行按比例关系消去其他行的第个变元的系数。
- 加一,重复上述过程直到全部变元消去。
(3)模拟如下:
代码
#include<iostream>
#include<vector>
using namespace std;
typedef vector<double> vec;
typedef vector<vec> mat;
double abs(double x)
{
if(x < 0)
return -x;
return x;
}
vec gauss_jordan(const mat &A, const vec &b)
{
int n = A.size();
mat B(n, vec(n+1));
// (1) -----------合并-------------
for(int i=0; i<n; i++)
for(int j=0; j<n; j++)
B[i][j] = A[i][j];
for(int i=0; i<n; i++)
B[i][n] = b[i];
// --------------------------------
for(int i=0; i<n; i++)
{
int base_index = i;
// 前i行已经固定,因此从j>=i行中选
for(int j=i+1; j<n; j++)
if(abs(B[j][i]) > abs(B[base_index][i]))
base_index = j;
// 无解或无穷解
if(abs(B[base_index][i]) < 10e-4) return vec();
swap(B[i], B[base_index]);
// -----------规范化-------------
int tmp = B[i][i];
for(int j=i; j<n+1; j++)
B[i][j] /= tmp;
//----------------------------------
// 消去其他行
for(int j=0; j<n; j++)
{
if(j!=i)
{
int tmp = B[j][i];
for(int k=i; k<n+1; k++)
B[j][k] -= tmp * B[i][k];
}
}
}
vec x(n);
for(int i=0; i<n; i++)
x[i] = B[i][n];
return x;
}
int main()
{
mat A(3, vec(3));
vec b(3);
for(int i=0; i<3; i++)
for(int j=0; j<3; j++)
cin >> A[i][j];
for(int i=0; i<3; i++)
cin >> b[i];
vec x(3);
x = gauss_jordan(A, b);
for(int i=0; i<3; i++)
cout << x[i] << endl;
return 0;
}