Class for computing eigenvalues of a matrix.
More...
#include <eigen.hpp>
|
| Eigen (const std::vector< std::vector< double >> &mat) |
| Constructor for the Eigen class. More...
|
|
double | power_iter (int max_iters=100, double tolerance=1e-10) const |
| Perform the power iteration method to find the dominant eigenvalue. More...
|
|
std::vector< double > | qr_algorithm (int max_iters=100, double tolerance=1e-10) const |
| Calculate all eigenvalues of the matrix using the QR algorithm. More...
|
|
std::vector< double > | sensitivity (double perturbation) const |
| Calculates the sensitivity of the eigenvalues of a matrix to small perturbations. More...
|
|
double | determinant () const |
|
void | schur_decomp (std::vector< std::vector< double >> &schurMatrix, double tolerance=1e-10) const |
| Computes the Schur decomposition of a matrix. More...
|
|
std::vector< std::vector< double > > | jordan_normal_form (double tolerance=1e-10) const |
| Computes the Jordan normal form of a matrix. More...
|
|
double | rayleigh_iter (int maxIterations, double tolerance) const |
| Perform Rayleigh Quotient Iteration to approximate the dominant eigenvalue. More...
|
|
|
std::vector< std::vector< double > > | matrix |
|
int | size |
|
Class for computing eigenvalues of a matrix.
Definition at line 45 of file eigen.hpp.
◆ Eigen()
gpmp::linalg::Eigen::Eigen |
( |
const std::vector< std::vector< double >> & |
mat | ) |
|
Constructor for the Eigen class.
- Parameters
-
mat | The square matrix for eigenvalue computation |
Definition at line 39 of file eigen.cpp.
std::vector< std::vector< double > > matrix
◆ determinant()
double gpmp::linalg::Eigen::determinant |
( |
| ) |
const |
Definition at line 143 of file eigen.cpp.
146 double determinant = std::accumulate(eigenvalues.begin(),
149 std::multiplies<double>());
std::vector< double > qr_algorithm(int max_iters=100, double tolerance=1e-10) const
Calculate all eigenvalues of the matrix using the QR algorithm.
double determinant() const
◆ jordan_normal_form()
std::vector< std::vector< double > > gpmp::linalg::Eigen::jordan_normal_form |
( |
double |
tolerance = 1e-10 | ) |
const |
Computes the Jordan normal form of a matrix.
This method computes the Jordan normal form of a matrix The Jordan normal form is a block diagonal matrix, where each block is either a diagonal matrix or a Jordan block A Jordan block is a square matrix with ones on the superdiagonal and the eigenvalue on the diagonal
- Parameters
-
tolerance | The tolerance for determining if a subdiagonal element is zero |
- Returns
- The Jordan normal form of the matrix
The returned matrix will have the same dimensions as the original matrix
Definition at line 212 of file eigen.cpp.
213 std::vector<std::vector<double>> jordanMatrix(
215 std::vector<double>(
size, 0.0));
218 for (
int i = 0; i <
size; ++i) {
219 jordanMatrix[i][i] = eigenvalues[i];
222 int jordanBlockSize = 1;
223 while (i + jordanBlockSize <
size &&
224 std::abs(
matrix[i + jordanBlockSize][i]) < tolerance) {
229 for (
int j = 1; j < jordanBlockSize; ++j) {
230 jordanMatrix[i + j][i + j - 1] = 1.0;
◆ power_iter()
double gpmp::linalg::Eigen::power_iter |
( |
int |
max_iters = 100 , |
|
|
double |
tolerance = 1e-10 |
|
) |
| const |
Perform the power iteration method to find the dominant eigenvalue.
- Parameters
-
max_iters | Maximum number of iterations for power iteration |
tolerance | Tolerance for convergence |
- Returns
- The dominant eigenvalue of the matrix
Definition at line 48 of file eigen.cpp.
50 std::vector<double> x(
size, 1.0);
51 std::vector<double> y(
size);
53 for (
int iter = 0; iter < max_iters; ++iter) {
55 for (
int i = 0; i <
size; ++i) {
57 for (
int j = 0; j <
size; ++j) {
58 y[i] +=
matrix[i][j] * x[j];
63 double max_element = 0.0;
64 for (
int i = 0; i <
size; ++i) {
65 max_element = std::max(max_element, std::abs(y[i]));
69 for (
int i = 0; i <
size; ++i) {
75 for (
int i = 0; i <
size; ++i) {
76 error += std::abs(y[i] - x[i]);
79 if (error < tolerance) {
87 std::cerr <<
"Warning: Power iteration did not converge within the"
88 "specified iterations\n";
Referenced by main().
◆ qr_algorithm()
std::vector< double > gpmp::linalg::Eigen::qr_algorithm |
( |
int |
max_iters = 100 , |
|
|
double |
tolerance = 1e-10 |
|
) |
| const |
Calculate all eigenvalues of the matrix using the QR algorithm.
- Parameters
-
max_iters | Maximum number of iterations for QR algorithm |
tolerance | Tolerance for convergence |
- Returns
- A vector containing all eigenvalues of the matrix
Definition at line 93 of file eigen.cpp.
96 std::vector<std::vector<double>> hessenberg_mtx =
matrix;
99 for (
int iter = 0; iter < max_iters; ++iter) {
101 for (
int i = 0; i <
size - 1; ++i) {
103 double a = hessenberg_mtx[i][i];
104 double b = hessenberg_mtx[i + 1][i];
105 double r = std::hypot(a, b);
110 for (
int j = 0; j <
size; ++j) {
112 c * hessenberg_mtx[i][j] + s * hessenberg_mtx[i + 1][j];
114 -s * hessenberg_mtx[i][j] + c * hessenberg_mtx[i + 1][j];
115 hessenberg_mtx[i][j] = temp1;
116 hessenberg_mtx[i + 1][j] = temp2;
121 double offDiagonalSum = 0.0;
122 for (
int i = 2; i <
size; ++i) {
123 offDiagonalSum += std::abs(hessenberg_mtx[i][i - 1]);
126 if (offDiagonalSum < tolerance) {
128 std::vector<double> eigenvalues;
129 for (
int i = 0; i <
size; ++i) {
130 eigenvalues.push_back(hessenberg_mtx[i][i]);
137 std::cerr <<
"Warning: QR iteration did not converge within the "
138 "specified iterations\n";
140 return std::vector<double>();
Referenced by sensitivity().
◆ rayleigh_iter()
double gpmp::linalg::Eigen::rayleigh_iter |
( |
int |
maxIterations, |
|
|
double |
tolerance |
|
) |
| const |
Perform Rayleigh Quotient Iteration to approximate the dominant eigenvalue.
This method iteratively refines an estimate of the dominant eigenvalue of the matrix using the Rayleigh quotient iteration. The method returns the final estimate of the dominant eigenvalue
- Parameters
-
maxIterations | Maximum number of iterations |
tolerance | Convergence tolerance |
- Returns
- The dominant eigenvalue estimate
- Note
- The iteration may not converge for all matrices. A warning is issued if convergence is not achieved
Definition at line 237 of file eigen.cpp.
240 std::vector<double> x(
size, 1.0);
241 double lambdaPrev = 0.0;
243 for (
int iter = 0; iter < maxIterations; ++iter) {
245 std::vector<double> Ax(
size, 0.0);
248 for (
int i = 0; i <
size; ++i) {
249 for (
int j = 0; j <
size; ++j) {
250 Ax[i] +=
matrix[i][j] * x[j];
256 std::inner_product(x.begin(), x.end(), Ax.begin(), 0.0) /
257 std::inner_product(x.begin(), x.end(), x.begin(), 0.0);
260 if (std::abs(lambda - lambdaPrev) < tolerance) {
265 double normAx = std::sqrt(
266 std::inner_product(Ax.begin(), Ax.end(), Ax.begin(), 0.0));
267 for (
int i = 0; i <
size; ++i) {
269 x[i] = Ax[i] / normAx;
275 std::cerr <<
"Warning: Rayleigh quotient iteration did not converge within "
276 "the specified iterations."
◆ schur_decomp()
void gpmp::linalg::Eigen::schur_decomp |
( |
std::vector< std::vector< double >> & |
schurMatrix, |
|
|
double |
tolerance = 1e-10 |
|
) |
| const |
Computes the Schur decomposition of a matrix.
This method computes the Schur decomposition of a matrix The Schur decomposition is a block triangular decomposition of a matrix, where the diagonal blocks are square and the off-diagonal blocks are zero or upper triangular
- Parameters
-
schurMatrix | The output matrix to store the Schur decomposition |
tolerance | The tolerance for determining if a subdiagonal element is zero |
The schurMatrix parameter must be pre-allocated with the same dimensions as the matrix object This method modifies the contents of the schurMatrix parameter
Definition at line 181 of file eigen.cpp.
187 for (
int i =
size - 1; i > 0; --i) {
189 if (std::abs(schurMatrix[i][i - 1]) < tolerance) {
190 schurMatrix[i][i - 1] = 0.0;
193 double a = schurMatrix[i - 1][i - 1];
194 double b = schurMatrix[i][i - 1];
195 double r = std::hypot(a, b);
199 for (
int j = 0; j <
size; ++j) {
201 c * schurMatrix[i - 1][j] + s * schurMatrix[i][j];
203 -s * schurMatrix[i - 1][j] + c * schurMatrix[i][j];
204 schurMatrix[i - 1][j] = temp1;
205 schurMatrix[i][j] = temp2;
◆ sensitivity()
std::vector< double > gpmp::linalg::Eigen::sensitivity |
( |
double |
perturbation | ) |
const |
Calculates the sensitivity of the eigenvalues of a matrix to small perturbations.
This method calculates the sensitivity of each eigenvalue of a matrix to small perturbations The sensitivity is defined as the change in the eigenvalue divided by the amount of perturbation
- Parameters
-
perturbation | The amount of perturbation to apply to the matrix |
- Returns
- A vector containing the sensitivity of each eigenvalue
The size of the returned vector will be the same as the size of the matrix
Definition at line 154 of file eigen.cpp.
155 std::vector<double> originalEigenvalues =
qr_algorithm();
157 std::vector<double> perturbedEigenvalues;
158 for (
int i = 0; i <
size; ++i) {
160 std::vector<std::vector<double>> perturbedMatrix =
matrix;
161 perturbedMatrix[i][i] += perturbation;
164 std::vector<double> perturbedVals =
165 Eigen(perturbedMatrix).qr_algorithm();
166 perturbedEigenvalues.push_back(perturbedVals[i]);
172 for (
int i = 0; i <
size; ++i) {
174 (perturbedEigenvalues[i] - originalEigenvalues[i]) / perturbation;
std::vector< double > sensitivity(double perturbation) const
Calculates the sensitivity of the eigenvalues of a matrix to small perturbations.
Eigen(const std::vector< std::vector< double >> &mat)
Constructor for the Eigen class.
References qr_algorithm().
◆ matrix
std::vector<std::vector<double> > gpmp::linalg::Eigen::matrix |
|
private |
◆ size
int gpmp::linalg::Eigen::size |
|
private |
The documentation for this class was generated from the following files: