zoukankan      html  css  js  c++  java
  • TOJ5272: 逆矩阵

    5272: 逆矩阵 分享至QQ空间

    Time Limit(Common/Java):1000MS/3000MS     Memory Limit:65536KByte
    Total Submit: 11            Accepted:7

    Description

     

    设A是数域上的一个n阶方阵,若在相同数域上存在另一个n阶矩阵B,使得:AB=BA=E(单位矩阵)。 则我们称B是A的逆矩阵,而A则被称为可逆矩阵。

    现在告诉你一个n阶方阵A,求它的逆矩阵B。

    blob.pngblob.png

    Input

     

    输入数据有多组,第一行为数据组数T,接下来有T个矩阵。

    每个矩阵的第一行为n(n<20),表示n阶方阵,接下来的n行n列表示n*n的矩阵

    矩阵元素为实数。

    Output

     

    按照n行n列输出逆矩阵B,所有元素保留2位小数。数据保证一定有逆矩阵。

    Sample Input

     

    1
    5
    1.3 0.8 0.5 0.8 1.0
    0.5 0.6 1.0 1.3 1.0
    0.8 1.4 0.9 1.1 1.4
    1.0 0.6 0.8 1.4 0.5
    0.7 0.6 1.4 1.4 1.2

    Sample Output

     

    0.86 -1.37 -0.36 0.37 0.69
    -1.10 -1.90 1.71 0.93 0.12
    -1.08 -4.01 0.72 0.64 3.14
    0.01 3.06 -0.61 0.33 -1.99
    1.29 2.85 -0.77 -1.81 -0.97

    Source

    矩阵的逆,我提供了两种方法。

    LU分解

    #include<stdio.h>
    const int N=21;
    double a[N][N],b[N][N],c[N][N],bt[N][N],ct[N][N],ans[N][N];
    int T,n;
    void LU()
    {
         for(int i=0; i<n; i++)
            for(int j=0; j<n; j++)b[i][j]=c[i][j]=bt[i][j]=ct[i][j]=ans[i][j]=0;
        for(int i=0; i<n; i++)b[i][i]=bt[i][i]=1;
        double s;
        for(int i=0; i<n; i++)
        {
            for(int j=i; j<n; j++)
            {
                s=0;
                for(int k=0; k<i; k++)
                    s+=b[i][k]*c[k][j];
                c[i][j]=a[i][j]-s;
            }
            for(int j=i+1; j<n; j++)
            {
                s=0;
                for(int k=0; k<i; k++)
                    s+=b[j][k]*c[k][i];
                b[j][i]=(a[j][i]-s)/c[i][i];
            }
        }
        for(int i=1; i<n; i++)
            for(int j=0; j<i; j++)
            {
                s=0;
                for(int k=0; k<i; k++)
                    s+=b[i][k]*bt[k][j];
                bt[i][j]=-s;
            }
        for(int i=0; i<n; i++)
            ct[i][i]=1/c[i][i];
        for(int i=1; i<n; i++)
            for(int j=i-1; j>=0; j--)
            {
                s=0;
                for(int k=j+1; k<=i; k++)
                    s+=c[j][k]*ct[k][i];
                ct[j][i]=-s/c[j][j];
            }
        for(int i=0; i<n; i++)
            for(int j=0; j<n; j++)
                for(int k=0; k<n; k++)
                    ans[i][j]+=ct[i][k]*bt[k][j];
        for(int i=0; i<n; i++)
            for(int j=0; j<n; j++)printf("%.2f%c",ans[i][j],j==n-1?'
    ':' ');
    }
    int main()
    {
        scanf("%d",&T);
        while(T--)
        {
            scanf("%d",&n);
            for(int i=0; i<n; i++)
                for(int j=0; j<n; j++)
                    scanf("%lf",&a[i][j]);
            LU();
        }
        return 0;
    }

    Gauss 消元

    #include<stdio.h>
    #include<math.h>
    #include<algorithm>
    const double eps=1e-4;
    const int N=21;
    double a[N][N],b[N],x[N],s,t[N][N],ans[N][N];
    int n;
    void gauss()
    {
        int i;
        for(int k=1; k<=n; k++)
        {
            for(i=k; i<=n&&fabs(a[i][k])<eps; i++);
            if(i!=k)
            {
                for(int j=k; j<=n; j++)std::swap(a[i][j],a[k][j]);
                std::swap(b[i],b[k]);
            }
            for(i=k+1; i<=n; i++)
            {
                s=a[i][k]/a[k][k];
                for(int j=k; j<=n; j++)a[i][j]-=a[k][j]*s;
                b[i]-=b[k]*s;
            }
        }
        for(i=n; i>=1; --i)
        {
            s=b[i];
            for(int j=i+1; j<=n; j++)s-=x[j]*a[i][j];
            x[i]=s/a[i][i];
            if(fabs(x[i])<eps)x[i]=0;
        }
    }
    int main()
    {
        int T;
        scanf("%d",&T);
        while(T--)
        {
            scanf("%d",&n);
            for(int i=1; i<=n; i++)
            {
                for(int j=1; j<=n; j++)
                    scanf("%lf",&t[i][j]),a[i][j]=t[i][j];
                b[i]=0;
            }
            for(int k=1; k<=n; k++)
            {
                for(int i=1; i<=n; i++)
                {
                    for(int j=1; j<=n; j++)a[i][j]=t[i][j];
                    b[i]=0;
                }
                b[k]=1;
                gauss();
                for(int i=1; i<=n; i++)ans[i][k]=x[i];
            }
            for(int i=1; i<=n; i++)
                for(int j=1; j<=n; j++)printf("%.2f%c",ans[i][j],j==n?'
    ':' ');
        }
        return 0;
    }
  • 相关阅读:
    BZOJ1787 [Ahoi2008]Meet 紧急集合[结论题]
    poj3728 The merchant[倍增]
    poj2750 Potted Flower[线段树]
    poj2482 Stars in Your Window[扫描线]
    poj2182 Lost Cows[BIT二分]
    UVA12096 The SetStack Computer
    第05组(65) 需求分析报告
    团队介绍与选题报告
    数据采集技术第三次作业
    结对编程作业
  • 原文地址:https://www.cnblogs.com/BobHuang/p/9760883.html
Copyright © 2011-2022 走看看