二更:把更多的行列式有关内容加了进来(%%%%%Jelly Goat奆佬)

题目描述

给你一个N(n≤10n\leq 10n≤10)阶行列式,请计算出它的值

输入输出格式

输入格式:

第一行有一个整数n
在以下n行中,每行有n个整数,表示该行列式

输出格式:

这个行列式的值

输入输出样例

输入样例#1:

8
2 10 4 4 3 6 10 6
1 10 9 3 2 1 6 7
3 9 8 7 1 1 8 7
2 10 8 6 9 9 3 4
1 7 1 8 2 6 2 3
9 2 4 8 10 6 10 3
3 6 7 9 8 2 8 1
2 9 2 1 10 7 4 5
输出样例#1:

-135742
输入样例#2:

4
1 2 3 4
1 3 4 1
1 4 1 2
1 1 2 3
输出样例#2:

16
首先这是一道非常简单的板子题,他耗费了我两天将近两个多小时的时间,那么我们就来细细分析一下这道题
思路大致如下: 按照高斯消元法,把行列式消成下三角,然后按照公式直接求对角线乘积即为答案
有这么几个坑
1.忘记用double类型,因为行列式做除法的时候肯定是要出小数的,不用double肯定gg
2.没有注意当a[i][i]==0的时候,我们没法按照公式把它下面消为零,所以需要一个换行操作
代码如下
while (a[i][i] ==  && sum<=n) //对是否a[i][i]是0的特判
{
CH2(i, sum + ); //交换x列和y列
ans *= -;
sum++;
}
3.输出的时候忘记控制精度,其实原因是这样的,在小数点后位数多于18个之后,c++会自动转成科学计数法。。。。。。
但是洛谷不认啊喂!!!!!!!,所以输出的时候手动控制一下就好
  printf("%0.0lf", ans);
4.各种奇奇怪怪的诸如循环控制写错了或者是while条件判错了的诡异失误,导致我挂了整整五次
不过这种经历也的确是能让我深刻的记住这道题了吧。
现在贴一下AC代码
#include <iostream>
#include <string>
#include <cstdio>
#include <algorithm>
#include <cstring>
using namespace std;
double n, a[][], ans = ;
int sum;
inline void CH1(int x, int y, double k) //第y行减k*x
{
for (int i = ; i <= n; ++i)
a[y][i] -= (double)(k * a[x][i]);
}
inline void CH2(int x, int y) //交换x列和y列
{
for (int i = ; i <= n; ++i)
swap(a[i][x], a[i][y]);
}
inline double CH3(int x, double k) //把第x行提出一个公因数k
{
for (int i = ; i <= n; ++i)
a[x][i] /= k;
return k;
}
int main()
{
scanf("%lf", &n);
for (int i = ; i <= n; ++i)
for (int j = ; j <= n; ++j)
scanf("%lf", &a[i][j]);
for (int i = ; i < n; ++i)
{
sum=i;
while (a[i][i] == && sum<=n) //对是否a[i][i]是0的特判
{
CH2(i, sum + ); //交换x列和y列
ans *= -;
sum++;
}
ans *= CH3(i, a[i][i]);
for (int j = i + ; j <= n; ++j)
CH1(i, j, a[j][i]);
}
for (int i = ; i <= n; ++i)
ans *= a[i][i];
printf("%0.0lf", ans);
return ;
}
 
05-11 22:13