Actual source code: opts.c

  1: /*
  2:       EPS routines related to options that can be set via the command-line 
  3:       or procedurally.

  5:    - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
  6:       SLEPc - Scalable Library for Eigenvalue Problem Computations
  7:       Copyright (c) 2002-2007, Universidad Politecnica de Valencia, Spain

  9:       This file is part of SLEPc. See the README file for conditions of use
 10:       and additional information.
 11:    - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
 12: */

 14:  #include src/eps/epsimpl.h

 18: /*@
 19:    EPSSetFromOptions - Sets EPS options from the options database.
 20:    This routine must be called before EPSSetUp() if the user is to be 
 21:    allowed to set the solver type. 

 23:    Collective on EPS

 25:    Input Parameters:
 26: .  eps - the eigensolver context

 28:    Notes:  
 29:    To see all options, run your program with the -help option.

 31:    Level: beginner

 33: .seealso: 
 34: @*/
 35: PetscErrorCode EPSSetFromOptions(EPS eps)
 36: {
 38:   char           type[256],monfilename[PETSC_MAX_PATH_LEN];
 39:   PetscTruth     flg;
 40:   PetscReal      r;
 41:   PetscInt       i,j;
 42:   PetscViewer    monviewer;

 46:   PetscOptionsBegin(eps->comm,eps->prefix,"Eigenproblem Solver (EPS) Options","EPS");
 47:     PetscOptionsList("-eps_type","Eigenproblem Solver method","EPSSetType",EPSList,(char*)(eps->type_name?eps->type_name:EPSKRYLOVSCHUR),type,256,&flg);
 48:     if (flg) {
 49:       EPSSetType(eps,type);
 50:     }

 52:     PetscOptionsTruthGroupBegin("-eps_hermitian","hermitian eigenvalue problem","EPSSetProblemType",&flg);
 53:     if (flg) {EPSSetProblemType(eps,EPS_HEP);}
 54:     PetscOptionsTruthGroup("-eps_gen_hermitian","generalized hermitian eigenvalue problem","EPSSetProblemType",&flg);
 55:     if (flg) {EPSSetProblemType(eps,EPS_GHEP);}
 56:     PetscOptionsTruthGroup("-eps_non_hermitian","non-hermitian eigenvalue problem","EPSSetProblemType",&flg);
 57:     if (flg) {EPSSetProblemType(eps,EPS_NHEP);}
 58:     PetscOptionsTruthGroup("-eps_gen_non_hermitian","generalized non-hermitian eigenvalue problem","EPSSetProblemType",&flg);
 59:     if (flg) {EPSSetProblemType(eps,EPS_GNHEP);}
 60:     PetscOptionsTruthGroupEnd("-eps_pos_gen_non_hermitian","generalized non-hermitian eigenvalue problem with positive semi-definite B","EPSSetProblemType",&flg);
 61:     if (flg) {EPSSetProblemType(eps,EPS_PGNHEP);}

 63:     /*
 64:       Set the type if it was never set.
 65:     */
 66:     if (!eps->type_name) {
 67:       EPSSetType(eps,EPSKRYLOVSCHUR);
 68:     }

 70:     PetscOptionsTruthGroupBegin("-eps_oneside","one-sided eigensolver","EPSSetClass",&flg);
 71:     if (flg) {EPSSetClass(eps,EPS_ONE_SIDE);}
 72:     PetscOptionsTruthGroupEnd("-eps_twoside","two-sided eigensolver","EPSSetClass",&flg);
 73:     if (flg) {EPSSetClass(eps,EPS_TWO_SIDE);}

 75:     r = i = PETSC_IGNORE;
 76:     PetscOptionsInt("-eps_max_it","Maximum number of iterations","EPSSetTolerances",eps->max_it,&i,PETSC_NULL);
 77:     PetscOptionsReal("-eps_tol","Tolerance","EPSSetTolerances",eps->tol,&r,PETSC_NULL);
 78:     EPSSetTolerances(eps,r,i);

 80:     i = j = PETSC_IGNORE;
 81:     PetscOptionsInt("-eps_nev","Number of eigenvalues to compute","EPSSetDimensions",eps->nev,&i,PETSC_NULL);
 82:     PetscOptionsInt("-eps_ncv","Number of basis vectors","EPSSetDimensions",eps->ncv,&j,PETSC_NULL);
 83:     EPSSetDimensions(eps,i,j);
 84: 
 85:     /* -----------------------------------------------------------------------*/
 86:     /*
 87:       Cancels all monitors hardwired into code before call to EPSSetFromOptions()
 88:     */
 89:     PetscOptionsName("-eps_monitor_cancel","Remove any hardwired monitor routines","EPSMonitorCancel",&flg);
 90:     if (flg) {
 91:       EPSMonitorCancel(eps);
 92:     }
 93:     /*
 94:       Prints approximate eigenvalues and error estimates at each iteration
 95:     */
 96:     PetscOptionsString("-eps_monitor","Monitor approximate eigenvalues and error estimates","EPSMonitorSet","stdout",monfilename,PETSC_MAX_PATH_LEN,&flg);
 97:     if (flg) {
 98:       PetscViewerASCIIOpen(eps->comm,monfilename,&monviewer);
 99:       EPSMonitorSet(eps,EPSMonitorDefault,monviewer,(PetscErrorCode (*)(void*))PetscViewerDestroy);
100:     }
101:     PetscOptionsName("-eps_monitor_draw","Monitor error estimates graphically","EPSMonitorSet",&flg);
102:     if (flg) {
103:       EPSMonitorSet(eps,EPSMonitorLG,PETSC_NULL,PETSC_NULL);
104:     }
105:   /* -----------------------------------------------------------------------*/
106:     PetscOptionsTruthGroupBegin("-eps_largest_magnitude","compute largest eigenvalues in magnitude","EPSSetWhichEigenpairs",&flg);
107:     if (flg) {EPSSetWhichEigenpairs(eps,EPS_LARGEST_MAGNITUDE);}
108:     PetscOptionsTruthGroup("-eps_smallest_magnitude","compute smallest eigenvalues in magnitude","EPSSetWhichEigenpairs",&flg);
109:     if (flg) {EPSSetWhichEigenpairs(eps,EPS_SMALLEST_MAGNITUDE);}
110:     PetscOptionsTruthGroup("-eps_largest_real","compute largest real parts","EPSSetWhichEigenpairs",&flg);
111:     if (flg) {EPSSetWhichEigenpairs(eps,EPS_LARGEST_REAL);}
112:     PetscOptionsTruthGroup("-eps_smallest_real","compute smallest real parts","EPSSetWhichEigenpairs",&flg);
113:     if (flg) {EPSSetWhichEigenpairs(eps,EPS_SMALLEST_REAL);}
114:     PetscOptionsTruthGroup("-eps_largest_imaginary","compute largest imaginary parts","EPSSetWhichEigenpairs",&flg);
115:     if (flg) {EPSSetWhichEigenpairs(eps,EPS_LARGEST_IMAGINARY);}
116:     PetscOptionsTruthGroupEnd("-eps_smallest_imaginary","compute smallest imaginary parts","EPSSetWhichEigenpairs",&flg);
117:     if (flg) {EPSSetWhichEigenpairs(eps,EPS_SMALLEST_IMAGINARY);}

119:     PetscOptionsName("-eps_view","Print detailed information on solver used","EPSView",0);
120:     PetscOptionsName("-eps_view_binary","Save the matrices associated to the eigenproblem","EPSSetFromOptions",0);
121:     PetscOptionsName("-eps_plot_eigs","Make a plot of the computed eigenvalues","EPSSolve",0);
122: 
123:     if (eps->ops->setfromoptions) {
124:       (*eps->ops->setfromoptions)(eps);
125:     }
126:   PetscOptionsEnd();

128:   IPSetFromOptions(eps->ip);
129:   STSetFromOptions(eps->OP);
130:   return(0);
131: }

