java实现高斯赛德尔算法解线性方程组

来源:互联网 发布:淘宝会员v0等级有什么 编辑:程序博客网 时间:2024/06/03 06:56
packagelinear_equation;
 
importjava.util.Scanner;
 
/*使用高斯赛德尔迭代法求解线性方程组*/
publicclassGauss_Seidel_Iterate {
    /*求下三角*/
    privatestaticfloat[][] find_lower(floatdata[][],intk){
        intlength=data.length;
        floatdata2[][]=newfloat[length][length];
        if(k>=0){
            for(inti=0;i<=length-k-1;i++){
                for(intj=0;j<=i+k;j++){
                    data2[i][j]=data[i][j];
                }
            }
            for(inti=length-k;i<length;i++){
                for(intj=0;j<length;j++){
                    data2[i][j]=data[i][j];
                }
            }
        }
        else{
            for(inti=-k;i<length;i++){
                for(intj=0;j<=i+k;j++){
                    data2[i][j]=data[i][j];
                }
            }
        }
        returndata2;
    }
    /*求原矩阵的负*/
    privatestaticfloat[][] opposite_matrix(float[][] data){
        intM=data.length;
        intN=data[0].length;
        floatdata_temp[][]=newfloat[M][N];
        for(inti=0;i<M;i++){
            for(intj=0;j<N;j++){
                data_temp[i][j]=-data[i][j];
            }
        }
        returndata_temp;
    }
    /*原矩阵去掉第i+1行第j+1列后的剩余矩阵*/
    privatestaticfloat[][] get_complement(float[][] data, inti,intj) {
 
        /* x和y为矩阵data的行数和列数 */
        intx = data.length;
        inty = data[0].length;
 
        /* data2为所求剩余矩阵 */
        floatdata2[][] = newfloat[x - 1][y - 1];
        for(intk = 0; k < x - 1; k++) {
            if(k < i) {
                for(intkk = 0; kk < y - 1; kk++) {
                    if(kk < j) {
                        data2[k][kk] = data[k][kk];
                    }else{
                        data2[k][kk] = data[k][kk + 1];
                    }
                }
 
            }else{
                for(intkk = 0; kk < y - 1; kk++) {
                    if(kk < j) {
                        data2[k][kk] = data[k + 1][kk];
                    }else{
                        data2[k][kk] = data[k + 1][kk + 1];
                    }
                }
            }
        }
        returndata2;
 
    }
    /* 计算矩阵行列式 */
    privatestaticfloat cal_det(float[][] data) {
        floatans=0;
        /*若为2*2的矩阵可直接求值并返回*/
        if(data[0].length==2){
             ans=data[0][0]*data[1][1]-data[0][1]*data[1][0];
        }
        else{
            for(inti=0;i<data[0].length;i++){
                /*若矩阵不为2*2那么需求出矩阵第一行代数余子式的和*/
                float[][] data_temp=get_complement(data, 0, i);
                if(i%2==0){
                    /*递归*/
                    ans=ans+data[0][i]*cal_det(data_temp);
                }
                else{
                    ans=ans-data[0][i]*cal_det(data_temp);
                }
            }
        }
        returnans;
 
    }
     
    /*计算矩阵的伴随矩阵*/
    privatestaticfloat[][] ajoint(float[][] data) {
        intM=data.length;
        intN=data[0].length;
        floatdata2[][]=newfloat[M][N];
        for(inti=0;i<M;i++){
            for(intj=0;j<N;j++){
            if((i+j)%2==0){
                data2[i][j]=cal_det(get_complement(data, i, j));
            }
            else{
                data2[i][j]=-cal_det(get_complement(data, i, j));
            }
            }
        }
         
        returntrans(data2);
         
 
    }
     
    /*转置矩阵*/
    privatestaticfloat [][]trans(float[][] data){
        inti=data.length;
        intj=data[0].length;
        float[][] data2=newfloat[j][i];
        for(intk2=0;k2<j;k2++){
            for(intk1=0;k1<i;k1++){
                data2[k2][k1]=data[k1][k2];
            }
        }
         
        /*将矩阵转置便可得到伴随矩阵*/
        returndata2;
         
    }
     
     
     
    /*求矩阵的逆,输入参数为原矩阵*/
    privatestaticfloat[][] inv(float[][] data){
        intM=data.length;
        intN=data[0].length;
        floatdata2[][]=newfloat[M][N];
        floatdet_val=cal_det(data);
        data2=ajoint(data);
        for(inti=0;i<M;i++){
            for(intj=0;j<N;j++){
                data2[i][j]=data2[i][j]/det_val;
            }
        }
         
        returndata2;
    }
    /*矩阵加法*/
    privatestaticfloat[][] matrix_add(float[][] data1,float[][] data2){
        intM=data1.length;
        intN=data1[0].length;
        floatdata[][]=newfloat[M][N];
        for(inti=0;i<M;i++){
            for(intj=0;j<N;j++){
                data[i][j]=data1[i][j]+data2[i][j];
            }
        }
        returndata;
    }
    /*矩阵相乘*/
    privatestaticfloat[][] multiply(float[][] data1,float[][] data2){
        intM=data1.length;
        intN=data1[0].length;
        intK=data2[0].length;
        float[][] data3=newfloat[M][K];
        for(inti=0;i<M;i++){
            for(intj=0;j<K;j++){
                for(intk=0;k<N;k++){
                    data3[i][j]+=data1[i][k]*data2[k][j];
                }
            }
        }
        returndata3;
    }
    /*输入参数为原矩阵和一个整数,该整数代表从对角线往上或往下平移的元素个数*/
    privatestaticfloat[][] find_upper(float[][] data,intk){
        intlength=data.length;
        intM=length-k;
        float[][] data2=newfloat[length][length];
        if(k>=0){
            for(inti=0;i<M;i++){
                for(intj=k;j<length;j++){
                    data2[i][j]=data[i][j];
                }
                k+=1;
            }
        }
        else{
            for(inti=0;i<-k;i++){
                for(intj=0;j<length;j++){
                    data2[i][j]=data[i][j];
                }
            }
            for(inti=-k;i<length;i++){
                for(intj=i+k;j<length;j++){
                    data2[i][j]=data[i][j];
                }
            }
        }
        returndata2;
    }
    /*m*n矩阵与n维向量的乘法*/
    privatestaticfloat[] multiply2(float[][] data1,float[] data2){
        intM=data1.length;
        intN=data1[0].length;
        float[] data3=newfloat[M];
        for(intk=0;k<M;k++){
                for(intj=0;j<N;j++){
                    data3[k]+=data1[k][j]*data2[j];
                }
        }
        returndata3;
    }
    /*向量加法*/
    privatestaticfloat[] matrix_add2(float[] data1,float[] data2){
        intM=data1.length;
        floatdata[]=newfloat[M];
        for(inti=0;i<M;i++){
                data[i]=data1[i]+data2[i];
        }
        returndata;
    }
    /*求两向量之差的二范数(用于检验误差)*/
    privatestaticdouble cal_error(float[] X1,float[] X2){
        intM=X1.length;
        doubletemp=0;
        for(inti=0;i<M;i++){
            temp+=Math.pow((X1[i]-X2[i]),2);
        }
        temp=Math.sqrt(temp);
        returntemp;
    }
    /*求矩阵的对角矩阵*/
    privatestaticfloat[][] find_diagnal(floatA[][]) {
        intm = A.length;
        intn = A[0].length;
        floatB[][] = newfloat[m][n];
        for(inti = 0; i < m; i++) {
            for(intj = 0; j < n; j++) {
                if(i == j) {
                    B[i][j] = A[i][j];
                }
            }
        }
        returnB;
 
    }
    /*高斯赛德尔迭代法*/
    privatestaticfloat[] Gauss_Seidel_method(float[][] A,float[] B,float[] X){
        floatD[][]=find_diagnal(A);
        floatL[][]=find_lower(A, -1);
        floatU[][]=find_upper(A,1);
        floattemp1[][]=inv(matrix_add(D, L));
        floattemp2[][]=opposite_matrix(temp1);
        floatB0[][]=multiply(temp2, U);
        floatF[]=multiply2(temp1, B);
         
        returnmatrix_add2(multiply2(B0, X), F);
     
         
    }
     
    publicstaticvoid main(String[] args) {
        System.out.println("输入系数矩阵的行和列数:");
        Scanner scan=newScanner(System.in);
        intM=scan.nextInt();
        System.out.println("输入方程组右侧方程值的维度:");
        intK=scan.nextInt();
        if(M!=K){
            System.out.println("方程组个数和未知数个数不等!");
            System.exit(0);
        }
         
        System.out.println("输入系数矩阵:");
        float[][] A=newfloat[M][M];
        for(inti=0;i<M;i++){
            for(intj=0;j<M;j++){
                A[i][j]=scan.nextFloat();
            }
        }
         
        System.out.println("输入值向量");
        float[] B=newfloat[M];
        for(inti=0;i<M;i++){
            B[i]=scan.nextFloat();
        }
         
        System.out.println("输入初始迭代向量:");
        float[] X=newfloat[M];
        for(inti=0;i<M;i++){
            X[i]=scan.nextFloat();
        }
         
        System.out.println("输入误差限:");
        floater=scan.nextFloat();
        floattemp[]=newfloat[M];
        while(cal_error((temp=Gauss_Seidel_method(A, B, X)), X)>=er){
            X=temp;
        }
//      while(cal_error((temp=Gauss_Seidel_method(A, B, X)), X)>=er){
//          X=temp;
//         
//      }
        X=temp;
        System.out.println("高斯赛德尔计算得到的解向量为:");
        for(inti=0;i<M;i++){
            System.out.println(X[i]+" ");
        }
        System.out.println();
 
    }
 
}
原文:http://www.oschina.net/code/snippet_574827_39084
0 0
原创粉丝点击