コード例 #1
0
void cisstAlgorithmICP_IMLP::ComputeCovDecomposition_SVD( const vct3x3 &M, vct3x3 &Minv, double &det_M )
{
  // Compute SVD of M
  static vctFixedSizeMatrix<double,3,3,VCT_COL_MAJOR> A;
  static vctFixedSizeMatrix<double,3,3,VCT_COL_MAJOR> U;
  static vctFixedSizeMatrix<double,3,3,VCT_COL_MAJOR> Vt;
  static vct3 S;
  static nmrSVDFixedSizeData<3,3,VCT_COL_MAJOR>::VectorTypeWorkspace workspace;
  try 
  {
    A.Assign(M);
    nmrSVD(A, U, S, Vt, workspace);
  }
  catch(...) 
  { assert(0); }

  // Compute Minv
  //   M = U*diag(S)*V'   where U = V
  //   Minv = V*diag(1/S)*U' = U*diag(1/S)*V'
  static vctFixedSizeMatrix<double,3,3,VCT_COL_MAJOR> Sinv_Ut;
  static vct3 Sinv;
  Sinv[0] = 1/S[0];
  Sinv[1] = 1/S[1];
  Sinv[2] = 1/S[2];
  Sinv_Ut.Row(0) = Sinv[0]*Vt.Row(0);
  Sinv_Ut.Row(1) = Sinv[1]*Vt.Row(1);
  Sinv_Ut.Row(2) = Sinv[2]*Vt.Row(2);
  Minv.Assign(U*Sinv_Ut);

  // Compute determinant of M
  det_M = S[0]*S[1]*S[2];
}
コード例 #2
0
ファイル: vctDeterminantTest.cpp プロジェクト: Shuyoung/cisst
void vctDeterminantTest::TestDeterminant2x2ByInverse(const vctFixedSizeMatrix<ElementType, 2, 2> & inputMatrix)
{
    const ElementType determinant = vctDeterminant<2>::Compute(inputMatrix);

    const ElementType tolerance = cmnTypeTraits<ElementType>::Tolerance();

    if (fabs(determinant) < tolerance) {
        vctFixedSizeVector<ElementType, 2> rowRatio;
        rowRatio.ElementwiseRatioOf( inputMatrix.Row(0), inputMatrix.Row(1) );
        CPPUNIT_ASSERT_DOUBLES_EQUAL( rowRatio[0], rowRatio[1], tolerance );

        vctFixedSizeVector<ElementType, 2> columnRatio;
        columnRatio.ElementwiseRatioOf( inputMatrix.Column(0), inputMatrix.Column(1) );
        CPPUNIT_ASSERT_DOUBLES_EQUAL( columnRatio[0], columnRatio[1], tolerance );

        return;
    }

    const vctFixedSizeMatrix<ElementType, 2, 2> inverse(
        inputMatrix[1][1] / determinant, -inputMatrix[0][1] / determinant,
        -inputMatrix[1][0] / determinant, inputMatrix[0][0] / determinant
        );

    /* gcc (Ubuntu 4.4.3-4ubuntu5) 4.4.3 crashes with internal error
       on ubuntu 64 - Ubuntu 10.04.1 LTS with const */
    /* const */ vctFixedSizeMatrix<ElementType, 2, 2> product( inputMatrix * inverse );
    const vctFixedSizeMatrix<ElementType, 2, 2> identity( ElementType(1), ElementType(0), ElementType(0), ElementType(1) );
    const vctFixedSizeMatrix<ElementType, 2, 2> difference = product - identity;
    ElementType diffNorm = difference.Norm();
    CPPUNIT_ASSERT_DOUBLES_EQUAL( 0, diffNorm, tolerance );
}
コード例 #3
0
void cisstAlgorithmICP_IMLP::ComputeCovDecomposition_NonIter(const vct3x3 &M, vct3x3 &Minv, vct3x3 &N, vct3x3 &Ninv, double &det_M)
{
  // Compute eigen decomposition of M
  //   M = V*diag(S)*V'
  vct3    eigenValues;
  vct3x3  eigenVectors;
  ComputeCovEigenDecomposition_NonIter(M, eigenValues, eigenVectors);

  // Compute Minv
  //   Minv = V*diag(1/S)*V'
  static vctFixedSizeMatrix<double, 3, 3, VCT_COL_MAJOR> V_Sinv;
  static vct3 Sinv;
  Sinv[0] = 1.0 / eigenValues[0];
  Sinv[1] = 1.0 / eigenValues[1];
  Sinv[2] = 1.0 / eigenValues[2];
  V_Sinv.Column(0) = eigenVectors.Column(0)*Sinv[0];
  V_Sinv.Column(1) = eigenVectors.Column(1)*Sinv[1];
  V_Sinv.Column(2) = eigenVectors.Column(2)*Sinv[2];
  Minv.Assign(V_Sinv * eigenVectors.TransposeRef());

  // Compute Decomposition of Minv = N'*N
  //   Minv = R*D^2*R' = N'*N     M = R*Dinv^2*R' => R' = V', Dinv = sqrt(S)
  //   N = D*R'      Ninv = R*inv(D)
  vct3 Dinv(
    sqrt(eigenValues[0]),
    sqrt(eigenValues[1]),
    sqrt(eigenValues[2])
    );
  N.Row(0) = eigenVectors.Column(0) / Dinv[0];
  N.Row(1) = eigenVectors.Column(1) / Dinv[1];
  N.Row(2) = eigenVectors.Column(2) / Dinv[2];
  Ninv.Column(0) = eigenVectors.Column(0)*Dinv[0];
  Ninv.Column(1) = eigenVectors.Column(1)*Dinv[1];
  Ninv.Column(2) = eigenVectors.Column(2)*Dinv[2];
  
  // Compute determinant of M
  det_M = eigenValues.ProductOfElements();
}
コード例 #4
0
void cisstAlgorithmICP_IMLP::ComputeCovDecomposition_NonIter(const vct3x3 &M, vct3x3 &Minv, double &det_M)
{
  // Compute eigen decomposition of M
  //   M = V*diag(S)*V'
  vct3    eigenValues;
  vct3x3  eigenVectors;
  ComputeCovEigenDecomposition_NonIter(M, eigenValues, eigenVectors);

  // Compute Minv
  //   Minv = V*diag(1/S)*V'
  static vctFixedSizeMatrix<double, 3, 3, VCT_COL_MAJOR> V_Sinv;
  static vct3 Sinv;
  Sinv[0] = 1.0 / eigenValues[0];
  Sinv[1] = 1.0 / eigenValues[1];
  Sinv[2] = 1.0 / eigenValues[2];
  V_Sinv.Column(0) = eigenVectors.Column(0)*Sinv[0];
  V_Sinv.Column(1) = eigenVectors.Column(1)*Sinv[1];
  V_Sinv.Column(2) = eigenVectors.Column(2)*Sinv[2];
  Minv.Assign(V_Sinv * eigenVectors.TransposeRef());

  // compute determinant of M
  det_M = eigenValues.ProductOfElements();
}
コード例 #5
0
void cisstAlgorithmICP_IMLP::ComputeCovDecomposition_SVD( const vct3x3 &M, vct3x3 &Minv, 
                                                      vct3x3 &N, vct3x3 &Ninv, double &det_M )
{
  // Compute SVD of M
  static vctFixedSizeMatrix<double,3,3,VCT_COL_MAJOR> A;
  static vctFixedSizeMatrix<double,3,3,VCT_COL_MAJOR> U;
  static vctFixedSizeMatrix<double,3,3,VCT_COL_MAJOR> Vt;
  static vct3 S;
  static nmrSVDFixedSizeData<3,3,VCT_COL_MAJOR>::VectorTypeWorkspace workspace;
  try 
  {
    A.Assign(M);
    nmrSVD(A, U, S, Vt, workspace);
  }
  catch(...) 
  { assert(0); }

  // Compute Minv
  //   M = U*diag(S)*V'   where U = V
  //   Minv = V*diag(1/S)*U' = U*diag(1/S)*V'
  static vctFixedSizeMatrix<double,3,3,VCT_COL_MAJOR> Sinv_Ut;
  static vct3 Sinv;
  Sinv[0] = 1/S[0];
  Sinv[1] = 1/S[1];
  Sinv[2] = 1/S[2];
  Sinv_Ut.Row(0) = Sinv[0]*Vt.Row(0);
  Sinv_Ut.Row(1) = Sinv[1]*Vt.Row(1);
  Sinv_Ut.Row(2) = Sinv[2]*Vt.Row(2);
  Minv.Assign(U*Sinv_Ut);

  // Compute Decomposition of Minv = N'*N
  //   Minv = R*D^2*R' = N'*N
  //   N = D*R'
  //   Ninv = R*inv(D)
  static vct3 Dinv; //,D;
  Dinv[0] = sqrt(S[0]);
  Dinv[1] = sqrt(S[1]);
  Dinv[2] = sqrt(S[2]);
  //D[0] = 1/Dinv[0];
  //D[1] = 1/Dinv[1];
  //D[2] = 1/Dinv[2];
  //N.Row(0) = D[0]*Vt.Row(0);
  //N.Row(1) = D[1]*Vt.Row(1);
  //N.Row(2) = D[2]*Vt.Row(2);
  N.Row(0) = Vt.Row(0)/Dinv[0];
  N.Row(1) = Vt.Row(1)/Dinv[1];
  N.Row(2) = Vt.Row(2)/Dinv[2];
  Ninv.Column(0) = U.Column(0)*Dinv[0];
  Ninv.Column(1) = U.Column(1)*Dinv[1];
  Ninv.Column(2) = U.Column(2)*Dinv[2];
  
  // Compute determinant of M
  det_M = S[0]*S[1]*S[2];
}