135: /*@
136:    EPSGetTolerances - Gets the tolerance and maximum
137:    iteration count used by the default EPS convergence tests. 

139:    Not Collective

141:    Input Parameter:
142: .  eps - the eigensolver context
143:   
144:    Output Parameters:
145: +  tol - the convergence tolerance
146: -  maxits - maximum number of iterations

148:    Notes:
149:    The user can specify PETSC_NULL for any parameter that is not needed.

151:    Level: intermediate

153: .seealso: EPSSetTolerances()
154: @*/
155: PetscErrorCode EPSGetTolerances(EPS eps,PetscReal *tol,int *maxits)
156: {
159:   if (tol)    *tol    = eps->tol;
160:   if (maxits) *maxits = eps->max_it;
161:   return(0);
162: }

166: /*@
167:    EPSSetTolerances - Sets the tolerance and maximum
168:    iteration count used by the default EPS convergence testers. 

170:    Collective on EPS

172:    Input Parameters:
173: +  eps - the eigensolver context
174: .  tol - the convergence tolerance
175: -  maxits - maximum number of iterations to use

177:    Options Database Keys:
178: +  -eps_tol <tol> - Sets the convergence tolerance
179: -  -eps_max_it <maxits> - Sets the maximum number of iterations allowed

181:    Notes:
182:    Use PETSC_IGNORE for an argument that need not be changed.

184:    Use PETSC_DECIDE for maxits to assign a reasonably good value, which is 
185:    dependent on the solution method.

187:    Level: intermediate

189: .seealso: EPSGetTolerances()
190: @*/
191: PetscErrorCode EPSSetTolerances(EPS eps,PetscReal tol,int maxits)
192: {
195:   if (tol != PETSC_IGNORE) {
196:     if (tol == PETSC_DEFAULT) {
197:       eps->tol = 1e-7;
198:     } else {
199:       if (tol < 0.0) SETERRQ(PETSC_ERR_ARG_OUTOFRANGE,"Illegal value of tol. Must be > 0");
200:       eps->tol = tol;
201:     }
202:   }
203:   if (maxits != PETSC_IGNORE) {
204:     if (maxits == PETSC_DEFAULT || maxits == PETSC_DECIDE) {
205:       eps->max_it = 0;
206:     } else {
207:       if (maxits < 0) SETERRQ(PETSC_ERR_ARG_OUTOFRANGE,"Illegal value of maxits. Must be > 0");
208:       eps->max_it = maxits;
209:     }
210:   }
211:   return(0);
212: }

