org.ejml.alg.dense.decomposition.svd.implicitqr
Class SvdImplicitQrAlgorithm

java.lang.Object
  extended by org.ejml.alg.dense.decomposition.svd.implicitqr.SvdImplicitQrAlgorithm

public class SvdImplicitQrAlgorithm
extends Object

Computes the QR decomposition of a bidiagonal matrix. Internally this matrix is stored as two arrays. Shifts can either be provided to it or it can generate the shifts on its own. It optionally computes the U and V matrices. This comparability allows it to be used to compute singular values and associated matrices efficiently.

A = U*S*VT
where A is the original m by n matrix.

Based off of the outline provided in:

David S. Watkins, "Fundamentals of Matrix Computations," Second Edition. Page 404-411

Note: To watch it process the matrix step by step uncomment commented out code.

Author:
Peter Abeles

Field Summary
protected  double[] diag
           
protected  EigenvalueSmall eigenSmall
           
protected  double maxValue
           
protected  int N
           
protected  int nextExceptional
           
protected  int numExceptional
           
protected  int numSplits
           
protected  double[] off
           
protected  Random rand
           
protected  int[] splits
           
protected  int totalSteps
           
protected  DenseMatrix64F Ut
           
protected  DenseMatrix64F Vt
           
protected  int x1
           
protected  int x2
           
 
Constructor Summary
SvdImplicitQrAlgorithm()
           
SvdImplicitQrAlgorithm(boolean fastValues)
           
 
Method Summary
 boolean _process()
           
protected  boolean checkForAndHandleZeros()
          Checks to see if either the diagonal element or off diagonal element is zero.
protected  void computeRotator(double rise, double run)
          Computes a rotator that will set run to zero (?)
protected  void createBulge(int x1, double p, double scale, boolean byAngle)
          Performs a similar transform on BTB-pI
protected  void eigenBB_2x2(int x1)
          Computes the eigenvalue of the 2 by 2 matrix BTB
 void exceptionShift()
          It is possible for the QR algorithm to get stuck in a loop because of symmetries.
 double[] getDiag()
           
 double getMaxValue()
           
 int getNumberOfSingularValues()
           
 double[] getOff()
           
 double getSingularValue(int index)
           
 double[] getSingularValues()
           
 DenseMatrix64F getUt()
           
 DenseMatrix64F getVt()
           
 void incrementSteps()
           
 void initParam(int M, int N)
           
 boolean isDiagonalZero(int i)
           
 boolean isOffZero(int i)
           
 boolean nextSplit()
          Tells it to process the submatrix at the next split.
 void performImplicitSingleStep(double scale, double lambda, boolean byAngle)
          Given the lambda value perform an implicit QR step on the matrix.
 void printMatrix()
           
 boolean process()
           
 boolean process(double[] values)
          Perform a sequence of steps based off of the singular values provided.
protected  void removeBulgeLeft(int x1, boolean notLast)
           
protected  void removeBulgeRight(int x1)
           
 void resetSteps()
           
 double selectWilkinsonShift(double scale)
          Selects the Wilkinson's shift for BTB.
 void setFastValues(boolean b)
           
 void setMatrix(int numRows, int numCols, double[] diag, double[] off)
           
 void setMaxValue(double maxValue)
           
 void setSubmatrix(int x1, int x2)
           
 void setUt(DenseMatrix64F ut)
           
 void setVt(DenseMatrix64F vt)
           
 double[] swapDiag(double[] diag)
           
 double[] swapOff(double[] off)
           
protected  void updateRotator(DenseMatrix64F Q, int m, int n, double c, double s)
          Multiplied a transpose orthogonal matrix Q by the specified rotator.
 
Methods inherited from class java.lang.Object
clone, equals, finalize, getClass, hashCode, notify, notifyAll, toString, wait, wait, wait
 

Field Detail

rand

protected Random rand

Ut

protected DenseMatrix64F Ut

Vt

protected DenseMatrix64F Vt

totalSteps

protected int totalSteps

maxValue

protected double maxValue

N

protected int N

eigenSmall

