Subversion Repositories slepc-dev

Rev

Go to most recent revision | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
535 dsic.upv.es!jroman 1
/*                      
6 dsic.upv.es!jroman 2
 
535 dsic.upv.es!jroman 3
   SLEPc eigensolver: "subspace"
4
 
5
   Method: Subspace Iteration
6
 
7
   Algorithm:
8
 
953 dsic.upv.es!jroman 9
       Subspace iteration with Rayleigh-Ritz projection and locking,
10
       based on the SRRIT implementation.
535 dsic.upv.es!jroman 11
 
12
   References:
13
 
953 dsic.upv.es!jroman 14
       [1] "Subspace Iteration in SLEPc", SLEPc Technical Report STR-3,
15
           available at http://www.grycap.upv.es/slepc.
535 dsic.upv.es!jroman 16
 
17
   Last update: June 2004
18
 
1376 slepc 19
   - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
20
      SLEPc - Scalable Library for Eigenvalue Problem Computations
21
      Copyright (c) 2002-2007, Universidad Politecnica de Valencia, Spain
22
 
23
      This file is part of SLEPc. See the README file for conditions of use
24
      and additional information.
25
   - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
535 dsic.upv.es!jroman 26
*/
1376 slepc 27
 
62 dsic.upv.es!antodo 28
#include "src/eps/epsimpl.h"                /*I "slepceps.h" I*/
470 dsic.upv.es!antodo 29
#include "slepcblaslapack.h"
6 dsic.upv.es!jroman 30
 
31
#undef __FUNCT__  
32
#define __FUNCT__ "EPSSetUp_SUBSPACE"
476 dsic.upv.es!antodo 33
PetscErrorCode EPSSetUp_SUBSPACE(EPS eps)
6 dsic.upv.es!jroman 34
{
476 dsic.upv.es!antodo 35
  PetscErrorCode ierr;
982 slepc 36
  PetscInt       N;
6 dsic.upv.es!jroman 37
 
38
  PetscFunctionBegin;
1343 slepc 39
  ierr = VecGetSize(eps->IV[0],&N);CHKERRQ(ierr);
6 dsic.upv.es!jroman 40
  if (eps->ncv) {
41
    if (eps->ncv<eps->nev) SETERRQ(1,"The value of ncv must be at least nev");
42
  }
651 dsic.upv.es!antodo 43
  else eps->ncv = PetscMin(N,PetscMax(2*eps->nev,eps->nev+15));
1220 slepc 44
  if (!eps->max_it) eps->max_it = PetscMax(100,2*N/eps->ncv);
259 dsic.upv.es!antodo 45
  if (eps->which!=EPS_LARGEST_MAGNITUDE)
46
    SETERRQ(1,"Wrong value of eps->which");
47
  ierr = EPSAllocateSolution(eps);CHKERRQ(ierr);
1040 slepc 48
  ierr = PetscFree(eps->T);CHKERRQ(ierr);
508 dsic.upv.es!antodo 49
  ierr = PetscMalloc(eps->ncv*eps->ncv*sizeof(PetscScalar),&eps->T);CHKERRQ(ierr);
432 dsic.upv.es!antodo 50
  ierr = EPSDefaultGetWork(eps,eps->ncv);CHKERRQ(ierr);
6 dsic.upv.es!jroman 51
  PetscFunctionReturn(0);
52
}
53
 