216: /*@
217:    EPSGetDimensions - Gets the number of eigenvalues to compute
218:    and the dimension of the subspace.

220:    Not Collective

222:    Input Parameter:
223: .  eps - the eigensolver context
224:   
225:    Output Parameters:
226: +  nev - number of eigenvalues to compute
227: -  ncv - the maximum dimension of the subspace to be used by the solver

229:    Notes:
230:    The user can specify PETSC_NULL for any parameter that is not needed.

232:    Level: intermediate

234: .seealso: EPSSetDimensions()
235: @*/
236: PetscErrorCode EPSGetDimensions(EPS eps,int *nev,int *ncv)
237: {
240:   if( nev )   *nev = eps->nev;
241:   if( ncv )   *ncv = eps->ncv;
242:   return(0);
243: }

247: /*@
248:    EPSSetDimensions - Sets the number of eigenvalues to compute
249:    and the dimension of the subspace.

251:    Collective on EPS

253:    Input Parameters:
254: +  eps - the eigensolver context
255: .  nev - number of eigenvalues to compute
256: -  ncv - the maximum dimension of the subspace to be used by the solver

258:    Options Database Keys:
259: +  -eps_nev <nev> - Sets the number of eigenvalues
260: -  -eps_ncv <ncv> - Sets the dimension of the subspace

262:    Notes:
263:    Use PETSC_IGNORE to retain the previous value of any parameter.

265:    Use PETSC_DECIDE for ncv to assign a reasonably good value, which is 
266:    dependent on the solution method.

268:    Level: intermediate

270: .seealso: EPSGetDimensions()
271: @*/
272: PetscErrorCode EPSSetDimensions(EPS eps,int nev,int ncv)
273: {

277:   if( nev != PETSC_IGNORE ) {
278:     if (nev<1) SETERRQ(PETSC_ERR_ARG_OUTOFRANGE,"Illegal value of nev. Must be > 0");
279:     eps->nev = nev;
280:     eps->setupcalled = 0;
281:   }
282:   if( ncv != PETSC_IGNORE ) {
283:     if (ncv == PETSC_DECIDE || ncv == PETSC_DEFAULT) {
284:       eps->ncv = 0;
285:     } else {
286:       if (ncv<1) SETERRQ(PETSC_ERR_ARG_OUTOFRANGE,"Illegal value of ncv. Must be > 0");
287:       eps->ncv = ncv;
288:     }
289:     eps->setupcalled = 0;
290:   }
291:   return(0);
292: }

