/// <summary>
        /// Explicitly creates the orthogonal matrix Q that resulted from the factorization: A = L * Q, where A is m-by-n,
        /// L is m-by-n and Q is n-by-n.
        /// This method is safe to use as the factorization data are copied (if necessary). However, it is inefficient if the
        /// generated matrix is only used once.
        /// </summary>
        public Matrix GetFactorQ()
        {
            if (NumRows > NumColumns)
            {
                throw new NotImplementedException("For now, the number of rows must be <= the number of columns");
            }

            // We need a larger buffer for Q (n-by-n) > reflectorsAndL (p-by-n)
            double[] matrixQ = ArrayColMajor.IncreaseRows(NumRows, NumColumns, NumColumns, reflectorsAndL);

            // Call LAPACK
            int numColsQ      = NumColumns;
            int numRowsQ      = numColsQ;
            int numReflectors = NumRows;
            int leadingDimQ   = numRowsQ;

            LapackLeastSquares.Dorglq(numRowsQ, numColsQ, numReflectors, matrixQ, 0, leadingDimQ, reflectorScalars, 0);
            return(Matrix.CreateFromArray(matrixQ, NumColumns, NumColumns, false));
        }
        /// <summary>
        /// Explicitly creates the orthogonal matrix Q that resulted from the factorization: A = Q * R, where A is m-by-n,
        /// Q is m-by-m and R is m-by-n.
        /// This method is safe to use as the factorization data are copied (if necessary). However, it is inefficient if the
        /// generated matrix is only used once.
        /// </summary>
        public Matrix GetFactorQ()
        {
            if (NumRows < NumColumns)
            {
                throw new NotImplementedException("For now, the number of rows must be >= the number of columns");
            }

            // We need a larger buffer for Q (m-by-m) > reflectorsAndR (m-by-p)
            double[] matrixQ = ArrayColMajor.ResizeCols(NumRows, NumColumns, NumRows, reflectorsAndR);

            // Call Lapack
            int numRowsQ      = NumRows;
            int numColsQ      = numRowsQ;
            int numReflectors = NumColumns;
            int leadingDimQ   = numRowsQ;

            LapackLeastSquares.Dorgqr(numRowsQ, numColsQ, numReflectors, matrixQ, 0, leadingDimQ, reflectorScalars, 0);

            return(Matrix.CreateFromArray(matrixQ, NumRows, NumRows, false));
        }