コード例 #1
0
ファイル: Matrix.cs プロジェクト: sandboxorg/QLNet
        // Crout's LU decomposition for matrix determinant and inverse
        // stores combined lower & upper in lum[][]
        // stores row permuations into perm[]
        // returns +1 or -1 according to even or odd number of row permutations
        // lower gets dummy 1.0s on diagonal (0.0s above)
        // upper gets lum values on diagonal (0.0s below)
        public static int decompose(Matrix m, out Matrix lum, out int[] perm)
        {
            int toggle = +1; // even (+1) or odd (-1) row permutatuions
            int n      = m.rows_;

            // Make a copy of Matrix m into result Matrix lu
            lum = new Matrix(n, n);
            for (int i = 0; i < n; ++i)
            {
                for (int j = 0; j < n; ++j)
                {
                    lum[i, j] = m[i, j];
                }
            }


            // make perm[]
            perm = new int[n];
            for (int i = 0; i < n; ++i)
            {
                perm[i] = i;
            }

            for (int j = 0; j < n - 1; ++j)  // process by column. note n-1
            {
                double max = Math.Abs(lum[j, j]);
                int    piv = j;

                for (int i = j + 1; i < n; ++i) // find pivot index
                {
                    double xij = Math.Abs(lum[i, j]);
                    if (xij > max)
                    {
                        max = xij;
                        piv = i;
                    }
                } // i

                if (piv != j)
                {
                    lum.swapRow(piv, j);

                    int t = perm[piv]; // swap perm elements
                    perm[piv] = perm[j];
                    perm[j]   = t;

                    toggle = -toggle;
                }

                double xjj = lum[j, j];
                if (xjj != 0.0)
                {
                    for (int i = j + 1; i < n; ++i)
                    {
                        double xij = lum[i, j] / xjj;
                        lum[i, j] = xij;
                        for (int k = j + 1; k < n; ++k)
                        {
                            lum[i, k] -= xij * lum[j, k];
                        }
                    }
                }
            } // j

            return(toggle);
        }