54
#undef __FUNCT__  
535 dsic.upv.es!jroman 55
#define __FUNCT__ "EPSHessCond"
56
/*
57
   EPSHessCond - Compute the inf-norm condition number of the upper
58
   Hessenberg matrix H: cond(H) = norm(H)*norm(inv(H)).
59
   This routine uses Gaussian elimination with partial pivoting to
60
   compute the inverse explicitly.
61
*/
62
static PetscErrorCode EPSHessCond(PetscScalar* H,int n, PetscReal* cond)
6 dsic.upv.es!jroman 63
{
806 dsic.upv.es!antodo 64
#if defined(PETSC_MISSING_LAPACK_GETRF) || defined(SLEPC_MISSING_LAPACK_GETRI) || defined(SLEPC_MISSING_LAPACK_LANGE) || defined(SLEPC_MISSING_LAPACK_LANHS)
817 dsic.upv.es!antodo 65
  PetscFunctionBegin;
806 dsic.upv.es!antodo 66
  SETERRQ(PETSC_ERR_SUP,"GETRF,GETRI - Lapack routines are unavailable.");
67
#else
476 dsic.upv.es!antodo 68
  PetscErrorCode ierr;
69
  int            *ipiv,lwork,info;
70
  PetscScalar    *work;
71
  PetscReal      hn,hin,*rwork;
470 dsic.upv.es!antodo 72
 
6 dsic.upv.es!jroman 73
  PetscFunctionBegin;
1339 slepc 74
  ierr = PetscLogEventBegin(EPS_Dense,0,0,0,0);CHKERRQ(ierr);
470 dsic.upv.es!antodo 75
  ierr = PetscMalloc(sizeof(int)*n,&ipiv);CHKERRQ(ierr);
76
  lwork = n*n;
77
  ierr = PetscMalloc(sizeof(PetscScalar)*lwork,&work);CHKERRQ(ierr);
78
  ierr = PetscMalloc(sizeof(PetscReal)*n,&rwork);CHKERRQ(ierr);
784 dsic.upv.es!antodo 79
  hn = LAPACKlanhs_("I",&n,H,&n,rwork,1);
80
  LAPACKgetrf_(&n,&n,H,&n,ipiv,&info);
476 dsic.upv.es!antodo 81
  if (info) SETERRQ1(PETSC_ERR_LIB,"Error in Lapack xGETRF %d",info);
784 dsic.upv.es!antodo 82
  LAPACKgetri_(&n,H,&n,ipiv,work,&lwork,&info);
476 dsic.upv.es!antodo 83
  if (info) SETERRQ1(PETSC_ERR_LIB,"Error in Lapack xGETRI %d",info);
784 dsic.upv.es!antodo 84
  hin = LAPACKlange_("I",&n,&n,H,&n,rwork,1);
470 dsic.upv.es!antodo 85
  *cond = hn * hin;
86
  ierr = PetscFree(ipiv);CHKERRQ(ierr);
87
  ierr = PetscFree(work);CHKERRQ(ierr);
88
  ierr = PetscFree(rwork);CHKERRQ(ierr);
1339 slepc 89
  ierr = PetscLogEventEnd(EPS_Dense,0,0,0,0);CHKERRQ(ierr);
470 dsic.upv.es!antodo 90
  PetscFunctionReturn(0);
806 dsic.upv.es!antodo 91
#endif
470 dsic.upv.es!antodo 92
}
6 dsic.upv.es!jroman 93
 
470 dsic.upv.es!antodo 94
#undef __FUNCT__  
535 dsic.upv.es!jroman 95
#define __FUNCT__ "EPSFindGroup"
96
/*
97
   EPSFindGroup - Find a group of nearly equimodular eigenvalues, provided
98
   in arrays wr and wi, according to the tolerance grptol. Also the 2-norms
99
   of the residuals must be passed-in (rsd). Arrays are processed from index
100
   l to index m only. The output information is:
101
 
102
   ngrp - number of entries of the group
893 dsic.upv.es!jroman 103
   ctr  - (w(l)+w(l+ngrp-1))/2
535 dsic.upv.es!jroman 104
   ae   - average of wr(l),...,wr(l+ngrp-1)
105
   arsd - average of rsd(l),...,rsd(l+ngrp-1)
106
*/
107
static PetscErrorCode EPSFindGroup(int l,int m,PetscScalar *wr,PetscScalar *wi,PetscReal *rsd,
470 dsic.upv.es!antodo 108
  PetscReal grptol,int *ngrp,PetscReal *ctr,PetscReal *ae,PetscReal *arsd)
