高斯消元模板 要求输出解的情况(无穷解/无解)

1. 之前写的丑陋代码

#include <iostream>
#include <cstdio>
#include <cmath>
#include <algorithm>
using namespace std;
const double eps=1e-7;
const int maxn=1000;
int n;//n个变量 n个方程
double A[maxn][maxn];
int Gauss() {//高斯消元 返回值 无解-- -1 //多解 -- 0 唯一解 -- 1(此时解保存在A[i][n+1]中) int h,l,r;//h--行 l--列 for(h = 1,l = 1;h <= n && l <= n;++ h,++ l){//消系数矩阵(n*n) r = h;for(int i = h + 1;i <= n;++ i) if(fabs(A[i][l]) > fabs(A[r][l]) + eps) r=i;//找到当前列所有行中的最大值(做除法时减小误差)if(r != h) for(int i = h;i <= n + 1;++ i) swap(A[r][i],A[h][i]);if(fabs(A[h][l]) < eps) {--h;continue;}///当前列h行以下全为0(包括h行)for(int i = h + 1;i <= n;++ i){if(fabs(A[i][l]) < eps) continue;for(int j = n + 1;j >= l;-- j) A[i][j]-=A[i][l]/A[h][l]*A[h][j];//加减消元 }}for(int i = h;i <= n;++ i) if(A[i][l] > eps) return -1;//系数均为0但结果不为0 无解 if(h <= n) return 0;//消元后所得方程不足n个(否则h为n+1) 有多解 for(int i = n; i ;-- i){//有唯一解 此时为严格的上三角矩阵 代入消元 for(int j = i + 1;j <= n + 1;++ j)A[i][n+1]-=A[i][j]*A[j][n+1];A[i][n+1]/=A[i][i];}return 1;
}
int main() {scanf("%d",&n);for(int i = 1;i <= n;++ i)for(int j = 1;j <= n + 1;++ j)scanf("%lf",&A[i][j]);int ans = Gauss();if(ans<=0) printf("%d",ans);else for(int i = 1;i <= n;++i){printf("x%d=", i);if (fabs(A[i][n+1]) < eps) puts("0");else printf("%.2f\n", A[i][n+1]);}return 0;
}

2. 改进后(更短更好理解)还是很丑陋???

