GCC Code Coverage Report


Directory: ./
File: src/eps/impls/krylov/lanczos/lanczos.c
Date: 2026-07-06 04:10:30
Exec Total Coverage
Lines: 461 491 93.9%
Functions: 17 18 94.4%
Branches: 930 1606 57.9%

Line Branch Exec Source
1 /*
2 - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
3 SLEPc - Scalable Library for Eigenvalue Problem Computations
4 Copyright (c) 2002-, Universitat Politecnica de Valencia, Spain
5
6 This file is part of SLEPc.
7 SLEPc is distributed under a 2-clause BSD license (see LICENSE).
8 - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
9 */
10 /*
11 SLEPc eigensolver: "lanczos"
12
13 Method: Explicitly Restarted Symmetric/Hermitian Lanczos
14
15 Algorithm:
16
17 Lanczos method for symmetric (Hermitian) problems, with explicit
18 restart and deflation. Several reorthogonalization strategies can
19 be selected.
20
21 References:
22
23 [1] "Lanczos Methods in SLEPc", SLEPc Technical Report STR-5,
24 available at https://slepc.upv.es.
25 */
26
27 #include <slepc/private/epsimpl.h> /*I "slepceps.h" I*/
28 #include <slepcblaslapack.h>
29
30 typedef struct {
31 EPSLanczosReorthogType reorthog; /* user-provided reorthogonalization parameter */
32 PetscInt allocsize; /* number of columns of work BV's allocated at setup */
33 BV AV; /* work BV used in selective reorthogonalization */
34 } EPS_LANCZOS;
35
36 364 static PetscErrorCode EPSSetUp_Lanczos(EPS eps)
37 {
38 364 EPS_LANCZOS *lanczos = (EPS_LANCZOS*)eps->data;
39 364 BVOrthogRefineType refine;
40 364 BVOrthogBlockType btype;
41 364 PetscReal eta;
42
43
1/2
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
364 PetscFunctionBegin;
44
4/10
✗ Branch 0 not taken.
✓ Branch 1 taken 10 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✓ Branch 4 taken 10 times.
✓ Branch 5 taken 10 times.
✗ Branch 6 not taken.
✓ Branch 7 taken 10 times.
✗ Branch 8 not taken.
✗ Branch 9 not taken.
364 EPSCheckHermitianDefinite(eps);
45
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 10 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
364 EPSCheckNotStructured(eps);
46
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
364 PetscCall(EPSSetDimensions_Default(eps,&eps->nev,&eps->ncv,&eps->mpd));
47
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 10 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
364 PetscCheck(eps->ncv<=eps->nev+eps->mpd,PetscObjectComm((PetscObject)eps),PETSC_ERR_USER_INPUT,"The value of ncv must not be larger than nev+mpd");
48
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
364 if (eps->max_it==PETSC_DETERMINE) eps->max_it = PetscMax(100,2*eps->n/eps->ncv);
49
6/8
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
✓ Branch 2 taken 2 times.
✓ Branch 3 taken 8 times.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✓ Branch 7 taken 2 times.
364 if (!eps->which) PetscCall(EPSSetWhichEigenpairs_Default(eps));
50
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 10 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
364 PetscCheck(eps->which!=EPS_ALL,PetscObjectComm((PetscObject)eps),PETSC_ERR_SUP,"This solver does not support computing all eigenvalues");
51
9/22
✗ Branch 0 not taken.
✓ Branch 1 taken 10 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✓ Branch 4 taken 2 times.
✓ Branch 5 taken 8 times.
✓ Branch 6 taken 2 times.
✓ Branch 7 taken 8 times.
✗ Branch 8 not taken.
✓ Branch 9 taken 2 times.
✗ Branch 10 not taken.
✓ Branch 11 taken 10 times.
✗ Branch 12 not taken.
✗ Branch 13 not taken.
✗ Branch 14 not taken.
✓ Branch 15 taken 10 times.
✗ Branch 16 not taken.
✗ Branch 17 not taken.
✗ Branch 18 not taken.
✓ Branch 19 taken 2 times.
✗ Branch 20 not taken.
✗ Branch 21 not taken.
364 EPSCheckUnsupported(eps,EPS_FEATURE_ARBITRARY | EPS_FEATURE_REGION | EPS_FEATURE_EXTRACTION | EPS_FEATURE_THRESHOLD);
52
1/8
✗ Branch 0 not taken.
✓ Branch 1 taken 10 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
364 EPSCheckIgnored(eps,EPS_FEATURE_BALANCE);
53
54
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 10 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
364 PetscCheck(lanczos->reorthog!=(EPSLanczosReorthogType)-1,PetscObjectComm((PetscObject)eps),PETSC_ERR_USER_INPUT,"You should explicitly provide the reorthogonalization type, e.g., -eps_lanczos_reorthog local. Note that the EPSLANCZOS solver is *NOT RECOMMENDED* for general use, because it uses explicit restart which typically has slow convergence. The recommended solver is EPSKRYLOVSCHUR (the default), which implements Lanczos with thick restart in the case of symmetric/Hermitian problems");
55
56
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
364 PetscCall(EPSAllocateSolution(eps,1));
57
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
364 PetscCall(EPS_SetInnerProduct(eps));
58
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
364 if (lanczos->reorthog != EPS_LANCZOS_REORTHOG_FULL) {
59
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
290 PetscCall(BVGetOrthogonalization(eps->V,NULL,&refine,&eta,&btype));
60
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
290 PetscCall(BVSetOrthogonalization(eps->V,BV_ORTHOG_MGS,refine,eta,btype));
61
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
290 PetscCall(PetscInfo(eps,"Switching to MGS orthogonalization\n"));
62 }
63
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
364 if (lanczos->reorthog == EPS_LANCZOS_REORTHOG_SELECTIVE) {
64
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
30 if (!lanczos->allocsize) {
65
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
10 PetscCall(BVDuplicate(eps->V,&lanczos->AV));
66
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
10 PetscCall(BVGetSizes(lanczos->AV,NULL,NULL,&lanczos->allocsize));
67 } else { /* make sure V and AV have the same size */
68
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
20 PetscCall(BVGetSizes(eps->V,NULL,NULL,&lanczos->allocsize));
69
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
20 PetscCall(BVResize(lanczos->AV,lanczos->allocsize,PETSC_FALSE));
70 }
71 }
72
73
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
364 PetscCall(DSSetType(eps->ds,DSHEP));
74
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
364 PetscCall(DSSetCompact(eps->ds,PETSC_TRUE));
75
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
364 PetscCall(DSAllocate(eps->ds,eps->ncv+1));
76
6/8
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
✓ Branch 2 taken 2 times.
✓ Branch 3 taken 8 times.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✓ Branch 7 taken 2 times.
364 if (lanczos->reorthog == EPS_LANCZOS_REORTHOG_LOCAL) PetscCall(EPSSetWorkVecs(eps,1));
77
6/12
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 2 times.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 2 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2 times.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✓ Branch 11 taken 2 times.
72 PetscFunctionReturn(PETSC_SUCCESS);
78 }
79
80 /*
81 EPSLocalLanczos - Local reorthogonalization.
82
83 This is the simplest variant. At each Lanczos step, the corresponding Lanczos vector
84 is orthogonalized with respect to the two previous Lanczos vectors, according to
85 the three term Lanczos recurrence. WARNING: This variant does not track the loss of
86 orthogonality that occurs in finite-precision arithmetic and, therefore, the
87 generated vectors are not guaranteed to be (semi-)orthogonal.
88 */
89 5181 static PetscErrorCode EPSLocalLanczos(EPS eps,PetscReal *alpha,PetscReal *beta,PetscInt k,PetscInt *M,PetscBool *breakdown)
90 {
91 5181 PetscInt i,j,m = *M;
92 5181 Mat Op;
93 5181 PetscBool *which,lwhich[100];
94 5181 PetscScalar *hwork,lhwork[100];
95
96
1/2
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
5181 PetscFunctionBegin;
97
1/8
✗ Branch 0 not taken.
✓ Branch 1 taken 10 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
5181 if (m > 100) PetscCall(PetscMalloc2(m,&which,m,&hwork));
98 else {
99 5181 which = lwhich;
100 5181 hwork = lhwork;
101 }
102
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
18106 for (i=0;i<k;i++) which[i] = PETSC_TRUE;
103
104
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
5181 PetscCall(BVSetActiveColumns(eps->V,0,m));
105
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
5181 PetscCall(STGetOperator(eps->st,&Op));
106
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
75416 for (j=k;j<m;j++) {
107
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
70235 PetscCall(BVMatMultColumn(eps->V,Op,j));
108 70235 which[j] = PETSC_TRUE;
109
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
70235 if (j-2>=k) which[j-2] = PETSC_FALSE;
110
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
70235 PetscCall(BVOrthogonalizeSomeColumn(eps->V,j+1,which,hwork,beta+j,breakdown));
111 70235 alpha[j] = PetscRealPart(hwork[j]);
112
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 10 times.
70235 if (PetscUnlikely(*breakdown)) {
113 *M = j+1;
114 break;
115
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
70235 } else PetscCall(BVScaleColumn(eps->V,j+1,1/beta[j]));
116 }
117
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
5181 PetscCall(STRestoreOperator(eps->st,&Op));
118
1/8
✗ Branch 0 not taken.
✓ Branch 1 taken 10 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
5181 if (m > 100) PetscCall(PetscFree2(which,hwork));
119
6/12
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 2 times.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 2 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2 times.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✓ Branch 11 taken 2 times.
1040 PetscFunctionReturn(PETSC_SUCCESS);
120 }
121
122 /*
123 DenseTridiagonal - Solves a real tridiagonal Hermitian Eigenvalue Problem.
124
125 Input Parameters:
126 + n - dimension of the eigenproblem
127 . D - pointer to the array containing the diagonal elements
128 - E - pointer to the array containing the off-diagonal elements
129
130 Output Parameters:
131 + w - pointer to the array to store the computed eigenvalues
132 - V - pointer to the array to store the eigenvectors
133
134 Notes:
135 If V is NULL then the eigenvectors are not computed.
136
137 This routine use LAPACK routines xSTEVR.
138 */
139 6745 static PetscErrorCode DenseTridiagonal(PetscInt n_,PetscReal *D,PetscReal *E,PetscReal *w,PetscScalar *V)
140 {
141 6745 PetscReal abstol = 0.0,vl,vu,*work;
142 6745 PetscBLASInt il,iu,m,*isuppz,n,lwork,*iwork,liwork;
143 6745 const char *jobz;
144 #if defined(PETSC_USE_COMPLEX)
145 3380 PetscInt i,j;
146 3380 PetscReal *VV=NULL;
147 #endif
148
149
1/2
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
6745 PetscFunctionBegin;
150
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
6745 PetscCall(PetscBLASIntCast(n_,&n));
151
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
6745 PetscCall(PetscBLASIntCast(20*n_,&lwork));
152
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
6745 PetscCall(PetscBLASIntCast(10*n_,&liwork));
153
2/2
✓ Branch 0 taken 5 times.
✓ Branch 1 taken 5 times.
6745 if (V) {
154 3380 jobz = "V";
155 #if defined(PETSC_USE_COMPLEX)
156
4/6
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 4 times.
✓ Branch 2 taken 1 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 1 times.
3380 PetscCall(PetscMalloc1(n*n,&VV));
157 #endif
158 } else jobz = "N";
159
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
6745 PetscCall(PetscMalloc3(2*n,&isuppz,lwork,&work,liwork,&iwork));
160
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
6745 PetscCall(PetscFPTrapPush(PETSC_FP_TRAP_OFF));
161 #if defined(PETSC_USE_COMPLEX)
162
13/28
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 4 times.
✓ Branch 2 taken 1 times.
✓ Branch 3 taken 4 times.
✓ Branch 4 taken 1 times.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✓ Branch 7 taken 5 times.
✓ Branch 8 taken 1 times.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✓ Branch 11 taken 1 times.
✓ Branch 12 taken 1 times.
✗ Branch 13 not taken.
✓ Branch 14 taken 1 times.
✗ Branch 15 not taken.
✗ Branch 16 not taken.
✓ Branch 17 taken 1 times.
✗ Branch 18 not taken.
✗ Branch 19 not taken.
✗ Branch 20 not taken.
✓ Branch 21 taken 1 times.
✗ Branch 22 not taken.
✗ Branch 23 not taken.
✗ Branch 24 not taken.
✓ Branch 25 taken 1 times.
✗ Branch 26 not taken.
✗ Branch 27 not taken.
3380 PetscCallLAPACKInfo("LAPACKstevr",LAPACKstevr_(jobz,"A",&n,D,E,&vl,&vu,&il,&iu,&abstol,&m,w,VV,&n,isuppz,work,&lwork,iwork,&liwork,&info));
163 #else
164
13/28
✓ Branch 0 taken 1 times.
✓ Branch 1 taken 4 times.
✓ Branch 2 taken 1 times.
✓ Branch 3 taken 4 times.
✓ Branch 4 taken 1 times.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✓ Branch 7 taken 5 times.
✓ Branch 8 taken 1 times.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✓ Branch 11 taken 1 times.
✓ Branch 12 taken 1 times.
✗ Branch 13 not taken.
✓ Branch 14 taken 1 times.
✗ Branch 15 not taken.
✗ Branch 16 not taken.
✓ Branch 17 taken 1 times.
✗ Branch 18 not taken.
✗ Branch 19 not taken.
✗ Branch 20 not taken.
✓ Branch 21 taken 1 times.
✗ Branch 22 not taken.
✗ Branch 23 not taken.
✗ Branch 24 not taken.
✓ Branch 25 taken 1 times.
✗ Branch 26 not taken.
✗ Branch 27 not taken.
3365 PetscCallLAPACKInfo("LAPACKstevr",LAPACKstevr_(jobz,"A",&n,D,E,&vl,&vu,&il,&iu,&abstol,&m,w,V,&n,isuppz,work,&lwork,iwork,&liwork,&info));
165 #endif
166
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
6745 PetscCall(PetscFPTrapPop());
167 #if defined(PETSC_USE_COMPLEX)
168
1/2
✓ Branch 0 taken 5 times.
✗ Branch 1 not taken.
3380 if (V) {
169
2/2
✓ Branch 0 taken 5 times.
✓ Branch 1 taken 5 times.
35265 for (i=0;i<n;i++)
170
2/2
✓ Branch 0 taken 5 times.
✓ Branch 1 taken 5 times.
423810 for (j=0;j<n;j++)
171 391925 V[i*n+j] = VV[i*n+j];
172
5/8
✓ Branch 0 taken 5 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 1 times.
✓ Branch 3 taken 4 times.
✓ Branch 4 taken 1 times.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✓ Branch 7 taken 1 times.
3380 PetscCall(PetscFree(VV));
173 }
174 #endif
175
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
6745 PetscCall(PetscFree3(isuppz,work,iwork));
176
6/12
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 2 times.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 2 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2 times.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✓ Branch 11 taken 2 times.
1349 PetscFunctionReturn(PETSC_SUCCESS);
177 }
178
179 /*
180 EPSSelectiveLanczos - Selective reorthogonalization.
181 */
182 380 static PetscErrorCode EPSSelectiveLanczos(EPS eps,PetscReal *alpha,PetscReal *beta,PetscInt k,PetscInt *M,PetscBool *breakdown,PetscReal anorm)
183 {
184 380 EPS_LANCZOS *lanczos = (EPS_LANCZOS*)eps->data;
185 380 PetscInt i,j,m = *M,n,nritz=0,nritzo;
186 380 Vec vj1,av;
187 380 Mat Op;
188 380 PetscReal *d,*e,*ritz,norm;
189 380 PetscScalar *Y,*hwork;
190 380 PetscBool *which;
191
192
1/2
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
380 PetscFunctionBegin;
193
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
380 PetscCall(PetscCalloc6(m+1,&d,m,&e,m,&ritz,m*m,&Y,m,&which,m,&hwork));
194
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
855 for (i=0;i<k;i++) which[i] = PETSC_TRUE;
195
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
380 PetscCall(STGetOperator(eps->st,&Op));
196
197
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
7125 for (j=k;j<m;j++) {
198
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
6745 PetscCall(BVSetActiveColumns(eps->V,0,m));
199
200 /* Lanczos step */
201
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
6745 PetscCall(BVMatMultColumn(eps->V,Op,j));
202 6745 which[j] = PETSC_TRUE;
203
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
6745 if (j-2>=k) which[j-2] = PETSC_FALSE;
204
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
6745 PetscCall(BVOrthogonalizeSomeColumn(eps->V,j+1,which,hwork,&norm,breakdown));
205 6745 alpha[j] = PetscRealPart(hwork[j]);
206 6745 beta[j] = norm;
207
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 10 times.
6745 if (PetscUnlikely(*breakdown)) {
208 *M = j+1;
209 break;
210 }
211
212 /* Compute eigenvalues and eigenvectors Y of the tridiagonal block */
213 6745 n = j-k+1;
214
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
70235 for (i=0;i<n;i++) {
215 63490 d[i] = alpha[i+k];
216 63490 e[i] = beta[i+k];
217 }
218
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
6745 PetscCall(DenseTridiagonal(n,d,e,ritz,Y));
219
220 /* Estimate ||A|| */
221
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
70235 for (i=0;i<n;i++)
222
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
63490 if (PetscAbsReal(ritz[i]) > anorm) anorm = PetscAbsReal(ritz[i]);
223
224 /* Compute nearly converged Ritz vectors */
225 nritzo = 0;
226
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
70235 for (i=0;i<n;i++) {
227
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
63490 if (norm*PetscAbsScalar(Y[i*n+n-1]) < PETSC_SQRT_MACHINE_EPSILON*anorm) nritzo++;
228 }
229
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
6745 if (nritzo>nritz) {
230 nritz = 0;
231
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
1780 for (i=0;i<n;i++) {
232
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
1555 if (norm*PetscAbsScalar(Y[i*n+n-1]) < PETSC_SQRT_MACHINE_EPSILON*anorm) {
233
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
345 PetscCall(BVSetActiveColumns(eps->V,k,k+n));
234
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
345 PetscCall(BVGetColumn(lanczos->AV,nritz,&av));
235
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
345 PetscCall(BVMultVec(eps->V,1.0,0.0,av,Y+i*n));
236
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
345 PetscCall(BVRestoreColumn(lanczos->AV,nritz,&av));
237 345 nritz++;
238 }
239 }
240 }
241
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
6745 if (nritz > 0) {
242
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
2510 PetscCall(BVGetColumn(eps->V,j+1,&vj1));
243
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
2510 PetscCall(BVSetActiveColumns(lanczos->AV,0,nritz));
244
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
2510 PetscCall(BVOrthogonalizeVec(lanczos->AV,vj1,hwork,&norm,breakdown));
245
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
2510 PetscCall(BVRestoreColumn(eps->V,j+1,&vj1));
246
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 10 times.
2510 if (PetscUnlikely(*breakdown)) {
247 *M = j+1;
248 break;
249 }
250 }
251
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
6745 PetscCall(BVScaleColumn(eps->V,j+1,1.0/norm));
252 }
253
254
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
380 PetscCall(STRestoreOperator(eps->st,&Op));
255
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
380 PetscCall(PetscFree6(d,e,ritz,Y,which,hwork));
256
6/12
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 2 times.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 2 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2 times.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✓ Branch 11 taken 2 times.
76 PetscFunctionReturn(PETSC_SUCCESS);
257 }
258
259 8050 static void update_omega(PetscReal *omega,PetscReal *omega_old,PetscInt j,PetscReal *alpha,PetscReal *beta,PetscReal eps1,PetscReal anorm)
260 {
261 8050 PetscInt k;
262 8050 PetscReal T,binv;
263
264
1/2
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
8050 PetscFunctionBegin;
265 /* Estimate of contribution to roundoff errors from A*v
266 fl(A*v) = A*v + f,
267 where ||f|| \approx eps1*||A||.
268 For a full matrix A, a rule-of-thumb estimate is eps1 = sqrt(n)*eps */
269 8050 T = eps1*anorm;
270 8050 binv = 1.0/beta[j+1];
271
272 /* Update omega(1) using omega(0)==0 */
273 8050 omega_old[0]= beta[1]*omega[1] + (alpha[0]-alpha[j])*omega[0] - beta[j]*omega_old[0];
274
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
8050 if (omega_old[0] > 0) omega_old[0] = binv*(omega_old[0] + T);
275 4835 else omega_old[0] = binv*(omega_old[0] - T);
276
277 /* Update remaining components */
278
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
73230 for (k=1;k<j-1;k++) {
279 65180 omega_old[k] = beta[k+1]*omega[k+1] + (alpha[k]-alpha[j])*omega[k] + beta[k]*omega[k-1] - beta[j]*omega_old[k];
280
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
65180 if (omega_old[k] > 0) omega_old[k] = binv*(omega_old[k] + T);
281 33929 else omega_old[k] = binv*(omega_old[k] - T);
282 }
283 8050 omega_old[j-1] = binv*T;
284
285 /* Swap omega and omega_old */
286
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
89150 for (k=0;k<j;k++) {
287 81100 omega[k] = omega_old[k];
288 81100 omega_old[k] = omega[k];
289 }
290 8050 omega[j] = eps1;
291
6/12
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 2 times.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 2 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2 times.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✓ Branch 11 taken 2 times.
8050 PetscFunctionReturnVoid();
292 }
293
294 505 static void compute_int(PetscBool *which,PetscReal *mu,PetscInt j,PetscReal delta,PetscReal eta)
295 {
296 505 PetscInt i,k,maxpos;
297 505 PetscReal max;
298 505 PetscBool found;
299
300
1/2
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
505 PetscFunctionBegin;
301 /* initialize which */
302 505 found = PETSC_FALSE;
303 505 maxpos = 0;
304 505 max = 0.0;
305
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
7990 for (i=0;i<j;i++) {
306
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
7485 if (PetscAbsReal(mu[i]) >= delta) {
307 1820 which[i] = PETSC_TRUE;
308 1820 found = PETSC_TRUE;
309 5665 } else which[i] = PETSC_FALSE;
310
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
7485 if (PetscAbsReal(mu[i]) > max) {
311 830 maxpos = i;
312 830 max = PetscAbsReal(mu[i]);
313 }
314 }
315
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 10 times.
505 if (!found) which[maxpos] = PETSC_TRUE;
316
317
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
7990 for (i=0;i<j;i++) {
318
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
7485 if (which[i]) {
319 /* find left interval */
320
1/2
✓ Branch 0 taken 10 times.
✗ Branch 1 not taken.
6560 for (k=i;k>=0;k--) {
321
2/4
✓ Branch 0 taken 10 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 10 times.
6560 if (PetscAbsReal(mu[k])<eta || which[k]) break;
322 else which[k] = PETSC_TRUE;
323 }
324 /* find right interval */
325
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
11300 for (k=i+1;k<j;k++) {
326
4/4
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
✓ Branch 2 taken 10 times.
✓ Branch 3 taken 10 times.
10980 if (PetscAbsReal(mu[k])<eta || which[k]) break;
327 4740 else which[k] = PETSC_TRUE;
328 }
329 }
330 }
331
6/12
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 2 times.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 2 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2 times.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✓ Branch 11 taken 2 times.
505 PetscFunctionReturnVoid();
332 }
333
334 /*
335 EPSPartialLanczos - Partial reorthogonalization.
336 */
337 760 static PetscErrorCode EPSPartialLanczos(EPS eps,PetscReal *alpha,PetscReal *beta,PetscInt k,PetscInt *M,PetscBool *breakdown,PetscReal anorm)
338 {
339 760 EPS_LANCZOS *lanczos = (EPS_LANCZOS*)eps->data;
340 760 PetscInt i,j,m = *M;
341 760 Mat Op;
342 760 PetscReal norm,*omega,lomega[100],*omega_old,lomega_old[100],eps1,delta,eta;
343 760 PetscBool *which,lwhich[100],*which2,lwhich2[100];
344 760 PetscBool reorth = PETSC_FALSE,force_reorth = PETSC_FALSE;
345 760 PetscBool fro = PETSC_FALSE,estimate_anorm = PETSC_FALSE;
346 760 PetscScalar *hwork,lhwork[100];
347
348
1/2
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
760 PetscFunctionBegin;
349
1/8
✗ Branch 0 not taken.
✓ Branch 1 taken 10 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
760 if (m>100) PetscCall(PetscMalloc5(m,&omega,m,&omega_old,m,&which,m,&which2,m,&hwork));
350 else {
351 760 omega = lomega;
352 760 omega_old = lomega_old;
353 760 which = lwhich;
354 760 which2 = lwhich2;
355 760 hwork = lhwork;
356 }
357
358 760 eps1 = PetscSqrtReal((PetscReal)eps->n)*PETSC_MACHINE_EPSILON/2;
359 760 delta = PETSC_SQRT_MACHINE_EPSILON/PetscSqrtReal((PetscReal)eps->ncv);
360 760 eta = PetscPowReal(PETSC_MACHINE_EPSILON,3.0/4.0)/PetscSqrtReal((PetscReal)eps->ncv);
361
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
760 if (anorm < 0.0) {
362 60 anorm = 1.0;
363 60 estimate_anorm = PETSC_TRUE;
364 }
365
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
76760 for (i=0;i<PetscMax(100,m);i++) omega[i] = omega_old[i] = 0.0;
366
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
1710 for (i=0;i<k;i++) which[i] = PETSC_TRUE;
367
368
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
760 PetscCall(BVSetActiveColumns(eps->V,0,m));
369
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
760 PetscCall(STGetOperator(eps->st,&Op));
370
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
14250 for (j=k;j<m;j++) {
371
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
13490 PetscCall(BVMatMultColumn(eps->V,Op,j));
372
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
13490 if (fro) {
373 /* Lanczos step with full reorthogonalization */
374
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
4680 PetscCall(BVOrthogonalizeColumn(eps->V,j+1,hwork,&norm,breakdown));
375 4680 alpha[j] = PetscRealPart(hwork[j]);
376 } else {
377 /* Lanczos step */
378 8810 which[j] = PETSC_TRUE;
379
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
8810 if (j-2>=k) which[j-2] = PETSC_FALSE;
380
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
8810 PetscCall(BVOrthogonalizeSomeColumn(eps->V,j+1,which,hwork,&norm,breakdown));
381 8810 alpha[j] = PetscRealPart(hwork[j]);
382 8810 beta[j] = norm;
383
384 /* Estimate ||A|| if needed */
385
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
8810 if (estimate_anorm) {
386
4/4
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
✓ Branch 2 taken 10 times.
✓ Branch 3 taken 10 times.
1140 if (j>k) anorm = PetscMax(anorm,PetscAbsReal(alpha[j])+norm+beta[j-1]);
387
1/2
✓ Branch 0 taken 10 times.
✗ Branch 1 not taken.
60 else anorm = PetscMax(anorm,PetscAbsReal(alpha[j])+norm);
388 }
389
390 /* Check if reorthogonalization is needed */
391 8810 reorth = PETSC_FALSE;
392
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
8810 if (j>k) {
393 8050 update_omega(omega,omega_old,j,alpha,beta-1,eps1,anorm);
394
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
87950 for (i=0;i<j-k;i++) {
395
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
71850 if (PetscAbsReal(omega[i]) > delta) reorth = PETSC_TRUE;
396 }
397 }
398
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
8810 if (reorth || force_reorth) {
399
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
2940 for (i=0;i<k;i++) which2[i] = PETSC_FALSE;
400
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
27790 for (i=k;i<=j;i++) which2[i] = PETSC_TRUE;
401
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
1660 if (lanczos->reorthog == EPS_LANCZOS_REORTHOG_PERIODIC) {
402 /* Periodic reorthogonalization */
403
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
820 if (force_reorth) force_reorth = PETSC_FALSE;
404 485 else force_reorth = PETSC_TRUE;
405
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
12880 for (i=0;i<j-k;i++) omega[i] = eps1;
406 } else {
407 /* Partial reorthogonalization */
408
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
840 if (force_reorth) force_reorth = PETSC_FALSE;
409 else {
410 505 force_reorth = PETSC_TRUE;
411 505 compute_int(which2+k,omega,j-k,delta,eta);
412
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
8495 for (i=0;i<j-k;i++) {
413
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
7485 if (which2[i+k]) omega[i] = eps1;
414 }
415 }
416 }
417
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
1660 PetscCall(BVOrthogonalizeSomeColumn(eps->V,j+1,which2,hwork,&norm,breakdown));
418 }
419 }
420
421
2/4
✓ Branch 0 taken 10 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 10 times.
13490 if (PetscUnlikely(*breakdown || norm < eps->n*anorm*PETSC_MACHINE_EPSILON)) {
422 *M = j+1;
423 break;
424 }
425
4/4
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
✓ Branch 2 taken 10 times.
✓ Branch 3 taken 10 times.
13490 if (!fro && norm*delta < anorm*eps1) {
426 280 fro = PETSC_TRUE;
427
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
280 PetscCall(PetscInfo(eps,"Switching to full reorthogonalization at iteration %" PetscInt_FMT "\n",eps->its));
428 }
429 13490 beta[j] = norm;
430
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
13490 PetscCall(BVScaleColumn(eps->V,j+1,1.0/norm));
431 }
432
433
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
760 PetscCall(STRestoreOperator(eps->st,&Op));
434
1/8
✗ Branch 0 not taken.
✓ Branch 1 taken 10 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
760 if (m>100) PetscCall(PetscFree5(omega,omega_old,which,which2,hwork));
435
6/12
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 2 times.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 2 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2 times.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✓ Branch 11 taken 2 times.
152 PetscFunctionReturn(PETSC_SUCCESS);
436 }
437
438 /*
439 EPSBasicLanczos - Computes an m-step Lanczos factorization. The first k
440 columns are assumed to be locked and therefore they are not modified. On
441 exit, the following relation is satisfied:
442
443 OP * V - V * T = f * e_m^T
444
445 where the columns of V are the Lanczos vectors, T is a tridiagonal matrix,
446 f is the residual vector and e_m is the m-th vector of the canonical basis.
447 The Lanczos vectors (together with vector f) are B-orthogonal (to working
448 accuracy) if full reorthogonalization is being used, otherwise they are
449 (B-)semi-orthogonal. On exit, beta contains the B-norm of f and the next
450 Lanczos vector can be computed as v_{m+1} = f / beta.
451
452 This function simply calls another function which depends on the selected
453 reorthogonalization strategy.
454 */
455 9489 static PetscErrorCode EPSBasicLanczos(EPS eps,PetscInt k,PetscInt *m,PetscReal *betam,PetscBool *breakdown,PetscReal anorm)
456 {
457 9489 EPS_LANCZOS *lanczos = (EPS_LANCZOS*)eps->data;
458 9489 PetscScalar *T;
459 9489 PetscInt i,n=*m,ld;
460 9489 PetscReal *alpha,*beta;
461 9489 BVOrthogRefineType orthog_ref;
462 9489 Mat Op,M;
463
464
1/2
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
9489 PetscFunctionBegin;
465
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
9489 PetscCall(DSGetLeadingDimension(eps->ds,&ld));
466
5/6
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
✓ Branch 2 taken 10 times.
✓ Branch 3 taken 10 times.
✓ Branch 4 taken 10 times.
✗ Branch 5 not taken.
9489 switch (lanczos->reorthog) {
467 5181 case EPS_LANCZOS_REORTHOG_LOCAL:
468
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
5181 PetscCall(DSGetArrayReal(eps->ds,DS_MAT_T,&alpha));
469 5181 beta = alpha + ld;
470
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
5181 PetscCall(EPSLocalLanczos(eps,alpha,beta,k,m,breakdown));
471 5181 *betam = beta[*m-1];
472
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
5181 PetscCall(DSRestoreArrayReal(eps->ds,DS_MAT_T,&alpha));
473 break;
474 2918 case EPS_LANCZOS_REORTHOG_FULL:
475
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
2918 PetscCall(STGetOperator(eps->st,&Op));
476
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
2918 PetscCall(DSGetMat(eps->ds,DS_MAT_T,&M));
477
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
2918 PetscCall(BVMatLanczos(eps->V,Op,M,k,m,betam,breakdown));
478
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
2918 PetscCall(DSRestoreMat(eps->ds,DS_MAT_T,&M));
479
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
2918 PetscCall(STRestoreOperator(eps->st,&Op));
480 break;
481 380 case EPS_LANCZOS_REORTHOG_SELECTIVE:
482
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
380 PetscCall(DSGetArrayReal(eps->ds,DS_MAT_T,&alpha));
483 380 beta = alpha + ld;
484
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
380 PetscCall(EPSSelectiveLanczos(eps,alpha,beta,k,m,breakdown,anorm));
485 380 *betam = beta[*m-1];
486
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
380 PetscCall(DSRestoreArrayReal(eps->ds,DS_MAT_T,&alpha));
487 break;
488 760 case EPS_LANCZOS_REORTHOG_PERIODIC:
489 case EPS_LANCZOS_REORTHOG_PARTIAL:
490
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
760 PetscCall(DSGetArrayReal(eps->ds,DS_MAT_T,&alpha));
491 760 beta = alpha + ld;
492
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
760 PetscCall(EPSPartialLanczos(eps,alpha,beta,k,m,breakdown,anorm));
493 760 *betam = beta[*m-1];
494
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
760 PetscCall(DSRestoreArrayReal(eps->ds,DS_MAT_T,&alpha));
495 break;
496 250 case EPS_LANCZOS_REORTHOG_DELAYED:
497
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
250 PetscCall(PetscMalloc1(n*n,&T));
498
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
250 PetscCall(BVGetOrthogonalization(eps->V,NULL,&orthog_ref,NULL,NULL));
499
1/8
✗ Branch 0 not taken.
✓ Branch 1 taken 10 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
250 if (orthog_ref == BV_ORTHOG_REFINE_NEVER) PetscCall(EPSDelayedArnoldi1(eps,T,n,k,m,betam,breakdown));
500
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
250 else PetscCall(EPSDelayedArnoldi(eps,T,n,k,m,betam,breakdown));
501 250 n = *m;
502
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
250 PetscCall(DSGetArrayReal(eps->ds,DS_MAT_T,&alpha));
503 250 beta = alpha + ld;
504
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
4375 for (i=k;i<n-1;i++) {
505 4125 alpha[i] = PetscRealPart(T[n*i+i]);
506 4125 beta[i] = PetscRealPart(T[n*i+i+1]);
507 }
508 250 alpha[n-1] = PetscRealPart(T[n*(n-1)+n-1]);
509 250 beta[n-1] = *betam;
510
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
250 PetscCall(DSRestoreArrayReal(eps->ds,DS_MAT_T,&alpha));
511
5/8
✓ Branch 0 taken 10 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2 times.
✓ Branch 3 taken 8 times.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✓ Branch 7 taken 2 times.
250 PetscCall(PetscFree(T));
512 break;
513 }
514
6/12
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 2 times.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 2 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2 times.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✓ Branch 11 taken 2 times.
1879 PetscFunctionReturn(PETSC_SUCCESS);
515 }
516
517 364 static PetscErrorCode EPSSolve_Lanczos(EPS eps)
518 {
519 364 EPS_LANCZOS *lanczos = (EPS_LANCZOS*)eps->data;
520 364 PetscInt nconv,i,j,k,l,x,n,*perm,restart,ncv=eps->ncv,r,ld;
521 364 Vec vi,vj,w;
522 364 Mat U;
523 364 PetscScalar *Y,*ritz,stmp;
524 364 PetscReal *bnd,anorm,beta,norm,rtmp,resnorm;
525 364 PetscBool breakdown;
526 364 char *conv,ctmp;
527
528
1/2
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
364 PetscFunctionBegin;
529
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
364 PetscCall(DSGetLeadingDimension(eps->ds,&ld));
530
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
364 PetscCall(PetscMalloc4(ncv,&ritz,ncv,&bnd,ncv,&perm,ncv,&conv));
531
532 /* The first Lanczos vector is the normalized initial vector */
533
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
364 PetscCall(EPSGetStartVector(eps,0,NULL));
534
535 anorm = -1.0;
536 nconv = 0;
537
538 /* Restart loop */
539 9853 while (eps->reason == EPS_CONVERGED_ITERATING) {
540 9489 eps->its++;
541
542 /* Compute an ncv-step Lanczos factorization */
543 9489 n = PetscMin(nconv+eps->mpd,ncv);
544
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
9489 PetscCall(DSSetDimensions(eps->ds,n,nconv,PETSC_DETERMINE));
545
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
9489 PetscCall(EPSBasicLanczos(eps,nconv,&n,&beta,&breakdown,anorm));
546
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
9489 PetscCall(DSSetDimensions(eps->ds,n,nconv,0));
547
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
9489 PetscCall(DSSetState(eps->ds,DS_STATE_INTERMEDIATE));
548
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
9489 PetscCall(BVSetActiveColumns(eps->V,nconv,n));
549
550 /* Solve projected problem */
551
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
9489 PetscCall(DSSolve(eps->ds,ritz,NULL));
552
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
9489 PetscCall(DSSort(eps->ds,ritz,NULL,NULL,NULL,NULL));
553
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
9489 PetscCall(DSSynchronize(eps->ds,ritz,NULL));
554
555 /* Estimate ||A|| */
556
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
135303 for (i=nconv;i<n;i++)
557
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
130092 anorm = PetscMax(anorm,PetscAbsReal(PetscRealPart(ritz[i])));
558
559 /* Compute residual norm estimates as beta*abs(Y(m,:)) + eps*||A|| */
560
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
9489 PetscCall(DSGetArray(eps->ds,DS_MAT_Q,&Y));
561
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
135303 for (i=nconv;i<n;i++) {
562 125814 resnorm = beta*PetscAbsScalar(Y[n-1+i*ld]) + PETSC_MACHINE_EPSILON*anorm;
563
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
125814 PetscCall((*eps->converged)(eps,ritz[i],eps->eigi[i],resnorm,&bnd[i],eps->convergedctx));
564
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
125814 if (bnd[i]<eps->tol) conv[i] = 'C';
565 124119 else conv[i] = 'N';
566 }
567
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
9489 PetscCall(DSRestoreArray(eps->ds,DS_MAT_Q,&Y));
568
569 /* purge repeated ritz values */
570
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
9489 if (lanczos->reorthog == EPS_LANCZOS_REORTHOG_LOCAL) {
571
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
70235 for (i=nconv+1;i<n;i++) {
572
4/4
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
✓ Branch 2 taken 10 times.
✓ Branch 3 taken 10 times.
65054 if (conv[i] == 'C' && PetscAbsScalar((ritz[i]-ritz[i-1])/ritz[i]) < eps->tol) conv[i] = 'R';
573 }
574 }
575
576 /* Compute restart vector */
577
6/8
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
✓ Branch 2 taken 2 times.
✓ Branch 3 taken 8 times.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✓ Branch 7 taken 2 times.
9489 if (breakdown) PetscCall(PetscInfo(eps,"Breakdown in Lanczos method (it=%" PetscInt_FMT " norm=%g)\n",eps->its,(double)beta));
578 else {
579 restart = nconv;
580
3/4
✓ Branch 0 taken 10 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 10 times.
✓ Branch 3 taken 10 times.
10960 while (restart<n && conv[restart] != 'N') restart++;
581
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 10 times.
9479 if (restart >= n) {
582 breakdown = PETSC_TRUE;
583 } else {
584
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
124153 for (i=restart+1;i<n;i++) {
585
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
114674 if (conv[i] == 'N') {
586
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
114640 PetscCall(SlepcSCCompare(eps->sc,ritz[restart],0.0,ritz[i],0.0,&r));
587
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
114640 if (r>0) restart = i;
588 }
589 }
590
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
9479 PetscCall(DSGetArray(eps->ds,DS_MAT_Q,&Y));
591
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
9479 PetscCall(BVMultColumn(eps->V,1.0,0.0,n,Y+restart*ld+nconv));
592
4/6
✓ Branch 0 taken 9 times.
✓ Branch 1 taken 1 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
9479 PetscCall(DSRestoreArray(eps->ds,DS_MAT_Q,&Y));
593 }
594 }
595
596 /* Count and put converged eigenvalues first */
597
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
135303 for (i=nconv;i<n;i++) perm[i] = i;
598
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
11160 for (k=nconv;k<n;k++) {
599
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
11150 if (conv[perm[k]] != 'C') {
600 9506 j = k + 1;
601
4/4
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
✓ Branch 2 taken 10 times.
✓ Branch 3 taken 10 times.
124204 while (j<n && conv[perm[j]] != 'C') j++;
602
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
9506 if (j>=n) break;
603 27 l = perm[k]; perm[k] = perm[j]; perm[j] = l;
604 }
605 }
606
607 /* Sort eigenvectors according to permutation */
608
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
9489 PetscCall(DSGetArray(eps->ds,DS_MAT_Q,&Y));
609
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
11160 for (i=nconv;i<k;i++) {
610 1671 x = perm[i];
611
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
1671 if (x != i) {
612 27 j = i + 1;
613
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
61 while (perm[j] != i) j++;
614 /* swap eigenvalues i and j */
615 27 stmp = ritz[x]; ritz[x] = ritz[i]; ritz[i] = stmp;
616 27 rtmp = bnd[x]; bnd[x] = bnd[i]; bnd[i] = rtmp;
617 27 ctmp = conv[x]; conv[x] = conv[i]; conv[i] = ctmp;
618 27 perm[j] = x; perm[i] = i;
619 /* swap eigenvectors i and j */
620
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
540 for (l=0;l<n;l++) {
621 513 stmp = Y[l+x*ld]; Y[l+x*ld] = Y[l+i*ld]; Y[l+i*ld] = stmp;
622 }
623 }
624 }
625
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
9489 PetscCall(DSRestoreArray(eps->ds,DS_MAT_Q,&Y));
626
627 /* compute converged eigenvectors */
628
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
9489 PetscCall(DSGetMat(eps->ds,DS_MAT_Q,&U));
629
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
9489 PetscCall(BVMultInPlace(eps->V,U,nconv,k));
630
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
9489 PetscCall(DSRestoreMat(eps->ds,DS_MAT_Q,&U));
631
632 /* purge spurious ritz values */
633
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
9489 if (lanczos->reorthog == EPS_LANCZOS_REORTHOG_LOCAL) {
634
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
5926 for (i=nconv;i<k;i++) {
635
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
745 PetscCall(BVGetColumn(eps->V,i,&vi));
636
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
745 PetscCall(VecNorm(vi,NORM_2,&norm));
637
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
745 PetscCall(VecScale(vi,1.0/norm));
638 745 w = eps->work[0];
639
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
745 PetscCall(STApply(eps->st,vi,w));
640
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
745 PetscCall(VecAXPY(w,-ritz[i],vi));
641
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
745 PetscCall(BVRestoreColumn(eps->V,i,&vi));
642
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
745 PetscCall(VecNorm(w,NORM_2,&norm));
643
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
745 PetscCall((*eps->converged)(eps,ritz[i],eps->eigi[i],norm,&bnd[i],eps->convergedctx));
644
2/2
✓ Branch 0 taken 5 times.
✓ Branch 1 taken 10 times.
745 if (bnd[i]>=eps->tol) conv[i] = 'S';
645 }
646
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
5921 for (i=nconv;i<k;i++) {
647
2/2
✓ Branch 0 taken 5 times.
✓ Branch 1 taken 10 times.
745 if (conv[i] != 'C') {
648 5 j = i + 1;
649
1/4
✗ Branch 0 not taken.
✓ Branch 1 taken 5 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
5 while (j<k && conv[j] != 'C') j++;
650
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 5 times.
5 if (j>=k) break;
651 /* swap eigenvalues i and j */
652 stmp = ritz[j]; ritz[j] = ritz[i]; ritz[i] = stmp;
653 rtmp = bnd[j]; bnd[j] = bnd[i]; bnd[i] = rtmp;
654 ctmp = conv[j]; conv[j] = conv[i]; conv[i] = ctmp;
655 /* swap eigenvectors i and j */
656 PetscCall(BVGetColumn(eps->V,i,&vi));
657 PetscCall(BVGetColumn(eps->V,j,&vj));
658 PetscCall(VecSwap(vi,vj));
659 PetscCall(BVRestoreColumn(eps->V,i,&vi));
660
0/6
✗ Branch 0 not taken.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
740 PetscCall(BVRestoreColumn(eps->V,j,&vj));
661 }
662 }
663 k = i;
664 }
665
666 /* store ritz values and estimated errors */
667
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
135303 for (i=nconv;i<n;i++) {
668 125814 eps->eigr[i] = ritz[i];
669 125814 eps->errest[i] = bnd[i];
670 }
671 9489 nconv = k;
672
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
9489 PetscCall(EPSMonitor(eps,eps->its,nconv,eps->eigr,eps->eigi,eps->errest,n));
673
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
9489 PetscCall((*eps->stopping)(eps,eps->its,eps->max_it,nconv,eps->nev,&eps->reason,eps->stoppingctx));
674
675
2/2
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
9489 if (eps->reason == EPS_CONVERGED_ITERATING) { /* copy restart vector */
676
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
9125 PetscCall(BVCopyColumn(eps->V,n,nconv));
677
3/4
✓ Branch 0 taken 10 times.
✓ Branch 1 taken 10 times.
✓ Branch 2 taken 10 times.
✗ Branch 3 not taken.
9125 if (lanczos->reorthog == EPS_LANCZOS_REORTHOG_LOCAL && !breakdown) {
678 /* Reorthonormalize restart vector */
679
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
5001 PetscCall(BVOrthonormalizeColumn(eps->V,nconv,PETSC_FALSE,NULL,&breakdown));
680 }
681
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 10 times.
9125 if (breakdown) {
682 /* Use random vector for restarting */
683 PetscCall(PetscInfo(eps,"Using random vector for restart\n"));
684 PetscCall(EPSGetStartVector(eps,nconv,&breakdown));
685 }
686
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 10 times.
9125 if (PetscUnlikely(breakdown)) { /* give up */
687 eps->reason = EPS_DIVERGED_BREAKDOWN;
688
4/8
✗ Branch 0 not taken.
✗ Branch 1 not taken.
✓ Branch 2 taken 8 times.
✓ Branch 3 taken 8 times.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
✓ Branch 6 taken 2 times.
✓ Branch 7 taken 2 times.
9853 PetscCall(PetscInfo(eps,"Unable to generate more start vectors\n"));
689 }
690 }
691 }
692 364 eps->nconv = nconv;
693
694
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
364 PetscCall(PetscFree4(ritz,bnd,perm,conv));
695
6/12
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 2 times.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 2 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2 times.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✓ Branch 11 taken 2 times.
72 PetscFunctionReturn(PETSC_SUCCESS);
696 }
697
698 184 static PetscErrorCode EPSSetFromOptions_Lanczos(EPS eps,PetscOptionItems PetscOptionsObject)
699 {
700 184 EPS_LANCZOS *lanczos = (EPS_LANCZOS*)eps->data;
701 184 PetscBool flg;
702 184 EPSLanczosReorthogType reorthog=EPS_LANCZOS_REORTHOG_LOCAL,curval;
703
704
1/2
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
184 PetscFunctionBegin;
705
1/12
✗ Branch 0 not taken.
✓ Branch 1 taken 10 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
✗ Branch 8 not taken.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✗ Branch 11 not taken.
184 PetscOptionsHeadBegin(PetscOptionsObject,"EPS Lanczos Options");
706
707
1/2
✗ Branch 0 not taken.
✓ Branch 1 taken 10 times.
184 curval = (lanczos->reorthog==(EPSLanczosReorthogType)-1)? EPS_LANCZOS_REORTHOG_LOCAL: lanczos->reorthog;
708
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
184 PetscCall(PetscOptionsEnum("-eps_lanczos_reorthog","Lanczos reorthogonalization","EPSLanczosSetReorthog",EPSLanczosReorthogTypes,(PetscEnum)curval,(PetscEnum*)&reorthog,&flg));
709
5/8
✓ Branch 0 taken 10 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2 times.
✓ Branch 3 taken 8 times.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✓ Branch 7 taken 2 times.
184 if (flg) PetscCall(EPSLanczosSetReorthog(eps,reorthog));
710
711
1/14
✗ Branch 0 not taken.
✓ Branch 1 taken 2 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
✗ Branch 8 not taken.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✗ Branch 11 not taken.
✗ Branch 12 not taken.
✗ Branch 13 not taken.
184 PetscOptionsHeadEnd();
712
6/12
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 2 times.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 2 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2 times.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✓ Branch 11 taken 2 times.
36 PetscFunctionReturn(PETSC_SUCCESS);
713 }
714
715 194 static PetscErrorCode EPSLanczosSetReorthog_Lanczos(EPS eps,EPSLanczosReorthogType reorthog)
716 {
717 194 EPS_LANCZOS *lanczos = (EPS_LANCZOS*)eps->data;
718
719
1/2
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
194 PetscFunctionBegin;
720
1/2
✓ Branch 0 taken 10 times.
✗ Branch 1 not taken.
194 switch (reorthog) {
721 194 case EPS_LANCZOS_REORTHOG_LOCAL:
722 case EPS_LANCZOS_REORTHOG_FULL:
723 case EPS_LANCZOS_REORTHOG_DELAYED:
724 case EPS_LANCZOS_REORTHOG_SELECTIVE:
725 case EPS_LANCZOS_REORTHOG_PERIODIC:
726 case EPS_LANCZOS_REORTHOG_PARTIAL:
727
1/2
✓ Branch 0 taken 10 times.
✗ Branch 1 not taken.
194 if (lanczos->reorthog != reorthog) {
728 194 lanczos->reorthog = reorthog;
729 194 eps->state = EPS_STATE_INITIAL;
730 }
731 38 break;
732 default:
733 SETERRQ(PetscObjectComm((PetscObject)eps),PETSC_ERR_ARG_OUTOFRANGE,"Invalid reorthogonalization type");
734 }
735
6/12
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 2 times.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 2 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2 times.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✓ Branch 11 taken 2 times.
38 PetscFunctionReturn(PETSC_SUCCESS);
736 }
737
738 /*@
739 EPSLanczosSetReorthog - Sets the type of reorthogonalization used during the Lanczos
740 iteration.
741
742 Logically Collective
743
744 Input Parameters:
745 + eps - the linear eigensolver context
746 - reorthog - the type of reorthogonalization, see `EPSLanczosReorthogType` for possible values
747
748 Options Database Key:
749 . -eps_lanczos_reorthog (local|full|selective|periodic|partial|delayed) - sets the reorthogonalization type
750
751 Notes:
752 Details of the different reorthogonalization strategies can be found in
753 {cite:p}`Her06`.
754
755 This applies to `EPSLANCZOS`, not to `EPSKRYLOVSCHUR`.
756
757 Level: advanced
758
759 .seealso: [](ch:eps), `EPSLANCZOS`, `EPSLanczosGetReorthog()`, `EPSLanczosReorthogType`
760 @*/
761 194 PetscErrorCode EPSLanczosSetReorthog(EPS eps,EPSLanczosReorthogType reorthog)
762 {
763
1/2
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
194 PetscFunctionBegin;
764
3/16
✗ Branch 0 not taken.
✓ Branch 1 taken 2 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
✗ Branch 8 not taken.
✓ Branch 9 taken 2 times.
✗ Branch 10 not taken.
✗ Branch 11 not taken.
✗ Branch 12 not taken.
✗ Branch 13 not taken.
✗ Branch 14 not taken.
✗ Branch 15 not taken.
194 PetscValidHeaderSpecific(eps,EPS_CLASSID,1);
765
27/62
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 2 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 2 times.
✗ Branch 11 not taken.
✗ Branch 12 not taken.
✓ Branch 13 taken 2 times.
✗ Branch 14 not taken.
✓ Branch 15 taken 2 times.
✓ Branch 16 taken 2 times.
✗ Branch 17 not taken.
✗ Branch 18 not taken.
✓ Branch 19 taken 2 times.
✓ Branch 20 taken 2 times.
✗ Branch 21 not taken.
✗ Branch 22 not taken.
✓ Branch 23 taken 2 times.
✓ Branch 24 taken 2 times.
✗ Branch 25 not taken.
✗ Branch 26 not taken.
✓ Branch 27 taken 2 times.
✓ Branch 28 taken 2 times.
✗ Branch 29 not taken.
✗ Branch 30 not taken.
✓ Branch 31 taken 2 times.
✓ Branch 32 taken 2 times.
✗ Branch 33 not taken.
✓ Branch 34 taken 2 times.
✗ Branch 35 not taken.
✗ Branch 36 not taken.
✓ Branch 37 taken 2 times.
✗ Branch 38 not taken.
✗ Branch 39 not taken.
✗ Branch 40 not taken.
✓ Branch 41 taken 2 times.
✗ Branch 42 not taken.
✗ Branch 43 not taken.
✗ Branch 44 not taken.
✓ Branch 45 taken 2 times.
✓ Branch 46 taken 2 times.
✗ Branch 47 not taken.
✗ Branch 48 not taken.
✓ Branch 49 taken 2 times.
✓ Branch 50 taken 2 times.
✗ Branch 51 not taken.
✓ Branch 52 taken 2 times.
✗ Branch 53 not taken.
✗ Branch 54 not taken.
✓ Branch 55 taken 2 times.
✗ Branch 56 not taken.
✗ Branch 57 not taken.
✗ Branch 58 not taken.
✓ Branch 59 taken 2 times.
✗ Branch 60 not taken.
✗ Branch 61 not taken.
194 PetscValidLogicalCollectiveEnum(eps,reorthog,2);
766
8/14
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 10 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 10 times.
✓ Branch 6 taken 2 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2 times.
✗ Branch 9 not taken.
✓ Branch 10 taken 2 times.
✗ Branch 11 not taken.
✗ Branch 12 not taken.
✓ Branch 13 taken 2 times.
194 PetscTryMethod(eps,"EPSLanczosSetReorthog_C",(EPS,EPSLanczosReorthogType),(eps,reorthog));
767
6/12
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 2 times.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 2 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2 times.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✓ Branch 11 taken 2 times.
194 PetscFunctionReturn(PETSC_SUCCESS);
768 }
769
770 50 static PetscErrorCode EPSLanczosGetReorthog_Lanczos(EPS eps,EPSLanczosReorthogType *reorthog)
771 {
772 50 EPS_LANCZOS *lanczos = (EPS_LANCZOS*)eps->data;
773
774
1/2
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
50 PetscFunctionBegin;
775 50 *reorthog = lanczos->reorthog;
776
6/12
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 2 times.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 2 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2 times.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✓ Branch 11 taken 2 times.
50 PetscFunctionReturn(PETSC_SUCCESS);
777 }
778
779 /*@
780 EPSLanczosGetReorthog - Gets the type of reorthogonalization used during
781 the Lanczos iteration.
782
783 Not Collective
784
785 Input Parameter:
786 . eps - the linear eigensolver context
787
788 Output Parameter:
789 . reorthog - the type of reorthogonalization
790
791 Level: advanced
792
793 .seealso: [](ch:eps), `EPSLANCZOS`, `EPSLanczosSetReorthog()`, `EPSLanczosReorthogType`
794 @*/
795 50 PetscErrorCode EPSLanczosGetReorthog(EPS eps,EPSLanczosReorthogType *reorthog)
796 {
797
1/2
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
50 PetscFunctionBegin;
798
3/16
✗ Branch 0 not taken.
✓ Branch 1 taken 2 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
✗ Branch 8 not taken.
✓ Branch 9 taken 2 times.
✗ Branch 10 not taken.
✗ Branch 11 not taken.
✗ Branch 12 not taken.
✗ Branch 13 not taken.
✗ Branch 14 not taken.
✗ Branch 15 not taken.
50 PetscValidHeaderSpecific(eps,EPS_CLASSID,1);
799
2/8
✗ Branch 0 not taken.
✓ Branch 1 taken 2 times.
✗ Branch 2 not taken.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
✗ Branch 6 not taken.
✗ Branch 7 not taken.
50 PetscAssertPointer(reorthog,2);
800
9/16
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✓ Branch 3 taken 8 times.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
✗ Branch 6 not taken.
✓ Branch 7 taken 10 times.
✗ Branch 8 not taken.
✗ Branch 9 not taken.
✓ Branch 10 taken 2 times.
✗ Branch 11 not taken.
✓ Branch 12 taken 2 times.
✗ Branch 13 not taken.
✗ Branch 14 not taken.
✓ Branch 15 taken 2 times.
50 PetscUseMethod(eps,"EPSLanczosGetReorthog_C",(EPS,EPSLanczosReorthogType*),(eps,reorthog));
801
6/12
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 2 times.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 2 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2 times.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✓ Branch 11 taken 2 times.
50 PetscFunctionReturn(PETSC_SUCCESS);
802 }
803
804 224 static PetscErrorCode EPSReset_Lanczos(EPS eps)
805 {
806 224 EPS_LANCZOS *lanczos = (EPS_LANCZOS*)eps->data;
807
808
1/2
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
224 PetscFunctionBegin;
809
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
224 PetscCall(BVDestroy(&lanczos->AV));
810 224 lanczos->allocsize = 0;
811
6/12
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 2 times.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 2 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2 times.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✓ Branch 11 taken 2 times.
224 PetscFunctionReturn(PETSC_SUCCESS);
812 }
813
814 194 static PetscErrorCode EPSDestroy_Lanczos(EPS eps)
815 {
816
1/2
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
194 PetscFunctionBegin;
817
5/8
✓ Branch 0 taken 10 times.
✗ Branch 1 not taken.
✓ Branch 2 taken 2 times.
✓ Branch 3 taken 8 times.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
✗ Branch 6 not taken.
✓ Branch 7 taken 2 times.
194 PetscCall(PetscFree(eps->data));
818
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
194 PetscCall(PetscObjectComposeFunction((PetscObject)eps,"EPSLanczosSetReorthog_C",NULL));
819
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
194 PetscCall(PetscObjectComposeFunction((PetscObject)eps,"EPSLanczosGetReorthog_C",NULL));
820
6/12
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 2 times.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 2 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2 times.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✓ Branch 11 taken 2 times.
38 PetscFunctionReturn(PETSC_SUCCESS);
821 }
822
823 static PetscErrorCode EPSView_Lanczos(EPS eps,PetscViewer viewer)
824 {
825 EPS_LANCZOS *lanczos = (EPS_LANCZOS*)eps->data;
826 PetscBool isascii;
827
828 PetscFunctionBegin;
829 PetscCall(PetscObjectTypeCompare((PetscObject)viewer,PETSCVIEWERASCII,&isascii));
830 if (isascii) {
831 if (lanczos->reorthog != (EPSLanczosReorthogType)-1) PetscCall(PetscViewerASCIIPrintf(viewer," %s reorthogonalization\n",EPSLanczosReorthogTypes[lanczos->reorthog]));
832 }
833 PetscFunctionReturn(PETSC_SUCCESS);
834 }
835
836 /*MC
837 EPSLANCZOS - EPSLANCZOS = "lanczos" - A basic Krylov method for Hermitian
838 problems, with explicit restart.
839
840 Notes:
841 This solver is very basic and is not recommended in general, since it
842 will not be competitive with respect to other solvers.
843
844 The implemented method is Lanczos with explicit restart and deflation.
845 Generally, it is much better to use Lanczos with implicit restart (also
846 known as thick-restart Lanczos) as implemented in `EPSKRYLOVSCHUR`.
847
848 Several reorthogonalization strategies can be selected with `EPSLanczosSetReorthog()`.
849 Some of them may result in a cheaper computation, but it will seldom be
850 enough to beat `EPSKRYLOVSCHUR`.
851
852 Level: beginner
853
854 .seealso: [](ch:eps), `EPS`, `EPSType`, `EPSSetType()`, `EPSLanczosSetReorthog()`
855 M*/
856 194 SLEPC_EXTERN PetscErrorCode EPSCreate_Lanczos(EPS eps)
857 {
858 194 EPS_LANCZOS *ctx;
859
860
1/2
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
194 PetscFunctionBegin;
861
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
194 PetscCall(PetscNew(&ctx));
862 194 eps->data = (void*)ctx;
863 194 ctx->reorthog = (EPSLanczosReorthogType)-1;
864
865 194 eps->useds = PETSC_TRUE;
866
867 194 eps->ops->solve = EPSSolve_Lanczos;
868 194 eps->ops->setup = EPSSetUp_Lanczos;
869 194 eps->ops->setupsort = EPSSetUpSort_Default;
870 194 eps->ops->setfromoptions = EPSSetFromOptions_Lanczos;
871 194 eps->ops->destroy = EPSDestroy_Lanczos;
872 194 eps->ops->reset = EPSReset_Lanczos;
873 194 eps->ops->view = EPSView_Lanczos;
874 194 eps->ops->backtransform = EPSBackTransform_Default;
875 194 eps->ops->computevectors = EPSComputeVectors_Hermitian;
876
877
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
194 PetscCall(PetscObjectComposeFunction((PetscObject)eps,"EPSLanczosSetReorthog_C",EPSLanczosSetReorthog_Lanczos));
878
4/6
✓ Branch 0 taken 2 times.
✓ Branch 1 taken 8 times.
✓ Branch 2 taken 2 times.
✗ Branch 3 not taken.
✗ Branch 4 not taken.
✓ Branch 5 taken 2 times.
194 PetscCall(PetscObjectComposeFunction((PetscObject)eps,"EPSLanczosGetReorthog_C",EPSLanczosGetReorthog_Lanczos));
879
6/12
✓ Branch 0 taken 2 times.
✗ Branch 1 not taken.
✗ Branch 2 not taken.
✓ Branch 3 taken 2 times.
✓ Branch 4 taken 2 times.
✗ Branch 5 not taken.
✓ Branch 6 taken 2 times.
✗ Branch 7 not taken.
✓ Branch 8 taken 2 times.
✗ Branch 9 not taken.
✗ Branch 10 not taken.
✓ Branch 11 taken 2 times.
38 PetscFunctionReturn(PETSC_SUCCESS);
880 }
881