| 13 | |
| 14 | template<typename MatrixType, typename JacobiScalar> |
| 15 | void jacobi(const MatrixType& m = MatrixType()) |
| 16 | { |
| 17 | typedef typename MatrixType::Index Index; |
| 18 | Index rows = m.rows(); |
| 19 | Index cols = m.cols(); |
| 20 | |
| 21 | enum { |
| 22 | RowsAtCompileTime = MatrixType::RowsAtCompileTime, |
| 23 | ColsAtCompileTime = MatrixType::ColsAtCompileTime |
| 24 | }; |
| 25 | |
| 26 | typedef Matrix<JacobiScalar, 2, 1> JacobiVector; |
| 27 | |
| 28 | const MatrixType a(MatrixType::Random(rows, cols)); |
| 29 | |
| 30 | JacobiVector v = JacobiVector::Random().normalized(); |
| 31 | JacobiScalar c = v.x(), s = v.y(); |
| 32 | JacobiRotation<JacobiScalar> rot(c, s); |
| 33 | |
| 34 | { |
| 35 | Index p = internal::random<Index>(0, rows-1); |
| 36 | Index q; |
| 37 | do { |
| 38 | q = internal::random<Index>(0, rows-1); |
| 39 | } while (q == p); |
| 40 | |
| 41 | MatrixType b = a; |
| 42 | b.applyOnTheLeft(p, q, rot); |
| 43 | VERIFY_IS_APPROX(b.row(p), c * a.row(p) + numext::conj(s) * a.row(q)); |
| 44 | VERIFY_IS_APPROX(b.row(q), -s * a.row(p) + numext::conj(c) * a.row(q)); |
| 45 | } |
| 46 | |
| 47 | { |
| 48 | Index p = internal::random<Index>(0, cols-1); |
| 49 | Index q; |
| 50 | do { |
| 51 | q = internal::random<Index>(0, cols-1); |
| 52 | } while (q == p); |
| 53 | |
| 54 | MatrixType b = a; |
| 55 | b.applyOnTheRight(p, q, rot); |
| 56 | VERIFY_IS_APPROX(b.col(p), c * a.col(p) - s * a.col(q)); |
| 57 | VERIFY_IS_APPROX(b.col(q), numext::conj(s) * a.col(p) + numext::conj(c) * a.col(q)); |
| 58 | } |
| 59 | } |
| 60 | |
| 61 | void test_jacobi() |
| 62 | { |
nothing calls this directly
no test coverage detected