C# QR Decomp Example

← All NMath Code Examples

 

using System;

using CenterSpace.NMath.Core;
using CenterSpace.NMath.Matrix;

namespace CenterSpace.NMath.Matrix.Examples.CSharp
{
  /// <summary>
  /// A .NET example in C# demonstrating the features of the QR decomposition classes.
  /// </summary>
  class QRDecompExample
  {

    static void Main( string[] args )
    {
      // A general m x n system with random entries.
      var rng = new RandGenUniform( -1, 1 );
      rng.Reset( 0x124 );
      int rows = 6;
      int cols = 3;
      var A = new DoubleMatrix( rows, cols, rng );

      // Construct a QR decomposition of A.
      var decomp = new DoubleQRDecomp( A );

      Console.WriteLine();

      // Look at the components of the factorization AP = QR.
      Console.WriteLine( "Q =" );
      Console.WriteLine( decomp.Q.ToTabDelimited( "G3" ) );

      Console.WriteLine( "R =" );
      Console.WriteLine( decomp.R.ToTabDelimited( "G3" ) );

      Console.WriteLine( "P =" );
      Console.WriteLine( decomp.P.ToTabDelimited() );

      // Q =
      // -0.187  0.516   0.0534
      // 0.0654  -0.362  0.0361
      // 0.142   0.331   -0.428
      // 0.22    -0.597  -0.507
      // 0.784   0.0122  0.56
      // -0.527  -0.37   0.492

      // R =
      // -1.18   0.264   0.183
      // 0       -0.869  -0.0966
      // 0       0       0.745

      // P =
      // 0       1       0
      // 0       0       1
      // 1       0       0

      // Usually, you do not need to access the components of the 
      // decomposition explicitly. There are member functions for
      // multiplying by the decomposition components without 
      // explicitly constructing them. As an example, let's solve
      // the least squares problem Ax = b using a QR decomposition.
      // To do this we write A = QR, compute the vector QTb 
      // (QT is the transpose of the matrix Q), and solve the upper-
      // triangular system Rx = QTb for x. (NOTE: the NMath Matrix library
      // contains class DoubleQRLeastSq for solving least squares problems
      // using a QR decomposition).
      var b = new DoubleVector( A.Rows, rng );
      DoubleVector w = decomp.QTx( b );
      DoubleVector x = decomp.Px( decomp.RInvx( w ) );

      Console.WriteLine( "Least squares solution =" );
      Console.WriteLine( x.ToString() );

      // Note that we had to multiply by the permutation matrix to 
      // get the components of the solution back in the right order
      // since pivoting was done.
      //
      // Suppose that you wanted to compute a QR decomposition without pivoting.
      // The class DoubleQRDecompServer provides control over the pivoting 
      // strategy used by the QR decomposition algorithm.
      var decompServer = new DoubleQRDecompServer();
      decompServer.Pivoting = false;

      // Use the server to get a decomposition that was computed without pivoting.
      decomp = decompServer.GetDecomp( A );

      // The permutation matrix should be I, the identity matrix.
      Console.WriteLine();
      Console.WriteLine( "P with no pivoting =" );
      Console.WriteLine(decomp.P.ToTabDelimited() );

      // Use the decomposition to solve the least squares problem again. This
      // time we do not need to multiply by P.
      w = decomp.QTx( b );
      x = decomp.RInvx( w );

      Console.WriteLine( "Least squares solution, no pivoting =" );
      Console.WriteLine( x.ToString() );

      // You can also set the columns of A to be 'initial' columns. If the ith column
      // of A is set to be an initial column, it is moved to the beginning of AP 
      // before the computation, and fixed in place during the computation. If a 
      // column of A is set to be a 'free' column, it may be interchanged during the
      // computation with any other free column.
      decompServer.SetInitialColumn( 0 ); // Do not move the first column of A.
      decomp = decompServer.GetDecomp( A );
      decompServer.SetFreeColumn( 0 ); // Set the first column back to a free column.

      Console.WriteLine();
      Console.WriteLine( "Press Enter Key" );
      Console.Read();
    }
  }
}

← All NMath Code Examples
Top