/// <inheritdoc/>
 public new RealMatrix outerProduct(RealVector v)
 {
     if (v is ArrayRealVector)
     {
         double[]   vData = ((ArrayRealVector)v).data;
         int        m     = data.Length;
         int        n     = vData.Length;
         RealMatrix outp  = MatrixUtils.createRealMatrix(m, n);
         for (int i = 0; i < m; i++)
         {
             for (int j = 0; j < n; j++)
             {
                 outp.setEntry(i, j, data[i] * vData[j]);
             }
         }
         return(outp);
     }
     else
     {
         int        m    = data.Length;
         int        n    = v.getDimension();
         RealMatrix outp = MatrixUtils.createRealMatrix(m, n);
         for (int i = 0; i < m; i++)
         {
             for (int j = 0; j < n; j++)
             {
                 outp.setEntry(i, j, data[i] * v.getEntry(j));
             }
         }
         return(outp);
     }
 }
示例#2
0
        /// <summary>
        /// Returns the bi-diagonal matrix B of the transform.
        /// </summary>
        /// <returns>the B matrix</returns>
        public RealMatrix getB()
        {
            if (cachedB == null)
            {
                int        m  = householderVectors.Length;
                int        n  = householderVectors[0].Length;
                double[][] ba = new double[m][];
                for (int i = 0; i < main.Length; ++i)
                {
                    ba[i][i] = main[i];
                    if (m < n)
                    {
                        if (i > 0)
                        {
                            ba[i][i - 1] = secondary[i - 1];
                        }
                    }
                    else
                    {
                        if (i < main.Length - 1)
                        {
                            ba[i][i + 1] = secondary[i];
                        }
                    }
                }
                cachedB = MatrixUtils.createRealMatrix(ba);
            }

            // return the cached matrix
            return(cachedB);
        }
        /// <inheritdoc/>
        /// <exception cref="NumberIsTooLargeException"> if <c>m</c> is an
        /// <c>OpenMapRealMatrix</c>, and the total number of entries of the product
        /// is larger than <c>Int32.MaxValue</c>.</exception>
        public new RealMatrix multiply(RealMatrix m)
        {
            try
            {
                return(multiply((OpenMapRealMatrix)m));
            }
            catch (InvalidCastException)
            {
                MatrixUtils.checkMultiplicationCompatible(this, m);

                int             outCols = m.getColumnDimension();
                BlockRealMatrix outp    = new BlockRealMatrix(rows, outCols);
                for (OpenIntToDoubleHashMap.Iterator iterator = entries.iterator(); iterator.MoveNext();)
                {
                    double value = iterator.Current.Value;
                    int    key   = iterator.Current.Key;
                    int    i     = key / columns;
                    int    k     = key % columns;
                    for (int j = 0; j < outCols; ++j)
                    {
                        outp.addToEntry(i, j, value * m.getEntry(k, j));
                    }
                }
                return(outp);
            }
        }
        /// <inheritdoc/>
        public void copySubMatrix(int[] selectedRows, int[] selectedColumns, double[][] destination)
        {
            MatrixUtils.checkSubMatrixIndex(this, selectedRows, selectedColumns);
            int nCols = selectedColumns.Length;

            if ((destination.Length < selectedRows.Length) ||
                (destination[0].Length < nCols))
            {
                throw new MatrixDimensionMismatchException(destination.Length, destination[0].Length,
                                                           selectedRows.Length, selectedColumns.Length);
            }

            for (int i = 0; i < selectedRows.Length; i++)
            {
                double[] destinationI = destination[i];
                if (destinationI.Length < nCols)
                {
                    throw new MatrixDimensionMismatchException(destination.Length, destinationI.Length,
                                                               selectedRows.Length, selectedColumns.Length);
                }
                for (int j = 0; j < selectedColumns.Length; j++)
                {
                    destinationI[j] = getEntry(selectedRows[i], selectedColumns[j]);
                }
            }
        }
            /// <summary>
            /// Get the inverse of the decomposed matrix.
            /// </summary>
            /// <returns>the inverse matrix.</returns>
            /// <exception cref="SingularMatrixException"> if the decomposed matrix is singular.
            /// </exception>
            public RealMatrix getInverse()
            {
                if (!isNonSingular())
                {
                    throw new SingularMatrixException();
                }

                int m = realEigenvalues.Length;

                double[][] invData = new double[m][];

                for (int i = 0; i < m; ++i)
                {
                    double[] invI = invData[i];
                    for (int j = 0; j < m; ++j)
                    {
                        double invIJ = 0;
                        for (int k = 0; k < m; ++k)
                        {
                            double[] vK = eigenvectors[k].getDataRef();
                            invIJ += vK[i] * vK[j] / realEigenvalues[k];
                        }
                        invI[j] = invIJ;
                    }
                }
                return(MatrixUtils.createRealMatrix(invData));
            }
        /// <summary>
        /// Returns the Hessenberg matrix H of the transform.
        /// </summary>
        /// <returns>the H matrix</returns>
        public RealMatrix getH()
        {
            if (cachedH == null)
            {
                int        m = householderVectors.Length;
                double[][] h = new double[m][];
                for (int i = 0; i < m; ++i)
                {
                    if (i > 0)
                    {
                        // copy the entry of the lower sub-diagonal
                        h[i][i - 1] = householderVectors[i][i - 1];
                    }

                    // copy upper triangular part of the matrix
                    for (int j = i; j < m; ++j)
                    {
                        h[i][j] = householderVectors[i][j];
                    }
                }
                cachedH = MatrixUtils.createRealMatrix(h);
            }

            // return the cached matrix
            return(cachedH);
        }
