105 const typename Teuchos::ScalarTraits<typename V::scalar_type>::magnitudeType tolerance = 1e-7,
106 const int eigNormalizationFreq = 1,
107 Teuchos::RCP<Teuchos::FancyOStream> out = Teuchos::null,
108 const bool computeSpectralRadius =
true) {
109 typedef typename V::scalar_type ST;
110 typedef Teuchos::ScalarTraits<typename V::scalar_type> STS;
111 typedef typename Teuchos::ScalarTraits<typename V::scalar_type>::magnitudeType MT;
113 bool verbose = (out != Teuchos::null);
117 *out <<
" powerMethodWithInitGuess:" << endl;
120 const ST zero =
static_cast<ST
>(0.0);
121 const ST one =
static_cast<ST
>(1.0);
123 ST lambdaMaxOld = one;
127 TEUCHOS_TEST_FOR_EXCEPTION(norm == zero, std::runtime_error,
128 "Ifpack2::PowerMethod::powerMethodWithInitGuess: The initial guess "
129 "has zero norm. This could be either because Tpetra::Vector::"
130 "randomize filled the vector with zeros (if that was used to "
131 "compute the initial guess), or because the norm2 method has a "
132 "bug. The first is not impossible, but unlikely.");
135 *out <<
" Original norm1(x): " << x->norm1()
136 <<
", norm2(x): " << norm << endl;
139 x->scale(one / norm);
142 *out <<
" norm1(x.scale(one/norm)): " << x->norm1() << endl;
146 y = Teuchos::rcp(
new V(A.getRangeMap()));
155 if (computeSpectralRadius) {
159 *out <<
" PowerMethod using spectral radius route" << endl;
161 for (
int iter = 0; iter < numIters - 1; ++iter) {
163 *out <<
" Iteration " << iter << endl;
166 x->elementWiseMultiply(STS::one(), D_inv, *y, STS::zero());
168 if (((iter + 1) % eigNormalizationFreq == 0) && (iter < numIters - 2)) {
172 *out <<
" norm is zero; returning zero" << endl;
173 *out <<
" Power method terminated after " << iter <<
" iterations." << endl;
177 lambdaMaxOld = lambdaMax;
178 lambdaMax = pow(norm, Teuchos::ScalarTraits<MT>::one() / eigNormalizationFreq);
179 if (Teuchos::ScalarTraits<ST>::magnitude(lambdaMax - lambdaMaxOld) < tolerance * Teuchos::ScalarTraits<ST>::magnitude(lambdaMax)) {
181 *out <<
" lambdaMax: " << lambdaMax << endl;
182 *out <<
" Power method terminated after " << iter <<
" iterations." << endl;
185 }
else if (verbose) {
186 *out <<
" lambdaMaxOld: " << lambdaMaxOld << endl;
187 *out <<
" lambdaMax: " << lambdaMax << endl;
188 *out <<
" |lambdaMax-lambdaMaxOld|/|lambdaMax|: " << Teuchos::ScalarTraits<ST>::magnitude(lambdaMax - lambdaMaxOld) / Teuchos::ScalarTraits<ST>::magnitude(lambdaMax) << endl;
191 x->scale(one / norm);
195 *out <<
" lambdaMax: " << lambdaMax << endl;
201 *out <<
" norm is zero; returning zero" << endl;
202 *out <<
" Power method terminated after " << numIters <<
" iterations." << endl;
206 x->scale(one / norm);
208 y->elementWiseMultiply(STS::one(), D_inv, *y, STS::zero());
209 lambdaMax = y->norm2();
215 *out <<
" PowerMethod using largest eigenvalue route" << endl;
217 for (
int iter = 0; iter < numIters - 1; ++iter) {
219 *out <<
" Iteration " << iter << endl;
222 y->elementWiseMultiply(STS::one(), D_inv, *y, STS::zero());
224 if (((iter + 1) % eigNormalizationFreq == 0) && (iter < numIters - 2)) {
225 xDinvAx = x->dot(*y);
226 if (xDinvAx == zero) {
228 *out <<
" xDinvAx is zero; returning zero" << endl;
229 *out <<
" Power method terminated after " << iter <<
" iterations." << endl;
233 lambdaMaxOld = lambdaMax;
234 lambdaMax = pow(xDinvAx, Teuchos::ScalarTraits<MT>::one() / eigNormalizationFreq);
235 if (Teuchos::ScalarTraits<ST>::magnitude(lambdaMax - lambdaMaxOld) < tolerance * Teuchos::ScalarTraits<ST>::magnitude(lambdaMax)) {
237 *out <<
" lambdaMax: " << lambdaMax << endl;
238 *out <<
" Power method terminated after " << iter <<
" iterations." << endl;
241 }
else if (verbose) {
242 *out <<
" lambdaMaxOld: " << lambdaMaxOld << endl;
243 *out <<
" lambdaMax: " << lambdaMax << endl;
244 *out <<
" |lambdaMax-lambdaMaxOld|/|lambdaMax|: " << Teuchos::ScalarTraits<ST>::magnitude(lambdaMax - lambdaMaxOld) / Teuchos::ScalarTraits<ST>::magnitude(lambdaMax) << endl;
249 x->scale(one / norm);
253 *out <<
" lambdaMax: " << lambdaMax << endl;
259 *out <<
" norm is zero; returning zero" << endl;
260 *out <<
" Power method terminated after " << numIters <<
" iterations." << endl;
264 x->scale(one / norm);
266 y->elementWiseMultiply(STS::one(), D_inv, *y, STS::zero());
267 lambdaMax = y->dot(*x);
271 *out <<
" lambdaMax: " << lambdaMax << endl;
272 *out <<
" Power method terminated after " << numIters <<
" iterations." << endl;
291 typedef typename V::device_type::execution_space dev_execution_space;
292 typedef typename V::local_ordinal_type LO;
296 if (nonnegativeRealParts) {
297 auto x_lcl = x.getLocalViewDevice(Tpetra::Access::ReadWrite);
298 auto x_lcl_1d = Kokkos::subview(x_lcl, Kokkos::ALL(), 0);
300 const LO lclNumRows =
static_cast<LO
>(x.getLocalLength());
301 Kokkos::RangePolicy<dev_execution_space, LO> range(0, lclNumRows);
302 PositivizeVector<
decltype(x_lcl_1d), LO> functor(x_lcl_1d);
303 Kokkos::parallel_for(range, functor);
329 const typename Teuchos::ScalarTraits<typename V::scalar_type>::magnitudeType tolerance = 1e-7,
330 const int eigNormalizationFreq = 1,
331 Teuchos::RCP<Teuchos::FancyOStream> out = Teuchos::null,
332 const bool computeSpectralRadius =
true) {
333 typedef typename V::scalar_type ST;
334 typedef Teuchos::ScalarTraits<typename V::scalar_type> STS;
336 bool verbose = (out != Teuchos::null);
339 *out <<
"powerMethod:" << std::endl;
342 const ST zero =
static_cast<ST
>(0.0);
344 Teuchos::RCP<V> x = Teuchos::rcp(
new V(A.getDomainMap()));
350 ST lambdaMax =
powerMethodWithInitGuess(A, D_inv, numIters, x, y, tolerance, eigNormalizationFreq, out, computeSpectralRadius);
359 if (STS::real(lambdaMax) < STS::real(zero)) {
361 *out <<
"real(lambdaMax) = " << STS::real(lambdaMax) <<
" < 0; "
362 "try again with a different random initial guess"
373 lambdaMax =
powerMethodWithInitGuess(A, D_inv, numIters, x, y, tolerance, eigNormalizationFreq, out, computeSpectralRadius);
V::scalar_type powerMethodWithInitGuess(const OperatorType &A, const V &D_inv, const int numIters, Teuchos::RCP< V > x, Teuchos::RCP< V > y, const typename Teuchos::ScalarTraits< typename V::scalar_type >::magnitudeType tolerance=1e-7, const int eigNormalizationFreq=1, Teuchos::RCP< Teuchos::FancyOStream > out=Teuchos::null, const bool computeSpectralRadius=true)
Use the power method to estimate the maximum eigenvalue of A*D_inv, given an initial guess vector x.
Definition Ifpack2_PowerMethod.hpp:100
V::scalar_type powerMethod(const OperatorType &A, const V &D_inv, const int numIters, Teuchos::RCP< V > y, const typename Teuchos::ScalarTraits< typename V::scalar_type >::magnitudeType tolerance=1e-7, const int eigNormalizationFreq=1, Teuchos::RCP< Teuchos::FancyOStream > out=Teuchos::null, const bool computeSpectralRadius=true)
Use the power method to estimate the maximum eigenvalue of A*D_inv.
Definition Ifpack2_PowerMethod.hpp:325
void computeInitialGuessForPowerMethod(V &x, const bool nonnegativeRealParts)
Fill x with random initial guess for power method.
Definition Ifpack2_PowerMethod.hpp:290