<T>LAPACK 0.1.1
C++ Template Linear Algebra PACKage
Loading...
Searching...
No Matches
schur_move.hpp
Go to the documentation of this file.
1
5//
6// Copyright (c) 2021-2023, University of Colorado Denver. All rights reserved.
7//
8// This file is part of <T>LAPACK.
9// <T>LAPACK is free software: you can redistribute it and/or modify it under
10// the terms of the BSD 3-Clause license. See the accompanying LICENSE file.
11
12#ifndef TLAPACK_SCHUR_MOVE_HH
13#define TLAPACK_SCHUR_MOVE_HH
14
17
18namespace tlapack {
19
46template <TLAPACK_MATRIX matrix_t>
48 matrix_t& A,
49 matrix_t& Q,
52{
53 using idx_t = size_type<matrix_t>;
54 using T = type_t<matrix_t>;
55 using real_t = real_type<T>;
56
57 const idx_t n = ncols(A);
58 const real_t zero(0);
59
60 // Quick return
61 if (n == 0) return 0;
62
63 // Check if ifst points to the middle of a 2x2 block
64 if (is_real<T>)
65 if (ifst > 0)
66 if (A(ifst, ifst - 1) != zero) ifst = ifst - 1;
67
68 // Size of the current block, can be either 1, 2
69 idx_t nbf = 1;
70 if (is_real<T>)
71 if (ifst < n - 1)
72 if (A(ifst + 1, ifst) != zero) nbf = 2;
73
74 // Check if ilst points to the middle of a 2x2 block
75 if (is_real<T>)
76 if (ilst > 0)
77 if (A(ilst, ilst - 1) != zero) ilst = ilst - 1;
78
79 // Size of the final block, can be either 1, 2
80 idx_t nbl = 1;
81 if (is_real<T>)
82 if (ilst < n - 1)
83 if (A(ilst + 1, ilst) != zero) nbl = 2;
84
85 idx_t here = ifst;
86 if (ifst < ilst) {
87 if (nbf == 2 and nbl == 1) ilst = ilst - 1;
88 if (nbf == 1 and nbl == 2) ilst = ilst + 1;
89
90 while (here != ilst) {
91 // Size of the next eigenvalue block
92 idx_t nbnext = 1;
93 if (is_real<T>)
94 if (here + nbf + 1 < n)
95 if (A(here + nbf + 1, here + nbf) != zero) nbnext = 2;
96
97 int ierr = schur_swap(want_q, A, Q, here, nbf, nbnext);
98 if (ierr) {
99 // The swap failed, return with error
100 ilst = here;
101 return 1;
102 }
103 here = here + nbnext;
104 }
105 }
106 else {
107 while (here != ilst) {
108 // Size of the next eigenvalue block
109 idx_t nbnext = 1;
110 if (is_real<T>)
111 if (here > 1)
112 if (A(here - 1, here - 2) != zero) nbnext = 2;
113
114 int ierr = schur_swap(want_q, A, Q, here - nbnext, nbnext, nbf);
115 if (ierr) {
116 // The swap failed, return with error
117 ilst = here;
118 return 1;
119 }
120 here = here - nbnext;
121 }
122 }
123
124 return 0;
125}
126
127} // namespace tlapack
128
129#endif // TLAPACK_SCHUR_MOVE_HH
int schur_swap(bool want_q, matrix_t &A, matrix_t &Q, const size_type< matrix_t > &j0, const size_type< matrix_t > &n1, const size_type< matrix_t > &n2)
schur_swap, swaps 2 eigenvalues of A.
Definition schur_swap.hpp:49
int schur_move(bool want_q, matrix_t &A, matrix_t &Q, size_type< matrix_t > &ifst, size_type< matrix_t > &ilst)
schur_move reorders the Schur factorization of a matrix S = Q*A*Q**H, so that the diagonal element of...
Definition schur_move.hpp:47
typename traits::real_type_traits< Types..., int >::type real_type
The common real type of the list of types.
Definition scalar_type_traits.hpp:113