示例#7
0
 /// <summary>
 /// Returns the matrix P of the transform.
 /// <para>P is an orthogonal matrix, i.e. its inverse is also its transpose.</para>
 /// </summary>
 /// <returns>the P matrix</returns>
 public RealMatrix getP()
 {
     if (cachedP == null)
     {
         cachedP = MatrixUtils.createRealMatrix(matrixP);
     }
     return(cachedP);
 }
 /// <summary>
 /// Returns the diagonal matrix &Sigma; of the decomposition.
 /// <para>&Sigma; is a diagonal matrix. The singular values are provided in
 /// non-increasing order, for compatibility with Jama.</para>
 /// </summary>
 /// <returns>the &Sigma; matrix</returns>
 public RealMatrix getS()
 {
     if (cachedS == null)
     {
         // cache the matrix for subsequent calls
         cachedS = MatrixUtils.createRealDiagonalMatrix(singularValues);
     }
     return(cachedS);
 }
示例#9
0
 /// <inheritdoc/>
 public new void multiplyEntry(int row, int column, double factor)
 {
     // we don't care about non-diagonal elements for multiplication
     if (row == column)
     {
         MatrixUtils.checkRowIndex(this, row);
         data[row] *= factor;
     }
 }
示例#10
0
        /// <summary>
        /// Returns the quasi-triangular Schur matrix T of the transform.
        /// </summary>
        /// <returns>the T matrix</returns>
        public RealMatrix getT()
        {
            if (cachedT == null)
            {
                cachedT = MatrixUtils.createRealMatrix(matrixT);
            }

            // return the cached matrix
            return(cachedT);
        }
        /// <inheritdoc/>
        public RealMatrix getSubMatrix(int[] selectedRows, int[] selectedColumns)
        {
            MatrixUtils.checkSubMatrixIndex(this, selectedRows, selectedColumns);

            RealMatrix subMatrix = createMatrix(selectedRows.Length, selectedColumns.Length);

            subMatrix.walkInOptimizedOrder(new DefaultRealMatrixChangingVisitorAnonymous1(ref selectedRows, ref selectedColumns, this));

            return(subMatrix);
        }
示例#12
0
        /// <summary>
        /// Returns the transpose of the matrix L of the decomposition.
        /// <para>L^T is an upper-triangular matrix</para>
        /// </summary>
        /// <returns>the transpose of the matrix L of the decomposition</returns>
        public RealMatrix getLT()
        {
            if (cachedLT == null)
            {
                cachedLT = MatrixUtils.createRealMatrix(lTData);
            }

            // return the cached matrix
            return(cachedLT);
        }