296: /*@
297:     EPSSetWhichEigenpairs - Specifies which portion of the spectrum is 
298:     to be sought.

300:     Collective on EPS

302:     Input Parameter:
303: .   eps - eigensolver context obtained from EPSCreate()

305:     Output Parameter:
306: .   which - the portion of the spectrum to be sought

308:     Possible values:
309:     The parameter 'which' can have one of these values:
310:     
311: +     EPS_LARGEST_MAGNITUDE - largest eigenvalues in magnitude (default)
312: .     EPS_SMALLEST_MAGNITUDE - smallest eigenvalues in magnitude
313: .     EPS_LARGEST_REAL - largest real parts
314: .     EPS_SMALLEST_REAL - smallest real parts
315: .     EPS_LARGEST_IMAGINARY - largest imaginary parts
316: -     EPS_SMALLEST_IMAGINARY - smallest imaginary parts

318:     Options Database Keys:
319: +   -eps_largest_magnitude - Sets largest eigenvalues in magnitude
320: .   -eps_smallest_magnitude - Sets smallest eigenvalues in magnitude
321: .   -eps_largest_real - Sets largest real parts
322: .   -eps_smallest_real - Sets smallest real parts
323: .   -eps_largest_imaginary - Sets largest imaginary parts in magnitude
324: -   -eps_smallest_imaginary - Sets smallest imaginary parts in magnitude

326:     Notes:
327:     Not all eigensolvers implemented in EPS account for all the possible values
328:     stated above. Also, some values make sense only for certain types of 
329:     problems. If SLEPc is compiled for real numbers EPS_LARGEST_IMAGINARY
330:     and EPS_SMALLEST_IMAGINARY use the absolute value of the imaginary part 
331:     for eigenvalue selection.     
332:     
333:     Level: intermediate

335: .seealso: EPSGetWhichEigenpairs(), EPSSortEigenvalues(), EPSWhich
336: @*/
337: PetscErrorCode EPSSetWhichEigenpairs(EPS eps,EPSWhich which)
338: {
341:   switch (which) {
342:     case EPS_LARGEST_MAGNITUDE:
343:     case EPS_SMALLEST_MAGNITUDE:
344:     case EPS_LARGEST_REAL:
345:     case EPS_SMALLEST_REAL:
346:     case EPS_LARGEST_IMAGINARY:
347:     case EPS_SMALLEST_IMAGINARY:
348:       if (eps->which != which) {
349:         eps->setupcalled = 0;
350:         eps->which = which;
351:       }
352:       break;
353:     default:
354:       SETERRQ(PETSC_ERR_ARG_OUTOFRANGE,"Invalid 'which' value");
355:   }
356:   return(0);
357: }

361: /*@C
362:     EPSGetWhichEigenpairs - Returns which portion of the spectrum is to be 
363:     sought.

365:     Not Collective

367:     Input Parameter:
368: .   eps - eigensolver context obtained from EPSCreate()

370:     Output Parameter:
371: .   which - the portion of the spectrum to be sought

373:     Notes:
374:     See EPSSetWhichEigenpairs() for possible values of which

376:     Level: intermediate

378: .seealso: EPSSetWhichEigenpairs(), EPSWhich
379: @*/
380: PetscErrorCode EPSGetWhichEigenpairs(EPS eps,EPSWhich *which)
381: {
385:   *which = eps->which;
386:   return(0);
387: }

