c++算法:计算行列式的值(详细讲解)
参考了:https://blog.csdn.net/u011885865/article/details/42032229
需要的基础:学过《线性代数》,知道行列式值的求法
基本公式:对于如下的行列式:
其值为:
相信大家都懂这个公式的具体含义,我就不解释了,不懂的同学百度一下行列式
分析一个这个公式该如何实现:
假定现有有一个3*3的行列式,则其计算公式为:
观察这个式子,可以发现其有一个核心,那就是生成一个全排列。本例中是一个3*3矩阵,因此需要生成123的全排列,共有六个:123、132、213、231、321、312。
然后就是要计算,生成的排列的逆序数,即
总结起来可分为如下几步:
1、求出给定n阶矩阵的全排列,我用vector<int>存储一个全排列(即上例中6个全排列中的某一个),用vector<vector<int> >存储所有的全排列(即上例中的六个全排列)。
2、计算排列的逆序数。
3、分别以1,2...n为row值,从vector<int>中依次提取的值为col值,组成行列式中元素的下标,然后相乘
4、求和。
算法实现:
1、求全排的算法如下,不懂该算法的可以移步:https://www.cnblogs.com/XiaoXiaoShuai-/p/10383535.html
//交换元素
void swap(vector<int>& vec, int i, int j)
{
int temp = vec[i];
vec[i] = vec[j];
vec[j] = temp;
}
//第一个参数表示初始的数列,在上例中,该vec中的元素为1,2,3
//第二个参数表示最终得到的全排列集合
void Perm(vector<int>& vec, vector<vector<int> >& vec_seq, int current_index = 0)
{
if (current_index == ((int)vec.size() - 1))
{
vec_seq.push_back(vec);
}
else
{
for (int i = current_index; i < (int)vec.size(); i++)
{
swap(vec, i, current_index);
Perm(vec, vec_seq, current_index + 1);
swap(vec, i, current_index);
}
}
}
当然,还得有一个生成初始数列的函数
//根据n生成一个初始vector
vector<int> inivec(int n)
{
vector<int> vec;
for (int i = 0; i < n; i++)
vec.push_back(i);
return vec;
}
第二步:求出全排列的逆序数,判断逆序数的奇偶
//得出排列的逆排序数,并根据奇偶判读正负
bool Iseven(int num)
{
//用位与运算来判断奇偶(最快的判断奇偶的方法)
return ((num & 1) == 0);
}
//是否幂为正
bool PowerIsPosition(vector<int>& vec)
{
//count即为逆序数,初始化为0
int count = 0;
for (int i = 0; i < (int)vec.size(); i++)
{
for (int j = i + 1; j < (int)vec.size(); j++)
{
if (vec[i] > vec[j])
{
count += 1;
}
}
}
return (Iseven(count));
}
第三步和第四步:
//计算结果
//第一个参数表示输入的行列式
//第二个参数表示该行列式的阶数,在本例中n = 3,即一个3*3的行列式
int calculate(int** array, int n)
{
vector<vector<int> > vec_que;
vector<int> vec = inivec(n);
vector<int> vec_elem;
Perm(vec, vec_que);
//最终结果,初始化为0
int result = 0;
//依次为vec_que中取出行列式
for (int i = 0; i < (int)vec_que.size();i++)
{
vec_elem = vec_que[i];
//mi即为前面(-1)的n次幂,最后结果为-1或者1
int mi = PowerIsPosition(vec_elem) ? 1 : (-1);
int temp = mi;
//row号初始化为0之后依次加1
int row = 0;
//col号依次从vec_elem中取出
for (int j = 0; j < (int)vec_elem.size();j++)
{
int col = vec_elem[j];
temp *= array[row++][col];
}
result += temp;
}
return result;
}
检验一下:
int main()
{
int** array = new int*[3];
for (int i = 0; i < 3; i++)
{
array[i] = new int[3];
}
array[0][0] = 2;
array[0][1] = -4;
array[0][2] = 1;
array[1][0] = 1;
array[1][1] = -5;
array[1][2] = 3;
array[2][0] = 1;
array[2][1] = -1;
array[2][2] = 1;
int result = calculate(array, 3);
return 0;
}
计算的result = -8,结果正确
c++算法:计算行列式的值(详细讲解)的更多相关文章
- 数据结构与算法(九):AVL树详细讲解
数据结构与算法(一):基础简介 数据结构与算法(二):基于数组的实现ArrayList源码彻底分析 数据结构与算法(三):基于链表的实现LinkedList源码彻底分析 数据结构与算法(四):基于哈希 ...
- C#程序计算N阶行列式的值及N元一次方程组
C#程序计算N阶行列式的值及N元一次方程组 用了挺长时间自行完成了C#程序计算N阶行列式的值及N元一次方程组.由于自己没有在网上查阅其他资料,所以只能硬着头皮用最朴素的思想和基础的算法进行编程.在给出 ...
- C语言求行列式的值
#include "stdafx.h" #include <stdio.h> #include <stdlib.h> #include <window ...
- Java实现 蓝桥杯 算法提高 计算行列式
试题 算法提高 计算行列式 资源限制 时间限制:1.0s 内存限制:256.0MB 问题描述 //据说很多人的题目会有一大堆废话,本傻×就不在这里废话了. 给定一个N×N的矩阵A,求|A|. 输入格式 ...
- KMP算法计算next值和nextVal值
KMP算法: 给定一个主串S及一个模式串P,判断模式串是否为主串的子串:若是,返回匹配的第一个元素的位置(序号从1开始),否则返回0: 这里先不写算法,仅仅计算next和nextVal值 那么计算时只 ...
- Siki_Unity_2-1_API常用方法和类详细讲解(上)
Unity 2-1 API常用方法和类详细讲解(上) 任务1&2:课程前言.学习方法 && 开发环境.查API文档 API: Application Programming I ...
- 万字长文,以代码的思想去详细讲解yolov3算法的实现原理和训练过程,Visdrone数据集实战训练
以代码的思想去详细讲解yolov3算法的实现原理和训练过程,并教使用visdrone2019数据集和自己制作数据集两种方式去训练自己的pytorch搭建的yolov3模型,吐血整理万字长文,纯属干货 ...
- 30 道 Vue 面试题,内含详细讲解(涵盖入门到精通,自测 Vue 掌握程度)
前言 本文以前端面试官的角度出发,对 Vue 框架中一些重要的特性.框架的原理以问题的形式进行整理汇总,意在帮助作者及读者自测下 Vue 掌握的程度.本文章节结构以从易到难进行组织,建议读者按章节顺序 ...
- 高斯消元与行列式求值 part1
两道模板题,思路与算法却是相当经典. 先说最开始做的行列式求值,题目大致为给一个10*10的行列式,求其值 具体思路(一开始看到题我的思路): 1.暴算,把每种可能组合试一遍,求逆序数,做相应加减运算 ...
随机推荐
- Spring Boot2 系列教程 (十五) | 服务端参数校验之一
估计很多朋友都认为参数校验是客户端的职责,不关服务端的事.其实这是错误的,学过 Web 安全的都知道,客户端的验证只是第一道关卡.它的参数验证并不是安全的,一旦被有心人抓到可乘之机,他就可以有各种方法 ...
- 失衡天平 - 简单dp
链接:https://www.nowcoder.com/acm/contest/186/C来源:牛客网 终于Alice走出了大魔王的陷阱,可是现在傻傻的她忘了带武器了,这可如何是好???这个时候,一个 ...
- python小功能记录
本博客会不断完善,记录python小功能. 1. 合并两个字典 # in Python 3.5+ >>> x = {'a': 1, 'b': 2} >>> y = ...
- 前端笔记6-js2
1.break 和continue用法 break结束本次循环,如果想结束外层循环,可以通过这个label来指定要结束的循环. continue可以用来跳过当次循环,如果想跳过外次循环,也可以通过这个 ...
- 使用RobotFramework的JavaRemoteLibrary
终于被迫使用了Java的远程接口库(为了同时使用Java和python的用例库,且为了在pybot下跑速度能快一些),路途比实际想的要坎坷,记录下来. 远程库的原理在前边一篇文章中记录过: http: ...
- 【Java并发基础】加锁机制解决原子性问题
前言 原子性指一个或多个操作在CPU执行的过程不被中断的特性.前面提到原子性问题产生的源头是线程切换,而线程切换依赖于CPU中断.于是得出,禁用CPU中断就可以禁止线程切换从而解决原子性问题.但是这种 ...
- DataFrame分组和聚合
一.分组 1.语法 grouped= df.groupby(by='columns name') # grouped是一个DataFrameGroupBy对象,是可迭代的(遍历) # grouped中 ...
- SycSec成都信息工程大学2019CTF-前五道WEB题writeup
一.WEB (1)一起来撸猫 flag藏在标签的注释内 <!--这是注释--> (2)你看见过我的菜刀么 eval漏洞 利用蚁剑连接 连接密码就是要post传的参数 连接成功后在网站根目 ...
- windows10卸载虚拟机忘记按照步骤卸载的实际问题
好久没有写博客了,由于太多事情,工作需要用到虚拟机,结果,虚拟机出问题,,,怎么办???我的办法就是卸载了重新安装一个,结果呢?太心急没有按照不知操作,今天弄了一下午,终于弄好了... 错误原因,用了 ...
- 剑指Offer对答如流系列 - 实现Singleton模式
目录 面试题2:实现Singleton模式 一.懒汉式写法 二.饿汉式写法 三.枚举 面试题2:实现Singleton模式 题目:设计一个类,我们只能生成该类的一个实例. 由于设计模式在面向对象程序设 ...