示例#13
0
 /// <inheritdoc/>
 /// <exception cref="NumberIsTooLargeException"> if <c>row != column</c> and increment is
 /// non-zero.</exception>
 public new void addToEntry(int row, int column, double increment)
 {
     if (row == column)
     {
         MatrixUtils.checkRowIndex(this, row);
         data[row] += increment;
     }
     else
     {
         ensureZero(increment);
     }
 }
示例#14
0
 /// <inheritdoc/>
 /// <exception cref="NumberIsTooLargeException"> if <c>row != column</c> and value is
 /// non-zero.</exception>
 public override void setEntry(int row, int column, double value)
 {
     if (row == column)
     {
         MatrixUtils.checkRowIndex(this, row);
         data[row] = value;
     }
     else
     {
         ensureZero(value);
     }
 }
        /// <inheritdoc/>
        public double[] getColumn(int column)
        {
            MatrixUtils.checkColumnIndex(this, column);
            int nRows = getRowDimension();

            double[] outp = new double[nRows];
            for (int i = 0; i < nRows; ++i)
            {
                outp[i] = getEntry(i, column);
            }

            return(outp);
        }
        /// <inheritdoc/>
        public RealMatrix getRowMatrix(int row)
        {
            MatrixUtils.checkRowIndex(this, row);
            int        nCols = getColumnDimension();
            RealMatrix outp  = createMatrix(1, nCols);

            for (int i = 0; i < nCols; ++i)
            {
                outp.setEntry(0, i, getEntry(row, i));
            }

            return(outp);
        }
        /// <inheritdoc/>
        public RealMatrix getColumnMatrix(int column)
        {
            MatrixUtils.checkColumnIndex(this, column);
            int        nRows = getRowDimension();
            RealMatrix outp  = createMatrix(nRows, 1);

            for (int i = 0; i < nRows; ++i)
            {
                outp.setEntry(i, 0, getEntry(i, column));
            }

            return(outp);
        }
 /// <inheritdoc/>
 public override void setEntry(int row, int column, double value)
 {
     MatrixUtils.checkRowIndex(this, row);
     MatrixUtils.checkColumnIndex(this, column);
     if (value == 0.0)
     {
         entries.remove(computeKey(row, column));
     }
     else
     {
         entries.put(computeKey(row, column), value);
     }
 }
        /// <inheritdoc/>
        public double[] getRow(int row)
        {
            MatrixUtils.checkRowIndex(this, row);
            int nCols = getColumnDimension();

            double[] outp = new double[nCols];
            for (int i = 0; i < nCols; ++i)
            {
                outp[i] = getEntry(row, i);
            }

            return(outp);
        }
示例#20
0
 /// <inheritdoc/>
 public new RealVector preMultiply(RealVector v)
 {
     double[] vectorData;
     if (v is ArrayRealVector)
     {
         vectorData = ((ArrayRealVector)v).getDataRef();
     }
     else
     {
         vectorData = v.toArray();
     }
     return(MatrixUtils.createRealVector(preMultiply(vectorData)));
 }
示例#21
0
        /// <summary>
        /// Returns the result of postmultiplying <c>this</c> by <c>m</c>.
        /// </summary>
        /// <param name="m">matrix to postmultiply by</param>
        /// <returns><c>this * m</c></returns>
        /// <exception cref="DimensionMismatchException"> if
        /// <c>columnDimension(this) != rowDimension(m)</c></exception>
        public DiagonalMatrix multiply(DiagonalMatrix m)
        {
            MatrixUtils.checkMultiplicationCompatible(this, m);

            int dim = getRowDimension();

            double[] outData = new double[dim];
            for (int i = 0; i < dim; i++)
            {
                outData[i] = data[i] * m.data[i];
            }

            return(new DiagonalMatrix(outData, false));
        }