/*
高斯约当消元法
把矩阵直接消成对角矩阵
与普通的高斯消元(消成阶梯矩阵再回代)相比计算量略大
但因为省略回代过程 代码更好写
*/
#include <cstdio>
#include <algorithm>
#include <iostream>
#include <cstring>
#include <cmath>
using namespace std;
const int maxn=110;
int n,ans;
const double eps=1e-8;//控制精度
typedef double Matrix[maxn][maxn];//把二维数组重定义为矩阵
Matrix A;
int Guess(Matrix A,int n){
//传入增广矩阵和n的值 这里默认有n个未知数 n个方程 增广矩阵下标从1开始 有n行 n+1列
//若方程数有m个(m>=n) 可传入m 在此模板基础上微调
//返回值:-1--无实数解     0--有无穷多解    1--有唯一实数解 此时矩阵已被消成对角型 int r; bool flag = false;//flag 判无穷解 for(int i = 1; i <= n;++ i) {//i为枚举的行 也可以理解成当前要消第几个未知数r = i;for(int j = i + 1;j <= n;++ j) if(fabs(A[j][i]) > fabs(A[r][i])) r=j;//取包含该未知数的方程里系数绝对值最大的那个方程进行消元 可提高精度 if(fabs(A[r][i]) < eps) {//若最大系数绝对值为0 则包含该未知数的方程系数全是0//此时说明【可能】有无穷解 之后有可能会出现无解的情况 所以只能先标记再处理 而不能直接返回无穷解 //若题目不要求输出具体是无穷解还是无解 可以直接return flag = true; continue;}//放弃这一行 处理下一行(下一个未知数 if(r != i) swap(A[i],A[r]);//若系数绝对值最大的不是这一行 就交换这两行(swap直接交换两行的指针 不用for循环再交换) for(int k = 1;k <= n;++ k) if(k != i)//与除了第i行以外其他行进行消元 直接消成对角型 for(int j = n + 1;j >= 1;-- j)//逆序枚举列 可以避免用中间变量(double)记录需要乘的倍数造成的精度误差 A[k][j] -= A[k][i] / A[i][i] * A[i][j];}//以下为判断解的情况 若题目中明确方程一定有解 或者 不要求输出具体是无解还是无穷解 可省略下面几行 //需要先判断是否无解再判断是否为无穷解 for(int i = 1,j;i <= n;++ i){//枚举每一行 for(j = 0;!A[i][j] && j <= n;++ j);//用指针j指向第一个这一行第一个不为零的数 if(j == n + 1 && A[i][j]) return -1;//若指向第n+1列说明系数全为零但结果不为零 方程无解 }if(flag) return 0;//无穷解 return 1;//唯一解
}
int main()
{scanf("%d",&n);for(int i = 1;i <= n;++ i)for(int j = 1;j <= n + 1;++ j)scanf("%lf",&A[i][j]);ans = Guess(A,n);if(ans != 1) printf("%d",ans);elsefor (int i = 1; i <= n; ++i) {printf("x%d=", i);if (fabs(A[i][n+1]/A[i][i]) < eps) puts("0");//防止输出负零(double型) else printf("%.2f\n", A[i][n+1]/A[i][i]);//已消成对角矩阵 第i+1列除以第i列就是答案 }return 0;
}

转载于:https://www.cnblogs.com/yu-xing/p/10354275.html

洛谷P2455 [SDOI2006]线性方程组相关推荐

  1. 洛谷 P3389 【模板】高斯消元法 × 洛谷 P2455 [SDOI2006]线性方程组

    一.传送门 https://www.luogu.com.cn/problem/P3389 https://www.luogu.com.cn/problem/P2455 二.代码 日--两道题合起来搞了 ...

  2. P2455 [SDOI2006]线性方程组

    题目链接:点击这里 题目大意: 给定一个线性方程组,对其求解 题目分析: 高斯-约旦消元法 选择一个尚未被选过的未知数作为主元,选择一个包含这个主元的方程 通过加减消元,消掉其它方程中的这个未知数 重 ...

  3. 【luogu P2455 [SDOI2006]线性方程组】 题解

    题目链接:https://www.luogu.org/problemnew/show/P2455 无解:最后一列对应元素不为0,前面全是0. 无穷解:一行全是0. 嗯...在消元过程中不要直接拿矩阵元 ...

  4. 洛谷日报 2020年3月前索引

    2020 2019 2018 感觉洛谷日报全是干货!!!先记下来再说 2020 年洛谷日报索引 3 月 #260[dove]Church 编码(和 Lambda 演算) https://www.luo ...

  5. 洛谷日报索引(2020、2019、2018)

    历年洛谷日报索引 2020 2019 2018 感觉洛谷日报全是干货!!!先记下来再说 2020 年洛谷日报索引 3 月 #260[dove]Church 编码(和 Lambda 演算) https: ...

  6. 洛谷-题解 P2672 【推销员】

    独门思路!链表加优先队列! 这题一望,贪心是跑不掉了,但是我贪心并不好,所以想到了一个复杂一些但思路更保稳的做法 思路: 1 因为是离线操作,所以我们可以倒着求,先求x=n的情况,因为那样直接就知道了 ...

  7. 洛谷 P1142 轰炸

    洛谷 P1142 轰炸 题目描述 "我该怎么办?"飞行员klux向你求助. 事实上,klux面对的是一个很简单的问题,但是他实在太菜了. klux要想轰炸某个区域内的一些地方,它们 ...

  8. 洛谷 P1387 最大正方形

    P1387 最大正方形 题目描述 在一个n*m的只包含0和1的矩阵里找出一个不包含0的最大正方形,输出边长. 输入输出格式 输入格式: 输入文件第一行为两个整数n,m(1<=n,m<=10 ...

  9. 洛谷P2763 试题库问题

    题目:https://www.luogu.org/problemnew/show/P2763 题目描述 «问题描述: 假设一个试题库中有n道试题.每道试题都标明了所属类别.同一道题可能有多个类别属性. ...

最新文章

  1. 数据挖掘Apriori算法
  2. 强化学习笔记: backup diagram
  3. 基于CNN的阅读理解式问答模型:DGCNN
  4. CSDN-markdown编辑器(保存自CSDN官方)
  5. 编译AjaxControlToolkit发生错误如何解决?
  6. spring mvc学习(20):RequestHeader(获取请求头中某一部分值)
  7. 为什么defineProperty不能检测到数组长度的“变化”
  8. CentOS7忘记root密码的解决方法
  9. 【Pycharm】连接远程服务器并进行代码上传、调试
  10. linux内核升级到3.4
  11. 巴塞罗那IoT“首秀”归来,新华三成功展现物联网风采
  12. 堆排序-java实现
  13. Python数据处理之导入导出excel数据
  14. 整理了一些常用的软件测试工具【建议收藏】
  15. No Route to Host from master/192.168.2.131 to master:9000 failed on socket t
  16. 无线测温系统应用 对变电所进行实时的在线监测 生产高效安全
  17. 如何配置luogu,codeforces的spj(special judge)
  18. YOLO系列目标检测算法详解
  19. 学习ES6 The Dope Way Part I:const,let&var
  20. signature=da0cbfb45ebebe4ea0118c0a20df185e,MS15-018:Internet Explorer 累积安全更新:2015 年 3 月 10 日...

热门文章

  1. TerraBuilder 操作制作MPT
  2. 强化学习之Q学习与SARSA
  3. [PAT乙级]1025 反转链表 (思路+精简代码)
  4. Eclipse打开报错,The Eclipse executable launcher was unable to locate its companion shared library.
  5. ElasticSearch之Head插件集群健康问题
  6. 百度云同步盘网络异常【1】解决办法
  7. java 内存读写文件_Java的文件读写操作
  8. Linux Ubuntu20.04安装及环境配置细节分享
  9. 深入理解CSS margin折叠
  10. ldpc译码讲解_LDPC码编译码原理及应用