diff --git a/.cproject b/.cproject index f5bfad029..84dece771 100644 --- a/.cproject +++ b/.cproject @@ -390,6 +390,7 @@ make + testErrors.run true false @@ -509,6 +510,7 @@ make + testBayesTree.run true false @@ -516,6 +518,7 @@ make + testBinaryBayesNet.run true false @@ -563,6 +566,7 @@ make + testSymbolicBayesNet.run true false @@ -570,6 +574,7 @@ make + testSymbolicFactor.run true false @@ -577,6 +582,7 @@ make + testSymbolicFactorGraph.run true false @@ -656,7 +662,6 @@ make - testGraph.run true false @@ -752,7 +757,6 @@ make - testInference.run true false @@ -760,7 +764,6 @@ make - testGaussianBayesNet.run true false @@ -768,7 +771,6 @@ make - testGaussianFactor.run true false @@ -776,7 +778,6 @@ make - testJunctionTree.run true false @@ -784,7 +785,6 @@ make - testSymbolicBayesNet.run true false @@ -792,7 +792,6 @@ make - testSymbolicFactorGraph.run true false @@ -1008,7 +1007,6 @@ make - testSimulated2DOriented.run true false @@ -1048,7 +1046,6 @@ make - testSimulated2D.run true false @@ -1056,7 +1053,6 @@ make - testSimulated3D.run true false @@ -1086,6 +1082,22 @@ true true + + make + -j2 + tests/testFundamental.run + true + true + true + + + make + -j2 + tests/testHomography2.run + true + true + true + make -j2 @@ -1126,46 +1138,6 @@ true true - - make - -j2 - install - true - true - true - - - make - -j2 - clean - true - true - true - - - make - -j2 - check - true - true - true - - - make - -j2 - all - true - true - true - - - make - -j2 - dist - true - true - true - make -j2 @@ -1262,6 +1234,46 @@ true true + + make + -j2 + install + true + true + true + + + make + -j2 + clean + true + true + true + + + make + -j2 + check + true + true + true + + + make + -j2 + all + true + true + true + + + make + -j2 + dist + true + true + true + make -j2 diff --git a/base/Matrix.cpp b/base/Matrix.cpp index 2fc84b92f..dc97a7b2e 100644 --- a/base/Matrix.cpp +++ b/base/Matrix.cpp @@ -1112,6 +1112,37 @@ void svd(const Matrix& A, Matrix& U, Vector& s, Matrix& V, bool sort) { } } +/* ************************************************************************* */ +boost::tuple DLT(const Matrix& A, double rank_tol) { + + // Check size of A + int m = A.size1(), n = A.size2(); + if (m rank_tol) + rank++; + // Find minimum singular value and corresponding column index + int min_j = n - 1; + double min_S = S(min_j); + for (int j = 0; j < n - 1; j++) + if (S(j) < min_S) { + min_j = j; + min_S = S(j); + } + + // Return rank, minimum singular value, and corresponding column of V + return boost::tuple(rank, min_S, column_(V, min_j)); +} + #if 0 /* ************************************************************************* */ // TODO, would be faster with Cholesky diff --git a/base/Matrix.h b/base/Matrix.h index 654530069..b915b6658 100644 --- a/base/Matrix.h +++ b/base/Matrix.h @@ -347,6 +347,9 @@ inline Matrix skewSymmetric(const Vector& w) { return skewSymmetric(w(0),w(1),w( * @param sort boolean flag to sort singular values and V * if m > n then U*S*V' = (m*n)*(n*n)*(n*n) (the m-n columns of U are of no use) * if m < n then U*S*V' = (m*m)*(m*m)*(m*n) (the n-m columns of V are of no use) + * Careful! The dimensions above reflect V', not V, which is n*m if m n then U*S*V' = (m*n)*(n*n)*(n*n) (the m-n columns of U are of no use) + * You can just pass empty matrix V and vector S, they will be re-allocated. */ void svd(Matrix& A, Vector& S, Matrix& V, bool sort=true); +/** + * Direct linear transform algorithm that calls svd + * to find a vector v that minimizes the algebraic error A*v + * @param A of size m*n, where m>=n (pad with zero rows if not!) + * Returns rank of A, minimum error (singular value), + * and corresponding eigenvector (column of V, with A=U*S*V') + */ +boost::tuple DLT(const Matrix& A, double rank_tol=1e-9); + /** Use SVD to calculate inverse square root of a matrix */ Matrix inverse_square_root(const Matrix& A); diff --git a/geometry/tensorInterface.cpp b/geometry/tensorInterface.cpp index 8f26e61ee..ae3da52ac 100644 --- a/geometry/tensorInterface.cpp +++ b/geometry/tensorInterface.cpp @@ -12,27 +12,4 @@ using namespace tensors; namespace gtsam { -boost::tuple DLT(const Matrix& A) { - - // Do SVD on A - Matrix U, V; - Vector S; - svd(A, U, S, V, false); - - // Find minimum column - int n = V.size2(), min_j = n - 1, rank = 0; - for (int j = 0; j < n; j++) - if (S(j) > 1e-9) - rank++; - double min_S = S(min_j); - for (int j = 0; j < n - 1; j++) - if (S(j) < min_S) { - min_j = j; - min_S = S(j); - } - - // Return minimum column - return boost::tuple(rank, min_S, column_(V, min_j)); -} - } // namespace gtsam diff --git a/geometry/tensorInterface.h b/geometry/tensorInterface.h index a2ab58eb6..441b0d137 100644 --- a/geometry/tensorInterface.h +++ b/geometry/tensorInterface.h @@ -94,10 +94,4 @@ namespace gtsam { return R; } - /** - * Find Vector v that minimizes algebraic error A*v - * Returns rank of A, minimum error, and corresponding eigenvector - */ - boost::tuple DLT(const Matrix& A); - } // namespace gtsam