示例#22
0
        /// <summary>
        /// Returns the matrix V of the transform.
        /// <para>V is an orthogonal matrix, i.e. its transpose is also its inverse.</para>
        /// </summary>
        /// <returns>the V matrix</returns>
        public RealMatrix getV()
        {
            if (cachedV == null)
            {
                int        m          = householderVectors.Length;
                int        n          = householderVectors[0].Length;
                int        p          = main.Length;
                int        diagOffset = (m >= n) ? 1 : 0;
                double[]   diagonal   = (m >= n) ? secondary : main;
                double[][] va         = new double[n][];

                // fill up the part of the matrix not affected by Householder transforms
                for (int k = n - 1; k >= p; --k)
                {
                    va[k][k] = 1;
                }

                // build up first part of the matrix by applying Householder transforms
                for (int k = p - 1; k >= diagOffset; --k)
                {
                    double[] hK = householderVectors[k - diagOffset];
                    va[k][k] = 1;
                    if (hK[k] != 0.0)
                    {
                        for (int j = k; j < n; ++j)
                        {
                            double beta = 0;
                            for (int i = k; i < n; ++i)
                            {
                                beta -= va[i][j] * hK[i];
                            }
                            beta /= diagonal[k - diagOffset] * hK[k];

                            for (int i = k; i < n; ++i)
                            {
                                va[i][j] += -beta * hK[i];
                            }
                        }
                    }
                }
                if (diagOffset > 0)
                {
                    va[0][0] = 1;
                }
                cachedV = MatrixUtils.createRealMatrix(va);
            }

            // return the cached matrix
            return(cachedV);
        }
示例#23
0
        /// <summary>
        /// Returns the matrix U of the transform.
        /// <para>U is an orthogonal matrix, i.e. its transpose is also its inverse.</para>
        /// </summary>
        /// <returns>the U matrix</returns>
        public RealMatrix getU()
        {
            if (cachedU == null)
            {
                int        m          = householderVectors.Length;
                int        n          = householderVectors[0].Length;
                int        p          = main.Length;
                int        diagOffset = (m >= n) ? 0 : 1;
                double[]   diagonal   = (m >= n) ? main : secondary;
                double[][] ua         = new double[m][];

                // fill up the part of the matrix not affected by Householder transforms
                for (int k = m - 1; k >= p; --k)
                {
                    ua[k][k] = 1;
                }

                // build up first part of the matrix by applying Householder transforms
                for (int k = p - 1; k >= diagOffset; --k)
                {
                    double[] hK = householderVectors[k];
                    ua[k][k] = 1;
                    if (hK[k - diagOffset] != 0.0)
                    {
                        for (int j = k; j < m; ++j)
                        {
                            double alpha = 0;
                            for (int i = k; i < m; ++i)
                            {
                                alpha -= ua[i][j] * householderVectors[i][k - diagOffset];
                            }
                            alpha /= diagonal[k - diagOffset] * hK[k - diagOffset];

                            for (int i = k; i < m; ++i)
                            {
                                ua[i][j] += -alpha * householderVectors[i][k - diagOffset];
                            }
                        }
                    }
                }
                if (diagOffset > 0)
                {
                    ua[0][0] = 1;
                }
                cachedU = MatrixUtils.createRealMatrix(ua);
            }

            // return the cached matrix
            return(cachedU);
        }
 /// <summary>
 /// Gets the matrix V of the decomposition.
 /// V is an orthogonal matrix, i.e. its transpose is also its inverse.
 /// The columns of V are the eigenvectors of the original matrix.
 /// No assumption is made about the orientation of the system axes formed
 /// by the columns of V (e.g. in a 3-dimension space, V can form a left-
 /// or right-handed system).
 /// </summary>
 /// <returns>the V matrix.</returns>
 public RealMatrix getV()
 {
     if (cachedV == null)
     {
         int m = eigenvectors.Length;
         cachedV = MatrixUtils.createRealMatrix(m, m);
         for (int k = 0; k < m; ++k)
         {
             cachedV.setColumnVector(k, eigenvectors[k]);
         }
     }
     // return the cached matrix
     return(cachedV);
 }