protected EigenvalueSmall eigenSmall

numExceptional

protected int numExceptional

nextExceptional

protected int nextExceptional

diag

protected double[] diag

off

protected double[] off

x1

protected int x1

x2

protected int x2

splits

protected int[] splits

numSplits

protected int numSplits
Constructor Detail

SvdImplicitQrAlgorithm

public SvdImplicitQrAlgorithm(boolean fastValues)

SvdImplicitQrAlgorithm

public SvdImplicitQrAlgorithm()
Method Detail

getUt

public DenseMatrix64F getUt()

setUt

public void setUt(DenseMatrix64F ut)

getVt

public DenseMatrix64F getVt()

setVt

public void setVt(DenseMatrix64F vt)

setMatrix

public void setMatrix(int numRows,
                      int numCols,
                      double[] diag,
                      double[] off)

swapDiag

public double[] swapDiag(double[] diag)

swapOff

public double[] swapOff(double[] off)

setMaxValue

public void setMaxValue(double maxValue)

initParam

public void initParam(int M,
                      int N)

process

public boolean process()

process

public boolean process(double[] values)
Perform a sequence of steps based off of the singular values provided.

Parameters:
values -
Returns:

_process

public boolean _process()

incrementSteps

public void incrementSteps()

isOffZero

public boolean isOffZero(int i)

isDiagonalZero

public boolean isDiagonalZero(int i)

resetSteps

public void resetSteps()

nextSplit

public boolean nextSplit()
Tells it to process the submatrix at the next split. Should be called after the current submatrix has been processed.


performImplicitSingleStep

public void performImplicitSingleStep(double scale,
                                      double lambda,
                                      boolean byAngle)
Given the lambda value perform an implicit QR step on the matrix. B^T*B-lambda*I

Parameters:
lambda - Stepping factor.

updateRotator

protected void updateRotator(DenseMatrix64F Q,
                             int m,
                             int n,
                             double c,
                             double s)
Multiplied a transpose orthogonal matrix Q by the specified rotator. This is used to update the U and V matrices. Updating the transpose of the matrix is faster since it only modifies the rows.

Parameters:
Q - Orthogonal matrix
m - Coordinate of rotator.
n - Coordinate of rotator.
c - cosine of rotator.
s - sine of rotator.

createBulge

protected void createBulge(int x1,
                           double p,
                           double scale,
                           boolean byAngle)
Performs a similar transform on BTB-pI


computeRotator

protected void computeRotator(double rise,
                              double run)
Computes a rotator that will set run to zero (?)


removeBulgeLeft

protected void removeBulgeLeft(int x1,
                               boolean notLast)

removeBulgeRight

protected void removeBulgeRight(int x1)

setSubmatrix

public void setSubmatrix(int x1,
                         int x2)

selectWilkinsonShift

public double selectWilkinsonShift(double scale)
Selects the Wilkinson's shift for BTB. See page 410. It is guaranteed to converge and converges fast in practice.

Parameters:
scale - Scale factor used to help prevent overflow/underflow
Returns:
Shifting factor lambda/(scale*scale)

eigenBB_2x2

protected void eigenBB_2x2(int x1)
Computes the eigenvalue of the 2 by 2 matrix BTB


checkForAndHandleZeros

protected boolean checkForAndHandleZeros()
Checks to see if either the diagonal element or off diagonal element is zero. If one is then it performs a split or pushes it off the matrix.

Returns:
True if there was a zero.

exceptionShift

public void exceptionShift()
It is possible for the QR algorithm to get stuck in a loop because of symmetries. This happens more often with larger matrices. By taking a random step it can break the symmetry and finish.


printMatrix

public void printMatrix()

getNumberOfSingularValues

public int getNumberOfSingularValues()

getSingularValue

public double getSingularValue(int index)

setFastValues

public void setFastValues(boolean b)

getSingularValues

public double[] getSingularValues()

getDiag

public double[] getDiag()

getOff

public double[] getOff()

getMaxValue

public double getMaxValue()


Copyright © 2012. All Rights Reserved.