109
{
110
  int       i;
111
  PetscReal rmod,rmod1;
6 dsic.upv.es!jroman 112
 
470 dsic.upv.es!antodo 113
  PetscFunctionBegin;
114
  *ngrp = 0;
115
  *ctr = 0;
116
 
504 dsic.upv.es!antodo 117
  rmod = SlepcAbsEigenvalue(wr[l],wi[l]);
6 dsic.upv.es!jroman 118
 
470 dsic.upv.es!antodo 119
  for (i=l;i<m;) {
504 dsic.upv.es!antodo 120
    rmod1 = SlepcAbsEigenvalue(wr[i],wi[i]);
470 dsic.upv.es!antodo 121
    if (PetscAbsReal(rmod-rmod1) > grptol*(rmod+rmod1)) break;
122
    *ctr = (rmod+rmod1)/2.0;
123
    if (wi[i] != 0.0) {
124
      (*ngrp)+=2;
125
      i+=2;
126
    } else {
127
      (*ngrp)++;
128
      i++;
6 dsic.upv.es!jroman 129
    }
470 dsic.upv.es!antodo 130
  }
6 dsic.upv.es!jroman 131
 
470 dsic.upv.es!antodo 132
  *ae = 0;
133
  *arsd = 0;
6 dsic.upv.es!jroman 134
 
470 dsic.upv.es!antodo 135
  if (*ngrp) {
136
    for (i=l;i<l+*ngrp;i++) {
137
      (*ae) += PetscRealPart(wr[i]);
138
      (*arsd) += rsd[i]*rsd[i];
6 dsic.upv.es!jroman 139
    }
470 dsic.upv.es!antodo 140
    *ae = *ae / *ngrp;
141
    *arsd = PetscSqrtScalar(*arsd / *ngrp);
6 dsic.upv.es!jroman 142
  }
143
  PetscFunctionReturn(0);
144
}
145
 
146
#undef __FUNCT__  
470 dsic.upv.es!antodo 147
#define __FUNCT__ "EPSSchurResidualNorms"
535 dsic.upv.es!jroman 148
/*
149
   EPSSchurResidualNorms - Computes the column norms of residual vectors
150
   OP*V(1:n,l:m) - V*T(1:m,l:m) were on entry, OP*V has been computed and
151
   stored in AV. ldt is the leading dimension of T. On exit, rsd(l) to
152
   rsd(m) contain the computed norms.
153
*/
476 dsic.upv.es!antodo 154
static PetscErrorCode EPSSchurResidualNorms(EPS eps,Vec *V,Vec *AV,PetscScalar *T,int l,int m,int ldt,PetscReal *rsd)
6 dsic.upv.es!jroman 155
{
476 dsic.upv.es!antodo 156
  PetscErrorCode ierr;
157
  int            i;
470 dsic.upv.es!antodo 158
#if defined(PETSC_USE_COMPLEX)
476 dsic.upv.es!antodo 159
  PetscScalar    t;
470 dsic.upv.es!antodo 160
#endif
6 dsic.upv.es!jroman 161
 
162
  PetscFunctionBegin;
470 dsic.upv.es!antodo 163
  for (i=l;i<m;i++) {
828 dsic.upv.es!antodo 164
    ierr = VecSet(eps->work[0],0.0);CHKERRQ(ierr);
165
    ierr = VecMAXPY(eps->work[0],m,T+ldt*i,V);CHKERRQ(ierr);
166
    ierr = VecWAXPY(eps->work[1],-1.0,eps->work[0],AV[i]);CHKERRQ(ierr);
470 dsic.upv.es!antodo 167
#if !defined(PETSC_USE_COMPLEX)
168
    ierr = VecDot(eps->work[1],eps->work[1],rsd+i);CHKERRQ(ierr);
169
#else
170
    ierr = VecDot(eps->work[1],eps->work[1],&t);CHKERRQ(ierr);
171
    rsd[i] = PetscRealPart(t);
172
#endif    
6 dsic.upv.es!jroman 173
  }
470 dsic.upv.es!antodo 174
 
175
  for (i=l;i<m;i++) {
176
    if (i == m-1) {
177
      rsd[i] = sqrt(rsd[i]);  
178
    } else if (T[i+1+(ldt*i)]==0.0) {
179
      rsd[i] = sqrt(rsd[i]);
180
    } else {
181
      rsd[i] = sqrt(rsd[i]+rsd[i+1])/2.0;
182
      rsd[i+1] = rsd[i];
183
      i++;
184
    }
185
  }
6 dsic.upv.es!jroman 186
  PetscFunctionReturn(0);
187
}
188
 