示例#25
0
 /// <inheritdoc/>
 public new double walkInColumnOrder(RealMatrixPreservingVisitor visitor, int startRow, int endRow, int startColumn, int endColumn)
 {
     MatrixUtils.checkSubMatrixIndex(this, startRow, endRow, startColumn, endColumn);
     visitor.start(getRowDimension(), getColumnDimension(),
                   startRow, endRow, startColumn, endColumn);
     for (int j = startColumn; j <= endColumn; ++j)
     {
         for (int i = startRow; i <= endRow; ++i)
         {
             visitor.visit(i, j, data[i][j]);
         }
     }
     return(visitor.end());
 }
        /// <inheritdoc/>
        public void setColumn(int column, double[] array)
        {
            MatrixUtils.checkColumnIndex(this, column);
            int nRows = getRowDimension();

            if (array.Length != nRows)
            {
                throw new MatrixDimensionMismatchException(array.Length, 1, nRows, 1);
            }
            for (int i = 0; i < nRows; ++i)
            {
                setEntry(i, column, array[i]);
            }
        }
        /// <inheritdoc/>
        public void setRow(int row, double[] array)
        {
            MatrixUtils.checkRowIndex(this, row);
            int nCols = getColumnDimension();

            if (array.Length != nCols)
            {
                throw new MatrixDimensionMismatchException(1, array.Length, 1, nCols);
            }
            for (int i = 0; i < nCols; ++i)
            {
                setEntry(row, i, array[i]);
            }
        }
 /// <inheritdoc/>
 public double walkInColumnOrder(RealMatrixPreservingVisitor visitor, int startRow, int endRow, int startColumn, int endColumn)
 {
     MatrixUtils.checkSubMatrixIndex(this, startRow, endRow, startColumn, endColumn);
     visitor.start(getRowDimension(), getColumnDimension(),
                   startRow, endRow, startColumn, endColumn);
     for (int column = startColumn; column <= endColumn; ++column)
     {
         for (int row = startRow; row <= endRow; ++row)
         {
             visitor.visit(row, column, getEntry(row, column));
         }
     }
     return(visitor.end());
 }
        /// <summary>
        /// Returns the matrix P of the transform.
        /// <para>P is an orthogonal matrix, i.e. its inverse is also its transpose.</para>
        /// </summary>
        /// <returns>the P matrix</returns>
        public RealMatrix getP()
        {
            if (cachedP == null)
            {
                int        n    = householderVectors.Length;
                int        high = n - 1;
                double[][] pa   = new double[n][];

                for (int i = 0; i < n; i++)
                {
                    for (int j = 0; j < n; j++)
                    {
                        pa[i][j] = (i == j) ? 1 : 0;
                    }
                }

                for (int m = high - 1; m >= 1; m--)
                {
                    if (householderVectors[m][m - 1] != 0.0)
                    {
                        for (int i = m + 1; i <= high; i++)
                        {
                            ort[i] = householderVectors[i][m - 1];
                        }

                        for (int j = m; j <= high; j++)
                        {
                            double g = 0.0;

                            for (int i = m; i <= high; i++)
                            {
                                g += ort[i] * pa[i][j];
                            }

                            // Double division avoids possible underflow
                            g = (g / ort[m]) / householderVectors[m][m - 1];

                            for (int i = m; i <= high; i++)
                            {
                                pa[i][j] += g * ort[i];
                            }
                        }
                    }
                }

                cachedP = MatrixUtils.createRealMatrix(pa);
            }
            return(cachedP);
        }
示例#30
0
        /// <summary>
        /// Compute the sum of <c>this</c> and <c>m</c>.
        /// </summary>
        /// <param name="m">Matrix to be added.</param>
        /// <returns><c>this + m</c>.</returns>
        /// <exception cref="MatrixDimensionMismatchException"> if <c>m</c> is not the same
        /// size as <c>this</c>.</exception>
        public DiagonalMatrix add(DiagonalMatrix m)
        {
            // Safety check.
            MatrixUtils.checkAdditionCompatible(this, m);

            int dim = getRowDimension();

            double[] outData = new double[dim];
            for (int i = 0; i < dim; i++)
            {
                outData[i] = data[i] + m.data[i];
            }

            return(new DiagonalMatrix(outData, false));
        }