zoukankan      html  css  js  c++  java
  • 矩阵求逆 模板

    问题:给定一个N阶矩阵求他的逆矩阵

    建议学习线性代数后食用此题...

    我们对输入的矩阵进行初等变换(初等乱搞),同时对一个单位矩阵进行相同的初等变换,最后将我们输入的矩阵变换成单位矩阵之后,那个单位矩阵就变成了我们输入的矩阵的逆矩阵

    假设我们进行初等变换的初等矩阵乘起来是(P),且我们输入的矩阵为(A)

    (AP=E),则(A^{-1}AP=A^{-1}E),则(P=A^{-1}),也就是把初等变换矩阵乘起来(或者是说把它们乘上一个单位矩阵)得到的就是矩阵的逆矩阵

    (A)消成单位矩阵就要先把A大力消成上三角矩阵,高斯消元就能做

    #include <bits/stdc++.h>
    #define p 1000000007
    #define int long long
    using namespace std;
    
    int n;
    
    //定义矩阵及其初等变换 
    struct matrix
    {
    	int a[400][400];
    	
    	//矩阵第x行和第y行交换
    	void change1(int x, int y)
    	{
    		for (int i = 0; i < n; i++)
    			swap(a[x][i], a[y][i]);
    	}
    	
    	//矩阵第x行乘以k
    	void change2(int x, int k)
    	{
    		for (int i = 0; i < n; i++)
    			(((a[x][i] *= k) %= p) += p) %= p;
    	}
    	
    	//矩阵第x行加上第y行乘以k
    	void change3(int x, int y, int k)
    	{
    		for (int i = 0; i < n; i++)
    			(((a[x][i] += a[y][i] * k % p) %= p) += p) %= p;
    	}
    	
    	void print()
    	{
    		for (int i = 0; i < n; i++)
    			for (int j = 0; j < n; j++)
    				printf("%lld%c", a[i][j], j == n - 1 ? '
    ' : ' ');
    	}
    }a, b; 
    
    int ksm(int x, int y = (p - 2))
    {
    	int ans = 1;
    	while (y > 0)
    	{
    		if (y & 1)
    			(ans *= x) %= p;
    		(x *= x) %= p;
    		y >>= 1;
    	}
    	return ans;
    }
    
    signed main()
    {
    	//输入
    	scanf("%lld", &n);
    	for (int i = 0; i < n; i++)
    		for (int j = 0; j < n; j++)
    			scanf("%lld", &a.a[i][j]);
    	
    	//把B赋值为单位矩阵 
    	for (int i = 0; i < n; i++)
    		b.a[i][i] = 1;
    	
    	//把A消为上三角矩阵
    	for (int i = 0; i < n; i++)
    	{
    		if(a.a[i][i] == 0)
    			for (int j = i; j < n; j++)
    				if (a.a[j][i] != 0)
    				{
    					b.change1(i, j);
    					a.change1(i, j);
    					break;
    				}
    		if (a.a[i][i] == 0)//矩阵不是满秩的
    		{
    			printf("No Solution
    ");
    			return 0;
    		}
    		b.change2(i, ksm(a.a[i][i]));
    		a.change2(i, ksm(a.a[i][i]));
    		for (int j = i + 1; j < n; j++)
    		{
    			b.change3(j, i, -a.a[j][i]);
    			a.change3(j, i, -a.a[j][i]);
    		}
    	}
    	
    	//把A消为单位矩阵 
    	for (int i = n - 2; i >= 0; i--)
    		for (int j = i +1; j < n; j++)
    		{
    			b.change3(i, j, -a.a[i][j]);
    			a.change3(i, j, -a.a[i][j]);
    		}
    	
    	b.print();
    	return 0;
    }
    

    另外注意一个细节,要先对b乱搞,如果对a搞完了那么那个值就是1了,对b搞的那个值也变成1了

  • 相关阅读:
    poj 3411 Paid Roads
    uva 111 A History Grading
    hdu 4248 A Famous Stone Collector
    阶乘模版
    uva Coin Change
    POJ图论分类
    求 组合数 dp
    判断点是否在三角形中(三角形的有向积计算)
    扩展欧几里德
    UVA 116 Unidirectional TSP (白书dp)
  • 原文地址:https://www.cnblogs.com/oier/p/9596681.html
Copyright © 2011-2022 走看看