线性代数-矩阵-【5】矩阵化简 C和C++实现
点击这里可以跳转至
【1】矩阵汇总:http://www.cnblogs.com/HongYi-Liang/p/7287369.html
【2】矩阵生成:http://www.cnblogs.com/HongYi-Liang/p/7275278.html
【3】矩阵加减:http://www.cnblogs.com/HongYi-Liang/p/7287403.html
【4】矩阵点乘:http://www.cnblogs.com/HongYi-Liang/p/7287324.html
【5】矩阵化简:现在的位置
(待续)
...
C++语言:
高斯消元法:
继续使用这个矩阵

当我们使用高斯消元(无回代)化简这个矩阵,是这样算的:

上述过程归纳为:
- 找到第一行行的主元(第一行第一个数:1)
- 消除第而三行的的第一个数(r2-2*r1;r3-4*r1)
- 找到第二行的主元(第二行第二个数:-2)
- 消除第三行的第二个数(r3-3/2*r2)
可以发现实际上是1和2两个步骤的循环,所以写成循环的形式
- 从第一行开始到最后一行
- 找主元:找出第i的主元(第i行第i个数)
- 消元:消除下面所有行的第i个数(下面每一行减去x倍的第一行来消除第i列)
到目前为止,基本达到消元的目的了,但是有一些小小的瑕疵
我们可能碰到一个这样矩阵,有一行全是0,例如这个:

那么我们在步骤1中搜索到主元为0的话,0的任意倍数都是0,会导致第2步无法进行。所以我们需要添加换行的操作,计算方法为:

所以我们把代码逻辑修改成这样:
- 从第一行开始到最后一行
- 找主元:找出第i的主元(第i行第i个数),若主元为0,把第i行向下换行,直到找到有主元的行。若找不到主元,就开始找下一个
- 消元:消除下面所有行的第i个数(下面每一行减去x倍的第一行来消除第i列)
下面就是高斯消元的主程序:
template <typename T>
bool Matrix<T>::GaussianElimination()
{
Matrix<T> outputMatrix = *this; /*Gaussian elmiation*/
for(int k=;k<outputMatrix.m_iRows;k++)
{
/*if all the pivot have been found*/
if(k>=m_iColumns)
{
break;
} /*exchange rows downward to find the row's pivot*/
for(int i=k+;i<outputMatrix.m_iRows;i++)
{
/*pivot is non-zero*/
if(outputMatrix.m_vecMatrix[k][k] != )
{
//T temp = outputMatrix.m_vecMatrix[0][0];
break;
}
else
{
if(i < outputMatrix.m_iRows)
{
outputMatrix.exchangeRows(k,i);
}
}
} /*if there is no pivot in this row*/
if(outputMatrix.m_vecMatrix[k][k] == )
{
break;
} /*elimination:The rows below pivot row subtract times of pivot row*/
for(int i=k+;i<outputMatrix.m_iRows;i++)
{
double RowsfirstData = outputMatrix.m_vecMatrix[i][k]/outputMatrix.m_vecMatrix[k][k];//Save the first data of next(k+1) rows
if(RowsfirstData != )
{
outputMatrix.m_vecMatrix[i][k]=;
for(int j=k+;j<outputMatrix.m_iColumns;j++)
{
outputMatrix.m_vecMatrix[i][j] -= RowsfirstData*outputMatrix.m_vecMatrix[k][j] ;
}
}
}
} *this = outputMatrix;
return true;
}
高斯-若尔当法
若尔当在高斯消元的基础上加上了回代过程,把矩阵化简成行最简式。我们在高斯消元的基础上加上和回代,方法跟高斯消元相反,用上面的行减下面的行,这里就不详细描述(展开查看代码)
rref()//化简矩阵成行最简
template <typename T>
bool Matrix<T>::rref()
{
Matrix<T> outputMatrix = *this;
int rank=;//the rank of the matrix, how many columns's pivot will it has(-1) /*Gaussian elmiation*/
for(int k=;k<outputMatrix.m_iRows;k++)
{
/*if all the pivot elem have been found*/
if(k>=m_iColumns)
{
break;
} /*exchange rows downward to find the pivot row*/
for(int i=k+;i<outputMatrix.m_iRows;i++)
{
/*pivot is non-zero*/
if(outputMatrix.m_vecMatrix[k][k] != )
{
//T temp = outputMatrix.m_vecMatrix[0][0];
rank++;
break;
}
else
{
if(i < outputMatrix.m_iRows)
{
outputMatrix.exchangeRows(k,i);
}
}
} /*if there is no pivot in this row*/
if(outputMatrix.m_vecMatrix[k][k] == )
{
break;
} /*elimination:The rows below pivot row subtract times of pivot row*/
for(int i=k+;i<outputMatrix.m_iRows;i++)
{
double RowsfirstData = outputMatrix.m_vecMatrix[i][k]/outputMatrix.m_vecMatrix[k][k];//Save the first data of next(k+1) rows
if(RowsfirstData != )
{
outputMatrix.m_vecMatrix[i][k]=;
for(int j=k+;j<outputMatrix.m_iColumns;j++)
{
outputMatrix.m_vecMatrix[i][j] -= RowsfirstData*outputMatrix.m_vecMatrix[k][j] ;
}
}
}
} /*normalizing:set all pivots to 1*/
for(int i=;i<outputMatrix.m_iRows;i++)
{
for(int j=;j<outputMatrix.m_iColumns;j++)
{
if(outputMatrix.m_vecMatrix[i][j] != )//pivot has been foound
{
double pivot = outputMatrix.m_vecMatrix[i][j];//get pivot
for(int k=i;k<outputMatrix.m_iColumns;k++)
{
outputMatrix.m_vecMatrix[i][k] /=pivot;
}
break;
}
}
} /*Back substitution*/
for(int i = rank;i>=;i--)
{
/*find a first non-zero elem (It is pivot)*/
for(int j=;j<outputMatrix.m_iColumns;j++)
{
double times=;
if(outputMatrix.m_vecMatrix[i][j] !=)//pivot found
{
for(int l=i-;l>=;l--)
{
times = outputMatrix.m_vecMatrix[l][j]/outputMatrix.m_vecMatrix[i][j];
for(int k=j;k<outputMatrix.m_iColumns;k++)//tims of this row subtract by each columns in upon row
{
outputMatrix.m_vecMatrix[l][k] -= times*outputMatrix.m_vecMatrix[i][k];
}
}
break;
}
}
} *this = outputMatrix;
return true;
}
rrefmovie()//化简矩阵成行最简,并打印过程
template <typename T>
bool Matrix<T>::rrefmovie()
{
Matrix<T> outputMatrix = *this;
int rank=;//the rank of the matrix, how many columns's pivot will it has(-1) /*Gauss elmiation*/
cout<<"Gauss elimination:"<<endl;
outputMatrix.printfAll();
for(int k=;k<outputMatrix.m_iRows;k++)
{
/*If all the pivot elem have been found*/
if(k>=m_iColumns)
{
break;
} /*Exchange rows downward to find the pivot row*/
for(int i=k+;i<outputMatrix.m_iRows;i++)
{
/*Pivot is non-zero*/
if(outputMatrix.m_vecMatrix[k][k] != )
{
rank++;
break;
}
else
{
if(i < outputMatrix.m_iRows)
{
outputMatrix.exchangeRows(k,i);
}
}
if(k!=i)
{
cout<<"row"<<k+<<" exchange row"<<i+<<endl;//Debug
outputMatrix.printfAll();
}
} /*If there is no pivot in this row*/
if(outputMatrix.m_vecMatrix[k][k] == )
{
break;
} /*Elimination:The rows below pivot row subtract times of pivot row*/
for(int i=k+;i<outputMatrix.m_iRows;i++)
{
double RowsfirstData = outputMatrix.m_vecMatrix[i][k]/outputMatrix.m_vecMatrix[k][k];//Save the first data of next(k+1) rows
if(RowsfirstData != )
{
outputMatrix.m_vecMatrix[i][k]=;
for(int j=k+;j<outputMatrix.m_iColumns;j++)
{
outputMatrix.m_vecMatrix[i][j] -= RowsfirstData*outputMatrix.m_vecMatrix[k][j] ;
}
}
cout<<"row"<<i+<<" - "<<RowsfirstData<<"*"<<"row"<<k+<<endl;//Debug
outputMatrix.printfAll();
}
} /*Normalizing:set all rows pivot to 1*/
for(int i=;i<outputMatrix.m_iRows;i++)
{
for(int j=;j<outputMatrix.m_iColumns;j++)
{
if(outputMatrix.m_vecMatrix[i][j] != )//pivot has been foound
{
double pivot = outputMatrix.m_vecMatrix[i][j];//get pivot
for(int k=i;k<outputMatrix.m_iColumns;k++)
{
outputMatrix.m_vecMatrix[i][k] /=pivot;
}
cout<<"row"<<i+<<" / "<<pivot<<endl;//Debug
outputMatrix.printfAll();//Debug
break;
}
}
} /*Back substitution*/
cout<<"Back substitution:"<<endl;
for(int i = rank;i>=;i--)
{
/*find a first non-zero elem (It is pivot)*/
for(int j=;j<outputMatrix.m_iColumns;j++)
{
double times=;
if(outputMatrix.m_vecMatrix[i][j] !=)//pivot found
{
for(int l=i-;l>=;l--)
{
times = outputMatrix.m_vecMatrix[l][j]/outputMatrix.m_vecMatrix[i][j];
for(int k=j;k<outputMatrix.m_iColumns;k++)//tims of this row subtract by each columns in upon row
{
outputMatrix.m_vecMatrix[l][k] -= times*outputMatrix.m_vecMatrix[i][k];
}
cout<<"row"<<l+<<" - "<<times<<"*"<<"row"<<i+<<endl;
outputMatrix.printfAll();
}
break;
}
}
} *this = outputMatrix;
return true;
}
使用我们开始的矩阵测试:

Matrix<double> matrix(,);
matrix.setSpecifiedElem(,,);
matrix.setSpecifiedElem(,,);
matrix.setSpecifiedElem(,,);
matrix.setSpecifiedElem(,,);
matrix.setSpecifiedElem(,,);
matrix.setSpecifiedElem(,,);
matrix.setSpecifiedElem(,,);
matrix.setSpecifiedElem(,,);
matrix.setSpecifiedElem(,,);
matrix.printfAll(); matrix.rrefmovie();
matrix.printfAll();
system("pause");
结果:

线性代数-矩阵-【5】矩阵化简 C和C++实现的更多相关文章
- HDU 3802 矩阵快速幂 化简递推式子 加一点点二次剩余知识
求$G(a,b,n,p) = (a^{\frac {p-1}{2}}+1)(b^{\frac{p-1}{2}}+1)[(\sqrt{a} + \sqrt{b})^{2F_n} + (\sqrt{a} ...
- Google Code Jam 2008 Round 1A C Numbers(矩阵快速幂+化简方程,好题)
Problem C. Numbers This contest is open for practice. You can try every problem as many times as you ...
- HDU 4565 So Easy! 数学 + 矩阵 + 整体思路化简
http://acm.hdu.edu.cn/showproblem.php?pid=4565 首先知道里面那个东西,是肯定有小数的,就是说小数部分是约不走的,(因为b限定了不是一个完全平方数). 因为 ...
- 【BZOJ1048】分割矩阵(记忆化搜索,动态规划)
[BZOJ1048]分割矩阵(记忆化搜索,动态规划) 题面 BZOJ 洛谷 题解 一个很简单的\(dp\),写成记忆化搜索的形式的挺不错的. #include<iostream> #inc ...
- 【线性代数】2-4:矩阵操作(Matrix Operations)
title: [线性代数]2-4:矩阵操作(Matrix Operations) toc: true categories: Mathematic Linear Algebra date: 2017- ...
- 《Linear Algebra and Its Application》-chaper1-行化简法解决线性方程组
在实际生产生活中,需要我们解大量的线性方程组,例如是有探测.线性规划.电路等,这里我们便从理论角度建立一套解决线性方程组的体系. 线性方程组: 形如下面形式的方程组称为线性方程组. 回想起解决二元线性 ...
- 【11.5校内测试】【倒计时5天】【DP】【二分+贪心check】【推式子化简+线段树】
Solution 非常巧妙的建立DP方程. 据dalao们说题目明显暗示根号复杂度??(反正我是没看出来 因为每次分的块大小一定不超过$\sqrt n$,要不然直接每个位置开一个块答案都才为$n$. ...
- hdu 1588 Gauss Fibonacci(矩阵嵌矩阵)
题目大意: 求出斐波那契中的 第 k*i+b 项的和. 思路分析: 定义斐波那契数列的矩阵 f(n)为斐波那契第n项 F(n) = f(n+1) f(n) 那么能够知道矩阵 A = 1 1 1 0 ...
- DFA与NFA的等价性,DFA化简
等价性 对于每个NFA M存在一个DFA M',使得L(M)=L(M')--------等价性证明,NFA的确定化 假定NFA M=<S, Σ, δ, S 0 , F>,我们对M的状态转换 ...
随机推荐
- 阿里云服务器怎么运行多个项目(Nginx)
server { listen 80; server_name yy.test.cn; access_log /data/wwwlogs/access_nginx.log combined; root ...
- 初学Python(十)——列表生成式
初学Python(十)--列表生成式 初学Python,主要整理一些学习到的知识点,这次是列表生成式. # -*- coding:utf-8 -*- ''''' 列表生成式 ''' #一行代码表达所有 ...
- python机器学习实战(三)
python机器学习实战(三) 版权声明:本文为博主原创文章,转载请指明转载地址 www.cnblogs.com/fydeblog/p/7277205.html 前言 这篇notebook是关于机器 ...
- JAVA 中BIO,NIO,AIO的理解以及 同步 异步 阻塞 非阻塞
在高性能的IO体系设计中,有几个名词概念常常会使我们感到迷惑不解.具体如下: 序号 问题 1 什么是同步? 2 什么是异步? 3 什么是阻塞? 4 什么是非阻塞? 5 什么是同步阻塞? 6 什么是同步 ...
- vue-项目入门
初入前端的新人在碰到vue.js后,去过官网,估计粗略的看下api文档以后会以为vue的安装只是把那串js代码直接粘贴复制到文档即可,虽然这样是可以,但那在项目中并不合适. 项目中的vue引入(配制安 ...
- [补档]暑假集训D5总结
%dalao 今天又有dalao来讲课,讲的是网络流 网络流--从入门到放弃:7-29dalao讲课笔记--https://hzoi-mafia.github.io/2017/07/29/27/ ...
- 笔记本电脑连接上WiFi后,弹不出登录界面怎么办?
以CMCC为例子 步骤: 1 连接成功CMCC之后,打开适配器设置.右击无线网卡,选择属性 2.双击INTERNET协议版本4 3.将DNS改成自动获取,然后确定 4.再确定 5.然后重新断开CMCC ...
- java 使用https协议,cas认证PKIX path building failed错误解决方法
如果遇到的是 上图的异常,请继续往下看. linux 下 添加 证书 (1) 获取网站安全证书 xx.cer ( 详情见随笔 获取网站安全证书 ) (2) 将上面导出的证书导入java中的cacert ...
- HTML的正确入门姿势——基本结构与基本标签
一.什么是HTML HTML是超文本标签语言,即网页的源码.而浏览器就是翻译解释HTML源码的工具. 二.HTML文档的结构 HTML文档主要包括三大部分:文档声明部分.<head>头部部 ...
- Selenium对于对话框alert,confirm,prompt的处理
html 源码: <html> <head> <title>Alert</titl ...