Ejemplo n.º 1
0
 public static void printmatrix(MatDoub a)
 {
     for (int i = 0; i < a.nrows(); i++)
     {
         for (int j = 0; j < a.ncols(); j++)
         {
             System.Console.Write(a[i][j] + ",");
         }
         System.Console.WriteLine();
     }
     System.Console.WriteLine();
 }
Ejemplo n.º 2
0
        /// <summary>
        /// Constructor.  The single argument is A.  The SVD computation is done by
        /// decompose(), and the results are sorted by reorder().
        /// </summary>
        /// <param name="a">The matrix to decompose.</param>

        public SVD(MatDoub a)
        {
            m   = (a.nrows());
            n   = (a.ncols());
            u   = new MatDoub(a);
            v   = new MatDoub(n, n);
            w   = new VecDoub(n);
            eps = double.Epsilon;
            decompose();
            reorder();
            tsh = 0.5 * Math.Sqrt(m + n + 1.0) * w[0] * eps; // Default threshold for nonzero singular values;
        }
Ejemplo n.º 3
0
        /// <summary>
        /// Solve m sets of n equations AX=B using the pseudoinverse of A.
        /// The right-hand sides are input as b[0..n-1][0..m-1], while
        /// x[0..n-1][0..m-1] return the solutions.
        /// If positive, thresh is the threshold value below which singular values
        /// as considered to be zero.  If thresh is negative, a default based on rounodd error is used.
        /// </summary>
        /// <param name="b"></param>
        /// <param name="x"></param>
        /// <param name="thresh"></param>

        //void solve(MatDoub_I &b, MatDoub_O &x, double thresh);
        public void solve(MatDoub b, MatDoub x, double thresh)
        {
            int i, j, m = b.ncols();

            if (b.nrows() != n || x.nrows() != n || b.ncols() != x.ncols())
            {
                throw new Exception("SVD::solve bad sizes");
            }
            VecDoub xx = new VecDoub(n);

            for (j = 0; j < m; j++)
            {
                for (i = 0; i < n; i++)
                {
                    xx[i] = b[i][j];
                }
                solve(xx, xx, thresh);
                for (i = 0; i < n; i++)
                {
                    x[i][j] = xx[i];
                }
            }
        }
Ejemplo n.º 4
0
        public static void gaussj(MatDoub a, MatDoub b)
        {
            // Linear equation solution by Gauss-Jordan elimination,
            // equation (2.1.1) above. The input matrix is a[0..n-1][0..n-1].
            // b[0..n-1][0..m-1] is input containing the m right-hand side vectors.
            // On output, a is replaced by its matrix inverse, and b is replaced by
            // the corresponding set of solution vectors.
            int    i, icol = 0, irow = 0, j, k, l, ll, n = a.nrows(), m = a.ncols();
            double big, dum, pivinv;
            VecInt indxc = new VecInt(n);
            VecInt indxr = new VecInt(n);
            VecInt ipiv  = new VecInt(n); // These integer arrays are used

            // for bookkeeping on the pivoting.
            for (j = 0; j < n; j++)
            {
                ipiv[j] = 0;
            }
            for (i = 0; i < n; i++) // This is the main loop over the columns to
                                    // be
            {
                big = 0.0;          // reduced.
                for (j = 0; j < n; j++)
                {
                    // This is the outer loop of the search for a pivot over the entire matrix!
                    if (ipiv[j] != 1) // element.
                    {
                        for (k = 0; k < n; k++)
                        {
                            if (ipiv[k] == 0)
                            {
                                if (Math.Abs(a[j][k]) >= big)
                                {
                                    big  = Math.Abs(a[j][k]);
                                    irow = j;
                                    icol = k;
                                }
                            }
                        }
                    }
                }
                ++(ipiv[icol]);
                // We now have the pivot element, so we interchange rows, if needed,
                // to put the pivot element on the diagonal. The columns are not
                // physically interchanged, only relabeled: indxc[i], the column of the .iC1/th
                // pivot element, is the .iC1/th column that is reduced, while indxr[i] is
                // the row in which that pivot element was originally located.
                // If indxr[i] indxc[i], there is an implied column interchange.
                // With this form of bookkeeping, the solution bs will end up in the
                // correct order, and the inverse matrix will be scrambled by columns.
                if (irow != icol)
                {
                    for (l = 0; l < n; l++)
                    {
                        NR.SWAP(a, irow, l, icol, l);
                    }
                    for (l = 0; l < m; l++)
                    {
                        NR.SWAP(b, irow, l, icol, l);
                    }
                }
                indxr[i] = irow; // We are now ready to divide the pivot row by the
                // pivot element, located at irow and icol.
                indxc[i] = icol;
                if (a[icol][icol] == 0.0)
                {
                    throw new Exception("gaussj: Singular Matrix");
                }
                pivinv        = 1.0 / a[icol][icol];
                a[icol][icol] = 1.0;
                for (l = 0; l < n; l++)
                {
                    a[icol][l] *= pivinv;
                }
                for (l = 0; l < m; l++)
                {
                    b[icol][l] *= pivinv;
                }
                for (ll = 0; ll < n; ll++)
                {
                    // Next, we reduce the rows...
                    if (ll != icol)
                    { // ...except for the pivot one, of course.
                        dum         = a[ll][icol];
                        a[ll][icol] = 0.0;
                        for (l = 0; l < n; l++)
                        {
                            a[ll][l] -= a[icol][l] * dum;
                        }
                        for (l = 0; l < m; l++)
                        {
                            b[ll][l] -= b[icol][l] * dum;
                        }
                    }
                }
            }
            // This is the end of the main loop over columns of the reduction. It
            // only remains to unscramble the solution in view of the column
            // interchanges. We do this by interchanging pairs of columns in the
            // reverse order that the permutation was built up.
            for (l = n - 1; l >= 0; l--)
            {
                if (indxr[l] != indxc[l])
                {
                    for (k = 0; k < n; k++)
                    {
                        NR.SWAP(a, k, indxr[l], k, indxc[l]);
                    }
                }
            }
        }