391: /*@
392:    EPSSetProblemType - Specifies the type of the eigenvalue problem.

394:    Collective on EPS

396:    Input Parameters:
397: +  eps      - the eigensolver context
398: -  type     - a known type of eigenvalue problem 

400:    Options Database Keys:
401: +  -eps_hermitian - Hermitian eigenvalue problem
402: .  -eps_gen_hermitian - generalized Hermitian eigenvalue problem
403: .  -eps_non_hermitian - non-Hermitian eigenvalue problem
404: -  -eps_gen_non_hermitian - generalized non-Hermitian eigenvalue problem 
405:     
406:    Note:  
407:    Allowed values for the problem type are: Hermitian (EPS_HEP), non-Hermitian
408:    (EPS_NHEP), generalized Hermitian (EPS_GHEP) and generalized non-Hermitian 
409:    (EPS_GNHEP).

411:    This function must be used to instruct SLEPc to exploit symmetry. If no
412:    problem type is specified, by default a non-Hermitian problem is assumed
413:    (either standard or generalized). If the user knows that the problem is
414:    Hermitian (i.e. A=A^H) of generalized Hermitian (i.e. A=A^H, B=B^H, and 
415:    B positive definite) then it is recommended to set the problem type so
416:    that eigensolver can exploit these properties. 

418:    Level: beginner

420: .seealso: EPSSetOperators(), EPSSetType(), EPSGetProblemType(), EPSProblemType
421: @*/
422: PetscErrorCode EPSSetProblemType(EPS eps,EPSProblemType type)
423: {

427:   switch (type) {
428:     case EPS_HEP:
429:       eps->isgeneralized = PETSC_FALSE;
430:       eps->ishermitian = PETSC_TRUE;
431:       eps->ispositive = PETSC_FALSE;
432:       break;
433:     case EPS_NHEP:
434:       eps->isgeneralized = PETSC_FALSE;
435:       eps->ishermitian = PETSC_FALSE;
436:       eps->ispositive = PETSC_FALSE;
437:       break;
438:     case EPS_GHEP:
439:       eps->isgeneralized = PETSC_TRUE;
440:       eps->ishermitian = PETSC_TRUE;
441:       eps->ispositive = PETSC_TRUE;
442:       break;
443:     case EPS_GNHEP:
444:       eps->isgeneralized = PETSC_TRUE;
445:       eps->ishermitian = PETSC_FALSE;
446:       eps->ispositive = PETSC_FALSE;
447:       break;
448:     case EPS_PGNHEP:
449:       eps->isgeneralized = PETSC_TRUE;
450:       eps->ishermitian = PETSC_FALSE;
451:       eps->ispositive = PETSC_TRUE;
452:       break;
453: /*
454:     case EPS_CSEP: 
455:       eps->isgeneralized = PETSC_FALSE;
456:       eps->ishermitian = PETSC_FALSE;
457:       STSetBilinearForm(eps->OP,STINNER_SYMMETRIC);
458:       break;
459:     case EPS_GCSEP:
460:       eps->isgeneralized = PETSC_TRUE;
461:       eps->ishermitian = PETSC_FALSE;
462:       STSetBilinearForm(eps->OP,STINNER_B_SYMMETRIC);
463:       break;
464: */
465:     default:
466:       SETERRQ(PETSC_ERR_ARG_WRONG,"Unknown eigenvalue problem type");
467:   }
468:   eps->problem_type = type;

470:   return(0);
471: }

475: /*@C
476:    EPSGetProblemType - Gets the problem type from the EPS object.

478:    Not Collective

480:    Input Parameter:
481: .  eps - the eigensolver context 

483:    Output Parameter:
484: .  type - name of EPS problem type 

486:    Level: intermediate

488: .seealso: EPSSetProblemType(), EPSProblemType
489: @*/
490: PetscErrorCode EPSGetProblemType(EPS eps,EPSProblemType *type)
491: {
495:   *type = eps->problem_type;
496:   return(0);
497: }

501: /*@
502:    EPSSetClass - Specifies the eigensolver class: either one-sided or two-sided.

504:    Collective on EPS

506:    Input Parameters:
507: +  eps      - the eigensolver context
508: -  class    - the class of solver

510:    Options Database Keys:
511: +  -eps_oneside - one-sided solver
512: -  -eps_twoside - two-sided solver
513:     
514:    Note:  
515:    Allowed solver classes are: one-sided (EPS_ONE_SIDE) and two-sided (EPS_TWO_SIDE).
516:    One-sided eigensolvers are the standard ones, which allow the computation of
517:    eigenvalues and (right) eigenvectors, whereas two-sided eigensolvers compute
518:    left eigenvectors as well.

520:    Level: intermediate

522: .seealso: EPSGetLeftVector(), EPSComputeRelativeErrorLeft(), EPSSetLeftInitialVector(),
523:    EPSGetClass(), EPSClass
524: @*/
525: PetscErrorCode EPSSetClass(EPS eps,EPSClass cl)
526: {


532:   if (cl != EPS_ONE_SIDE && cl != EPS_TWO_SIDE) SETERRQ(PETSC_ERR_ARG_WRONG,"Unknown eigensolver class");
533:   if (eps->solverclass!=cl) {
534:     if (eps->solverclass == EPS_TWO_SIDE) { EPSFreeSolution(eps); }
535:     eps->solverclass = cl;
536:   }

538:   return(0);
539: }