189
#undef __FUNCT__  
470 dsic.upv.es!antodo 190
#define __FUNCT__ "EPSSolve_SUBSPACE"
476 dsic.upv.es!antodo 191
PetscErrorCode EPSSolve_SUBSPACE(EPS eps)
6 dsic.upv.es!jroman 192
{
476 dsic.upv.es!antodo 193
  PetscErrorCode ierr;
1175 slepc 194
  int            i,ngrp,nogrp,*itrsd,*itrsdold,
1220 slepc 195
                 nxtsrr,idsrr,idort,nxtort,ncv = eps->ncv,its;
1175 slepc 196
  PetscScalar    *T=eps->T,*U;
664 dsic.upv.es!antodo 197
  PetscReal      arsd,oarsd,ctr,octr,ae,oae,*rsd,*rsdold,norm,tcond;
550 dsic.upv.es!antodo 198
  PetscTruth     breakdown;
470 dsic.upv.es!antodo 199
  /* Parameters */
535 dsic.upv.es!jroman 200
  int            init = 5;        /* Number of initial iterations */
201
  PetscReal      stpfac = 1.5,    /* Max num of iter before next SRR step */
893 dsic.upv.es!jroman 202
                 alpha = 1.0,     /* Used to predict convergence of next residual */
203
                 beta = 1.1,      /* Used to predict convergence of next residual */
535 dsic.upv.es!jroman 204
                 grptol = 1e-8,   /* Tolerance for EPSFindGroup */
205
                 cnvtol = 1e-6;   /* Convergence criterion for cnv */
206
  int            orttol = 2;      /* Number of decimal digits whose loss
207
                                     can be tolerated in orthogonalization */
6 dsic.upv.es!jroman 208
 
209
  PetscFunctionBegin;
1220 slepc 210
  its = 0;
470 dsic.upv.es!antodo 211
  ierr = PetscMalloc(sizeof(PetscScalar)*ncv*ncv,&U);CHKERRQ(ierr);
664 dsic.upv.es!antodo 212
  ierr = PetscMalloc(sizeof(PetscReal)*ncv,&rsd);CHKERRQ(ierr);
470 dsic.upv.es!antodo 213
  ierr = PetscMalloc(sizeof(PetscReal)*ncv,&rsdold);CHKERRQ(ierr);
214
  ierr = PetscMalloc(sizeof(int)*ncv,&itrsd);CHKERRQ(ierr);
215
  ierr = PetscMalloc(sizeof(int)*ncv,&itrsdold);CHKERRQ(ierr);
535 dsic.upv.es!jroman 216
 
1343 slepc 217
  /* Generate set of initial vectors and orthonormalize them.
218
     Use initial vectors provided by the user if available   */
470 dsic.upv.es!antodo 219
  for (i=0;i<ncv;i++) {
1343 slepc 220
    if (i<eps->niv) { ierr = VecCopy(eps->IV[i],eps->V[i]);CHKERRQ(ierr); }
221
    else { ierr = SlepcVecSetRandom(eps->V[i]);CHKERRQ(ierr); }
664 dsic.upv.es!antodo 222
    rsd[i] = 0.0;
470 dsic.upv.es!antodo 223
    itrsd[i] = -1;
224
  }
1345 slepc 225
  ierr = IPQRDecomposition(eps->ip,eps->V,0,ncv,PETSC_NULL,0,eps->work[0]);CHKERRQ(ierr);
470 dsic.upv.es!antodo 226
 
227
  while (eps->its<eps->max_it) {
1220 slepc 228
    eps->its++;
229
 
535 dsic.upv.es!jroman 230
    /* Find group in previously computed eigenvalues */
664 dsic.upv.es!antodo 231
    ierr = EPSFindGroup(eps->nconv,ncv,eps->eigr,eps->eigi,rsd,grptol,&nogrp,&octr,&oae,&oarsd);CHKERRQ(ierr);
470 dsic.upv.es!antodo 232
 
535 dsic.upv.es!jroman 233
    /* Compute a Rayleigh-Ritz projection step
234
       on the active columns (idx) */
235
 
236
    /* 1. AV(:,idx) = OP * V(:,idx) */
470 dsic.upv.es!antodo 237
    for (i=eps->nconv;i<ncv;i++) {
238
      ierr = STApply(eps->OP,eps->V[i],eps->AV[i]);CHKERRQ(ierr);
231 dsic.upv.es!jroman 239
    }
6 dsic.upv.es!jroman 240
 
535 dsic.upv.es!jroman 241
    /* 2. T(:,idx) = V' * AV(:,idx) */
470 dsic.upv.es!antodo 242
    for (i=eps->nconv;i<ncv;i++) {
1009 slepc 243
      ierr = VecMDot(eps->AV[i],ncv,eps->V,T+i*ncv);CHKERRQ(ierr);
470 dsic.upv.es!antodo 244
    }
6 dsic.upv.es!jroman 245
 
535 dsic.upv.es!jroman 246
    /* 3. Reduce projected matrix to Hessenberg form: [U,T] = hess(T) */
1175 slepc 247
    ierr = EPSDenseHessenberg(ncv,eps->nconv,T,ncv,U);CHKERRQ(ierr);
470 dsic.upv.es!antodo 248
 
535 dsic.upv.es!jroman 249
    /* 4. Reduce T to quasi-triangular (Schur) form */
1057 slepc 250
    ierr = EPSDenseSchur(ncv,eps->nconv,T,ncv,U,eps->eigr,eps->eigi);CHKERRQ(ierr);
535 dsic.upv.es!jroman 251
 
252
    /* 5. Sort diagonal elements in T and accumulate rotations on U */
1174 slepc 253
    ierr = EPSSortDenseSchur(ncv,eps->nconv,T,ncv,U,eps->eigr,eps->eigi,eps->which);CHKERRQ(ierr);
470 dsic.upv.es!antodo 254
 
535 dsic.upv.es!jroman 255
    /* 6. AV(:,idx) = AV * U(:,idx) */
870 dsic.upv.es!antodo 256
    for (i=eps->nconv;i<ncv;i++) {
257
      ierr = VecSet(eps->work[i],0.0);CHKERRQ(ierr);
258
      ierr = VecMAXPY(eps->work[i],ncv,U+ncv*i,eps->AV);CHKERRQ(ierr);
259
    }    
260
    for (i=eps->nconv;i<ncv;i++) {
261
      ierr = VecCopy(eps->work[i],eps->AV[i]);CHKERRQ(ierr);
262
    }    
470 dsic.upv.es!antodo 263
 
535 dsic.upv.es!jroman 264
    /* 7. V(:,idx) = V * U(:,idx) */
870 dsic.upv.es!antodo 265
    for (i=eps->nconv;i<ncv;i++) {
266
      ierr = VecSet(eps->work[i],0.0);CHKERRQ(ierr);
267
      ierr = VecMAXPY(eps->work[i],ncv,U+ncv*i,eps->V);CHKERRQ(ierr);
268
    }    
269
    for (i=eps->nconv;i<ncv;i++) {
270
      ierr = VecCopy(eps->work[i],eps->V[i]);CHKERRQ(ierr);
271
    }    
470 dsic.upv.es!antodo 272
 
535 dsic.upv.es!jroman 273
    /* Compute residuals */
664 dsic.upv.es!antodo 274
    for (i=0;i<ncv;i++) { rsdold[i] = rsd[i]; }
6 dsic.upv.es!jroman 275
 
664 dsic.upv.es!antodo 276
    ierr = EPSSchurResidualNorms(eps,eps->V,eps->AV,T,eps->nconv,ncv,ncv,rsd);CHKERRQ(ierr);
6 dsic.upv.es!jroman 277
 
664 dsic.upv.es!antodo 278
    for (i=0;i<ncv;i++) {
279
      eps->errest[i] = rsd[i] / SlepcAbsEigenvalue(eps->eigr[i],eps->eigi[i]);
280
    }
470 dsic.upv.es!antodo 281
    EPSMonitor(eps,eps->its,eps->nconv,eps->eigr,eps->eigi,eps->errest,ncv);
282
 
535 dsic.upv.es!jroman 283
    /* Convergence check */
470 dsic.upv.es!antodo 284
    for (i=0;i<ncv;i++) { itrsdold[i] = itrsd[i]; }
1220 slepc 285
    for (i=eps->nconv;i<ncv;i++) { itrsd[i] = its; }
470 dsic.upv.es!antodo 286
 
287
    for (;;) {
535 dsic.upv.es!jroman 288
      /* Find group in currently computed eigenvalues */
664 dsic.upv.es!antodo 289
      ierr = EPSFindGroup(eps->nconv,ncv,eps->eigr,eps->eigi,rsd,grptol,&ngrp,&ctr,&ae,&arsd);CHKERRQ(ierr);
470 dsic.upv.es!antodo 290
      if (ngrp!=nogrp) break;
291
      if (ngrp==0) break;
292
      if (PetscAbsScalar(ae-oae)>ctr*cnvtol*(itrsd[eps->nconv]-itrsdold[eps->nconv])) break;
293
      if (arsd>ctr*eps->tol) break;
294
      eps->nconv = eps->nconv + ngrp;
295
      if (eps->nconv>=ncv) break;
296
    }
297
 
298
    if (eps->nconv>=eps->nev) break;
299
 
535 dsic.upv.es!jroman 300
    /* Compute nxtsrr (iteration of next projection step) */
1220 slepc 301
    nxtsrr = PetscMin(eps->max_it,PetscMax((int)floor(stpfac*its), init));
470 dsic.upv.es!antodo 302
 
303
    if (ngrp!=nogrp || ngrp==0 || arsd>=oarsd) {
1220 slepc 304
      idsrr = nxtsrr - its;
470 dsic.upv.es!antodo 305
    } else {
500 dsic.upv.es!jroman 306
      idsrr = (int)floor(alpha+beta*(itrsdold[eps->nconv]-itrsd[eps->nconv])*log(arsd/eps->tol)/log(arsd/oarsd));
470 dsic.upv.es!antodo 307
      idsrr = PetscMax(1,idsrr);
308
    }
1220 slepc 309
    nxtsrr = PetscMin(nxtsrr,its+idsrr);
6 dsic.upv.es!jroman 310
 
535 dsic.upv.es!jroman 311
    /* Compute nxtort (iteration of next orthogonalization step) */
470 dsic.upv.es!antodo 312
    ierr = PetscMemcpy(U,T,sizeof(PetscScalar)*ncv);CHKERRQ(ierr);
535 dsic.upv.es!jroman 313
    ierr = EPSHessCond(U,ncv,&tcond);CHKERRQ(ierr);
500 dsic.upv.es!jroman 314
    idort = PetscMax(1,(int)floor(orttol/PetscMax(1,log10(tcond))));    
1220 slepc 315
    nxtort = PetscMin(its+idort, nxtsrr);
6 dsic.upv.es!jroman 316
 
470 dsic.upv.es!antodo 317
    /* V(:,idx) = AV(:,idx) */
318
    for (i=eps->nconv;i<ncv;i++) {
319
      ierr = VecCopy(eps->AV[i],eps->V[i]);CHKERRQ(ierr);
320
    }
1220 slepc 321
    its++;
6 dsic.upv.es!jroman 322
 
535 dsic.upv.es!jroman 323
    /* Orthogonalization loop */
470 dsic.upv.es!antodo 324
    do {
1220 slepc 325
      while (its<nxtort) {
470 dsic.upv.es!antodo 326
 
535 dsic.upv.es!jroman 327
        /* AV(:,idx) = OP * V(:,idx) */
470 dsic.upv.es!antodo 328
        for (i=eps->nconv;i<ncv;i++) {
329
          ierr = STApply(eps->OP,eps->V[i],eps->AV[i]);CHKERRQ(ierr);
330
        }
331
 
535 dsic.upv.es!jroman 332
        /* V(:,idx) = AV(:,idx) with normalization */
470 dsic.upv.es!antodo 333
        for (i=eps->nconv;i<ncv;i++) {
334
          ierr = VecCopy(eps->AV[i],eps->V[i]);CHKERRQ(ierr);
335
          ierr = VecNorm(eps->V[i],NORM_INFINITY,&norm);CHKERRQ(ierr);
828 dsic.upv.es!antodo 336
          ierr = VecScale(eps->V[i],1/norm);CHKERRQ(ierr);
470 dsic.upv.es!antodo 337
        }
338
 
1220 slepc 339
        its++;
470 dsic.upv.es!antodo 340
      }
535 dsic.upv.es!jroman 341
      /* Orthonormalize vectors */
470 dsic.upv.es!antodo 342
      for (i=eps->nconv;i<ncv;i++) {
1345 slepc 343
        ierr = IPOrthogonalize(eps->ip,i+eps->nds,PETSC_NULL,eps->DSV,eps->V[i],PETSC_NULL,&norm,&breakdown,eps->work[0]);CHKERRQ(ierr);
550 dsic.upv.es!antodo 344
        if (breakdown) {
345
          ierr = SlepcVecSetRandom(eps->V[i]);CHKERRQ(ierr);
1345 slepc 346
          ierr = IPOrthogonalize(eps->ip,i+eps->nds,PETSC_NULL,eps->DSV,eps->V[i],PETSC_NULL,&norm,&breakdown,eps->work[0]);CHKERRQ(ierr);
550 dsic.upv.es!antodo 347
        }
828 dsic.upv.es!antodo 348
        ierr = VecScale(eps->V[i],1/norm);CHKERRQ(ierr);
470 dsic.upv.es!antodo 349
      }
1220 slepc 350
      nxtort = PetscMin(its+idort,nxtsrr);
351
    } while (its<nxtsrr);
470 dsic.upv.es!antodo 352
  }
6 dsic.upv.es!jroman 353
 
470 dsic.upv.es!antodo 354
  ierr = PetscFree(U);CHKERRQ(ierr);
664 dsic.upv.es!antodo 355
  ierr = PetscFree(rsd);CHKERRQ(ierr);
470 dsic.upv.es!antodo 356
  ierr = PetscFree(rsdold);CHKERRQ(ierr);
357
  ierr = PetscFree(itrsd);CHKERRQ(ierr);
358
  ierr = PetscFree(itrsdold);CHKERRQ(ierr);
6 dsic.upv.es!jroman 359
 
470 dsic.upv.es!antodo 360
  if( eps->nconv == eps->nev ) eps->reason = EPS_CONVERGED_TOL;
361
  else eps->reason = EPS_DIVERGED_ITS;
362
 
363
  PetscFunctionReturn(0);
364
}
365
 
6 dsic.upv.es!jroman 366
EXTERN_C_BEGIN
367
#undef __FUNCT__  
368
#define __FUNCT__ "EPSCreate_SUBSPACE"
476 dsic.upv.es!antodo 369
PetscErrorCode EPSCreate_SUBSPACE(EPS eps)
6 dsic.upv.es!jroman 370
{
371
  PetscFunctionBegin;
372
  eps->ops->solve                = EPSSolve_SUBSPACE;
504 dsic.upv.es!antodo 373
  eps->ops->setup                = EPSSetUp_SUBSPACE;
259 dsic.upv.es!antodo 374
  eps->ops->destroy              = EPSDestroy_Default;
176 dsic.upv.es!antodo 375
  eps->ops->backtransform        = EPSBackTransform_Default;
508 dsic.upv.es!antodo 376
  eps->ops->computevectors       = EPSComputeVectors_Schur;
6 dsic.upv.es!jroman 377
  PetscFunctionReturn(0);
378
}
379
EXTERN_C_END
380