aboutsummaryrefslogtreecommitdiffhomepage
path: root/Eigen/src
diff options
context:
space:
mode:
authorGravatar Gael Guennebaud <g.gael@free.fr>2008-10-01 10:17:08 +0000
committerGravatar Gael Guennebaud <g.gael@free.fr>2008-10-01 10:17:08 +0000
commitd907cd4410618628be0ab0f00d7e320014c61555 (patch)
treec613f31f6db8fac0c5e475c5ed86c4603745ae82 /Eigen/src
parent618de17bf751ab50bbc23603d073da9229bb066d (diff)
Fixes in Eigensolver:
* eigenvectors => pseudoEigenvectors * added pseudoEigenvalueMatrix * clear the documentation * added respective unit test Still missing: a proper eigenvectors() function.
Diffstat (limited to 'Eigen/src')
-rw-r--r--Eigen/src/QR/EigenSolver.h66
1 files changed, 63 insertions, 3 deletions
diff --git a/Eigen/src/QR/EigenSolver.h b/Eigen/src/QR/EigenSolver.h
index 44917d139..1b392cbb9 100644
--- a/Eigen/src/QR/EigenSolver.h
+++ b/Eigen/src/QR/EigenSolver.h
@@ -58,9 +58,50 @@ template<typename _MatrixType> class EigenSolver
compute(matrix);
}
- MatrixType eigenvectors(void) const { return m_eivec; }
-
- EigenvalueType eigenvalues(void) const { return m_eivalues; }
+ // TODO compute the complex eigen vectors
+ // MatrixType eigenvectors(void) const { return m_eivec; }
+
+ /** \returns a real matrix V of pseudo eigenvectors.
+ *
+ * Let D be the block diagonal matrix with the real eigenvalues in 1x1 blocks,
+ * and any complex values u+iv in 2x2 blocks [u v ; -v u]. Then, the matrices D
+ * and V satisfy A*V = V*D.
+ *
+ * More precisely, if the diagonal matrix of the eigen values is:\n
+ * \f$
+ * \left[ \begin{array}{cccccc}
+ * u+iv & & & & & \\
+ * & u-iv & & & & \\
+ * & & a+ib & & & \\
+ * & & & a-ib & & \\
+ * & & & & x & \\
+ * & & & & & y \\
+ * \end{array} \right]
+ * \f$ \n
+ * then, we have:\n
+ * \f$
+ * D =\left[ \begin{array}{cccccc}
+ * u & v & & & & \\
+ * -v & u & & & & \\
+ * & & a & b & & \\
+ * & & -b & a & & \\
+ * & & & & x & \\
+ * & & & & & y \\
+ * \end{array} \right]
+ * \f$
+ *
+ * \sa pseudoEigenvalueMatrix()
+ */
+ const MatrixType& pseudoEigenvectors() const { return m_eivec; }
+
+ /** \returns the real block diagonal matrix D of the eigenvalues.
+ *
+ * See pseudoEigenvectors() for the details.
+ */
+ MatrixType pseudoEigenvalueMatrix() const;
+
+ /** \returns the eigenvalues as a column vector */
+ EigenvalueType eigenvalues() const { return m_eivalues; }
void compute(const MatrixType& matrix);
@@ -75,6 +116,25 @@ template<typename _MatrixType> class EigenSolver
};
template<typename MatrixType>
+MatrixType EigenSolver<MatrixType>::pseudoEigenvalueMatrix() const
+{
+ int n = m_eivec.cols();
+ MatrixType matD = MatrixType::Zero(n,n);
+ for (int i=0; i<n; i++)
+ {
+ if (ei_isMuchSmallerThan(ei_imag(m_eivalues.coeff(i)), ei_real(m_eivalues.coeff(i))))
+ matD.coeffRef(i,i) = ei_real(m_eivalues.coeff(i));
+ else
+ {
+ matD.template block<2,2>(i,i) << ei_real(m_eivalues.coeff(i)), ei_imag(m_eivalues.coeff(i)),
+ -ei_imag(m_eivalues.coeff(i)), ei_real(m_eivalues.coeff(i));
+ i++;
+ }
+ }
+ return matD;
+}
+
+template<typename MatrixType>
void EigenSolver<MatrixType>::compute(const MatrixType& matrix)
{
assert(matrix.cols() == matrix.rows());