543: /*@C
544:    EPSGetClass - Gets the eigensolver class from the EPS object.

546:    Not Collective

548:    Input Parameter:
549: .  eps - the eigensolver context 

551:    Output Parameter:
552: .  class - class of EPS solver (either one-sided or two-sided)

554:    Level: intermediate

556: .seealso: EPSSetClass(), EPSClass
557: @*/
558: PetscErrorCode EPSGetClass(EPS eps,EPSClass *cl)
559: {
563:   *cl = eps->solverclass;
564:   return(0);
565: }

569: /*@C
570:    EPSSetOptionsPrefix - Sets the prefix used for searching for all 
571:    EPS options in the database.

573:    Collective on EPS

575:    Input Parameters:
576: +  eps - the eigensolver context
577: -  prefix - the prefix string to prepend to all EPS option requests

579:    Notes:
580:    A hyphen (-) must NOT be given at the beginning of the prefix name.
581:    The first character of all runtime options is AUTOMATICALLY the
582:    hyphen.

584:    For example, to distinguish between the runtime options for two
585:    different EPS contexts, one could call
586: .vb
587:       EPSSetOptionsPrefix(eps1,"eig1_")
588:       EPSSetOptionsPrefix(eps2,"eig2_")
589: .ve

591:    Level: advanced

593: .seealso: EPSAppendOptionsPrefix(), EPSGetOptionsPrefix()
594: @*/
595: PetscErrorCode EPSSetOptionsPrefix(EPS eps,const char *prefix)
596: {
600:   PetscObjectSetOptionsPrefix((PetscObject)eps, prefix);
601:   STSetOptionsPrefix(eps->OP,prefix);
602:   IPSetOptionsPrefix(eps->ip,prefix);
603:   IPAppendOptionsPrefix(eps->ip,"eps_");
604:   return(0);
605: }
606: 
609: /*@C
610:    EPSAppendOptionsPrefix - Appends to the prefix used for searching for all 
611:    EPS options in the database.

613:    Collective on EPS

615:    Input Parameters:
616: +  eps - the eigensolver context
617: -  prefix - the prefix string to prepend to all EPS option requests

619:    Notes:
620:    A hyphen (-) must NOT be given at the beginning of the prefix name.
621:    The first character of all runtime options is AUTOMATICALLY the hyphen.

623:    Level: advanced

625: .seealso: EPSSetOptionsPrefix(), EPSGetOptionsPrefix()
626: @*/
627: PetscErrorCode EPSAppendOptionsPrefix(EPS eps,const char *prefix)
628: {
632:   PetscObjectAppendOptionsPrefix((PetscObject)eps, prefix);
633:   STAppendOptionsPrefix(eps->OP,prefix);
634:   IPSetOptionsPrefix(eps->ip,prefix);
635:   IPAppendOptionsPrefix(eps->ip,"eps_");
636:   return(0);
637: }

641: /*@C
642:    EPSGetOptionsPrefix - Gets the prefix used for searching for all 
643:    EPS options in the database.

645:    Not Collective

647:    Input Parameters:
648: .  eps - the eigensolver context

650:    Output Parameters:
651: .  prefix - pointer to the prefix string used is returned

653:    Notes: On the fortran side, the user should pass in a string 'prefix' of
654:    sufficient length to hold the prefix.

656:    Level: advanced

658: .seealso: EPSSetOptionsPrefix(), EPSAppendOptionsPrefix()
659: @*/
660: PetscErrorCode EPSGetOptionsPrefix(EPS eps,const char *prefix[])
661: {
666:   PetscObjectGetOptionsPrefix((PetscObject)eps, prefix);
667:   return(0);
668: }