Date: 2022-08-09T09:05:59+00:00

Actual source code: lmeopts.c
slepc-3.17.2 2022-08-09
Report Typos and Errors

      1: /*
      2:    - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
      3:    SLEPc - Scalable Library for Eigenvalue Problem Computations
      4:    Copyright (c) 2002-, Universitat Politecnica de Valencia, Spain

      6:    This file is part of SLEPc.
      7:    SLEPc is distributed under a 2-clause BSD license (see LICENSE).
      8:    - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
      9: */
     10: /*
     11:    LME routines related to options that can be set via the command-line
     12:    or procedurally
     13: */

     15: #include <slepc/private/lmeimpl.h>
     16: #include <petscdraw.h>

     18: /*@C
     19:    LMEMonitorSetFromOptions - Sets a monitor function and viewer appropriate for the type
     20:    indicated by the user.

     22:    Collective on lme

     24:    Input Parameters:
     25: +  lme      - the linear matrix equation context
     26: .  opt  - the command line option for this monitor
     27: .  name - the monitor type one is seeking
     28: -  ctx  - an optional user context for the monitor, or NULL

     30:    Level: developer

     32: .seealso: LMEMonitorSet()
     33: @*/
     34: PetscErrorCode LMEMonitorSetFromOptions(LME lme,const char opt[],const char name[],void *ctx)
     35: {
     36:   PetscErrorCode       (*mfunc)(LME,PetscInt,PetscReal,void*);
     37:   PetscErrorCode       (*cfunc)(PetscViewer,PetscViewerFormat,void*,PetscViewerAndFormat**);
     38:   PetscErrorCode       (*dfunc)(PetscViewerAndFormat**);
     39:   PetscViewerAndFormat *vf;
     40:   PetscViewer          viewer;
     41:   PetscViewerFormat    format;
     42:   PetscViewerType      vtype;
     43:   char                 key[PETSC_MAX_PATH_LEN];
     44:   PetscBool            flg;

     46:   PetscOptionsGetViewer(PetscObjectComm((PetscObject)lme),((PetscObject)lme)->options,((PetscObject)lme)->prefix,opt,&viewer,&format,&flg);
     47:   if (!flg) PetscFunctionReturn(0);

     49:   PetscViewerGetType(viewer,&vtype);
     50:   SlepcMonitorMakeKey_Internal(name,vtype,format,key);
     51:   PetscFunctionListFind(LMEMonitorList,key,&mfunc);
     53:   PetscFunctionListFind(LMEMonitorCreateList,key,&cfunc);
     54:   PetscFunctionListFind(LMEMonitorDestroyList,key,&dfunc);
     55:   if (!cfunc) cfunc = PetscViewerAndFormatCreate_Internal;
     56:   if (!dfunc) dfunc = PetscViewerAndFormatDestroy;

     58:   (*cfunc)(viewer,format,ctx,&vf);
     59:   PetscObjectDereference((PetscObject)viewer);
     60:   LMEMonitorSet(lme,mfunc,vf,(PetscErrorCode(*)(void **))dfunc);
     61:   PetscFunctionReturn(0);
     62: }

     64: /*@
     65:    LMESetFromOptions - Sets LME options from the options database.
     66:    This routine must be called before LMESetUp() if the user is to be
     67:    allowed to set the solver type.

     69:    Collective on lme

     71:    Input Parameters:
     72: .  lme - the linear matrix equation solver context

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

     77:    Level: beginner

     79: .seealso: LMESetOptionsPrefix()
     80: @*/
     81: PetscErrorCode LMESetFromOptions(LME lme)
     82: {
     84:   char           type[256];
     85:   PetscBool      set,flg,flg1,flg2;
     86:   PetscReal      r;
     87:   PetscInt       i;

     90:   LMERegisterAll();
     91:   ierr = PetscObjectOptionsBegin((PetscObject)lme);
     92:     PetscOptionsFList("-lme_type","Linear matrix equation","LMESetType",LMEList,(char*)(((PetscObject)lme)->type_name?((PetscObject)lme)->type_name:LMEKRYLOV),type,sizeof(type),&flg);
     93:     if (flg) LMESetType(lme,type);
     94:     else if (!((PetscObject)lme)->type_name) LMESetType(lme,LMEKRYLOV);

     96:     PetscOptionsBoolGroupBegin("-lme_lyapunov","Continuous-time Lyapunov equation","LMESetProblemType",&flg);
     97:     if (flg) LMESetProblemType(lme,LME_LYAPUNOV);
     98:     PetscOptionsBoolGroup("-lme_sylvester","Continuous-time Sylvester equation","LMESetProblemType",&flg);
     99:     if (flg) LMESetProblemType(lme,LME_SYLVESTER);
    100:     PetscOptionsBoolGroup("-lme_gen_lyapunov","Generalized Lyapunov equation","LMESetProblemType",&flg);
    101:     if (flg) LMESetProblemType(lme,LME_GEN_LYAPUNOV);
    102:     PetscOptionsBoolGroup("-lme_gen_sylvester","Generalized Sylvester equation","LMESetProblemType",&flg);
    103:     if (flg) LMESetProblemType(lme,LME_GEN_SYLVESTER);
    104:     PetscOptionsBoolGroup("-lme_dt_lyapunov","Discrete-time Lyapunov equation","LMESetProblemType",&flg);
    105:     if (flg) LMESetProblemType(lme,LME_DT_LYAPUNOV);
    106:     PetscOptionsBoolGroupEnd("-lme_stein","Stein equation","LMESetProblemType",&flg);
    107:     if (flg) LMESetProblemType(lme,LME_STEIN);

    109:     i = lme->max_it;
    110:     PetscOptionsInt("-lme_max_it","Maximum number of iterations","LMESetTolerances",lme->max_it,&i,&flg1);
    111:     if (!flg1) i = PETSC_DEFAULT;
    112:     r = lme->tol;
    113:     PetscOptionsReal("-lme_tol","Tolerance","LMESetTolerances",SlepcDefaultTol(lme->tol),&r,&flg2);
    114:     if (flg1 || flg2) LMESetTolerances(lme,r,i);

    116:     PetscOptionsInt("-lme_ncv","Number of basis vectors","LMESetDimensions",lme->ncv,&i,&flg);
    117:     if (flg) LMESetDimensions(lme,i);

    119:     PetscOptionsBool("-lme_error_if_not_converged","Generate error if solver does not converge","LMESetErrorIfNotConverged",lme->errorifnotconverged,&lme->errorifnotconverged,NULL);

    121:     /* -----------------------------------------------------------------------*/
    122:     /*
    123:       Cancels all monitors hardwired into code before call to LMESetFromOptions()
    124:     */
    125:     PetscOptionsBool("-lme_monitor_cancel","Remove any hardwired monitor routines","LMEMonitorCancel",PETSC_FALSE,&flg,&set);
    126:     if (set && flg) LMEMonitorCancel(lme);
    127:     LMEMonitorSetFromOptions(lme,"-lme_monitor","error_estimate",NULL);

    129:     /* -----------------------------------------------------------------------*/
    130:     PetscOptionsName("-lme_view","Print detailed information on solver used","LMEView",NULL);

    132:     if (lme->ops->setfromoptions) (*lme->ops->setfromoptions)(PetscOptionsObject,lme);
    133:     PetscObjectProcessOptionsHandlers(PetscOptionsObject,(PetscObject)lme);
    134:   ierr = PetscOptionsEnd();

    136:   if (!lme->V) LMEGetBV(lme,&lme->V);
    137:   BVSetFromOptions(lme->V);
    138:   PetscFunctionReturn(0);
    139: }

    141: /*@
    142:    LMESetProblemType - Specifies the type of matrix equation to be solved.

    144:    Logically Collective on lme

    146:    Input Parameters:
    147: +  lme  - the linear matrix equation solver context
    148: -  type - a known type of matrix equation

    150:    Options Database Keys:
    151: +  -lme_lyapunov - continuous-time Lyapunov equation A*X+X*A'=-C
    152: .  -lme_sylvester - continuous-time Sylvester equation A*X+X*B=C
    153: .  -lme_gen_lyapunov - generalized Lyapunov equation A*X*D'+D*X*A'=-C
    154: .  -lme_gen_sylvester - generalized Sylvester equation A*X*E+D*X*B=C
    155: .  -lme_dt_lyapunov - discrete-time Lyapunov equation A*X*A'-X=-C
    156: -  -lme_stein - Stein equation A*X*E+X=C

    158:    Notes:
    159:    The coefficient matrices A, B, D, E must be provided via LMESetCoefficients(),
    160:    but some of them are optional depending on the matrix equation.

    162: .vb
    163:                             equation              A    B    D    E
    164:                           -----------------      ---  ---  ---  ---
    165:        LME_LYAPUNOV        A*X+X*A'=-C           yes (A-t)  -    -
    166:        LME_SYLVESTER       A*X+X*B=C             yes  yes   -    -
    167:        LME_GEN_LYAPUNOV    A*X*D'+D*X*A'=-C      yes (A-t) yes (D-t)
    168:        LME_GEN_SYLVESTER   A*X*E+D*X*B=C         yes  yes  yes  yes
    169:        LME_DT_LYAPUNOV     A*X*A'-X=-C           yes   -    -  (A-t)
    170:        LME_STEIN           A*X*E+X=C             yes   -    -   yes
    171: .ve

    173:    In the above table, the notation (A-t) means that this matrix need
    174:    not be passed, but the user may choose to pass an explicit transpose
    175:    of matrix A (for improved efficiency).

    177:    Also note that some of the equation types impose restrictions on the
    178:    properties of the coefficient matrices and possibly on the right-hand
    179:    side C.

    181:    Level: beginner

    183: .seealso: LMESetCoefficients(), LMESetType(), LMEGetProblemType(), LMEProblemType
    184: @*/
    185: PetscErrorCode LMESetProblemType(LME lme,LMEProblemType type)
    186: {
    189:   if (type == lme->problem_type) PetscFunctionReturn(0);
    190:   switch (type) {
    191:     case LME_LYAPUNOV:
    192:     case LME_SYLVESTER:
    193:     case LME_GEN_LYAPUNOV:
    194:     case LME_GEN_SYLVESTER:
    195:     case LME_DT_LYAPUNOV:
    196:     case LME_STEIN:
    197:       break;
    198:     default:
    199:       SETERRQ(PetscObjectComm((PetscObject)lme),PETSC_ERR_ARG_WRONG,"Unknown matrix equation type");
    200:   }
    201:   lme->problem_type = type;
    202:   lme->setupcalled  = PETSC_FALSE;
    203:   PetscFunctionReturn(0);
    204: }

    206: /*@
    207:    LMEGetProblemType - Gets the matrix equation type from the LME object.

    209:    Not Collective

    211:    Input Parameter:
    212: .  lme - the linear matrix equation solver context

    214:    Output Parameter:
    215: .  type - name of LME problem type

    217:    Level: intermediate

    219: .seealso: LMESetProblemType(), LMEProblemType
    220: @*/
    221: PetscErrorCode LMEGetProblemType(LME lme,LMEProblemType *type)
    222: {
    225:   *type = lme->problem_type;
    226:   PetscFunctionReturn(0);
    227: }

    229: /*@C
    230:    LMEGetTolerances - Gets the tolerance and maximum iteration count used
    231:    by the LME convergence tests.

    233:    Not Collective

    235:    Input Parameter:
    236: .  lme - the linear matrix equation solver context

    238:    Output Parameters:
    239: +  tol - the convergence tolerance
    240: -  maxits - maximum number of iterations

    242:    Notes:
    243:    The user can specify NULL for any parameter that is not needed.

    245:    Level: intermediate

    247: .seealso: LMESetTolerances()
    248: @*/
    249: PetscErrorCode LMEGetTolerances(LME lme,PetscReal *tol,PetscInt *maxits)
    250: {
    252:   if (tol)    *tol    = lme->tol;
    253:   if (maxits) *maxits = lme->max_it;
    254:   PetscFunctionReturn(0);
    255: }

    257: /*@
    258:    LMESetTolerances - Sets the tolerance and maximum iteration count used
    259:    by the LME convergence tests.

    261:    Logically Collective on lme

    263:    Input Parameters:
    264: +  lme - the linear matrix equation solver context
    265: .  tol - the convergence tolerance
    266: -  maxits - maximum number of iterations to use

    268:    Options Database Keys:
    269: +  -lme_tol <tol> - Sets the convergence tolerance
    270: -  -lme_max_it <maxits> - Sets the maximum number of iterations allowed

    272:    Notes:
    273:    Use PETSC_DEFAULT for either argument to assign a reasonably good value.

    275:    Level: intermediate

    277: .seealso: LMEGetTolerances()
    278: @*/
    279: PetscErrorCode LMESetTolerances(LME lme,PetscReal tol,PetscInt maxits)
    280: {
    284:   if (tol == PETSC_DEFAULT) {
    285:     lme->tol = PETSC_DEFAULT;
    286:     lme->setupcalled = 0;
    287:   } else {
    289:     lme->tol = tol;
    290:   }
    291:   if (maxits == PETSC_DEFAULT || maxits == PETSC_DECIDE) {
    292:     lme->max_it = PETSC_DEFAULT;
    293:     lme->setupcalled = 0;
    294:   } else {
    296:     lme->max_it = maxits;
    297:   }
    298:   PetscFunctionReturn(0);
    299: }

    301: /*@
    302:    LMEGetDimensions - Gets the dimension of the subspace used by the solver.

    304:    Not Collective

    306:    Input Parameter:
    307: .  lme - the linear matrix equation solver context

    309:    Output Parameter:
    310: .  ncv - the maximum dimension of the subspace to be used by the solver

    312:    Level: intermediate

    314: .seealso: LMESetDimensions()
    315: @*/
    316: PetscErrorCode LMEGetDimensions(LME lme,PetscInt *ncv)
    317: {
    320:   *ncv = lme->ncv;
    321:   PetscFunctionReturn(0);
    322: }

    324: /*@
    325:    LMESetDimensions - Sets the dimension of the subspace to be used by the solver.

    327:    Logically Collective on lme

    329:    Input Parameters:
    330: +  lme - the linear matrix equation solver context
    331: -  ncv - the maximum dimension of the subspace to be used by the solver

    333:    Options Database Keys:
    334: .  -lme_ncv <ncv> - Sets the dimension of the subspace

    336:    Notes:
    337:    Use PETSC_DEFAULT for ncv to assign a reasonably good value, which is
    338:    dependent on the solution method.

    340:    Level: intermediate

    342: .seealso: LMEGetDimensions()
    343: @*/
    344: PetscErrorCode LMESetDimensions(LME lme,PetscInt ncv)
    345: {
    348:   if (ncv == PETSC_DECIDE || ncv == PETSC_DEFAULT) {
    349:     lme->ncv = PETSC_DEFAULT;
    350:   } else {
    352:     lme->ncv = ncv;
    353:   }
    354:   lme->setupcalled = 0;
    355:   PetscFunctionReturn(0);
    356: }

    358: /*@
    359:    LMESetErrorIfNotConverged - Causes LMESolve() to generate an error if the
    360:    solver has not converged.

    362:    Logically Collective on lme

    364:    Input Parameters:
    365: +  lme - the linear matrix equation solver context
    366: -  flg - PETSC_TRUE indicates you want the error generated

    368:    Options Database Keys:
    369: .  -lme_error_if_not_converged - this takes an optional truth value (0/1/no/yes/true/false)

    371:    Level: intermediate

    373:    Note:
    374:    Normally SLEPc continues if the solver fails to converge, you can call
    375:    LMEGetConvergedReason() after a LMESolve() to determine if it has converged.

    377: .seealso: LMEGetErrorIfNotConverged()
    378: @*/
    379: PetscErrorCode LMESetErrorIfNotConverged(LME lme,PetscBool flg)
    380: {
    383:   lme->errorifnotconverged = flg;
    384:   PetscFunctionReturn(0);
    385: }

    387: /*@
    388:    LMEGetErrorIfNotConverged - Return a flag indicating whether LMESolve() will
    389:    generate an error if the solver does not converge.

    391:    Not Collective

    393:    Input Parameter:
    394: .  lme - the linear matrix equation solver context

    396:    Output Parameter:
    397: .  flag - PETSC_TRUE if it will generate an error, else PETSC_FALSE

    399:    Level: intermediate

    401: .seealso: LMESetErrorIfNotConverged()
    402: @*/
    403: PetscErrorCode LMEGetErrorIfNotConverged(LME lme,PetscBool *flag)
    404: {
    407:   *flag = lme->errorifnotconverged;
    408:   PetscFunctionReturn(0);
    409: }

    411: /*@C
    412:    LMESetOptionsPrefix - Sets the prefix used for searching for all
    413:    LME options in the database.

    415:    Logically Collective on lme

    417:    Input Parameters:
    418: +  lme - the linear matrix equation solver context
    419: -  prefix - the prefix string to prepend to all LME option requests

    421:    Notes:
    422:    A hyphen (-) must NOT be given at the beginning of the prefix name.
    423:    The first character of all runtime options is AUTOMATICALLY the
    424:    hyphen.

    426:    For example, to distinguish between the runtime options for two
    427:    different LME contexts, one could call
    428: .vb
    429:       LMESetOptionsPrefix(lme1,"fun1_")
    430:       LMESetOptionsPrefix(lme2,"fun2_")
    431: .ve

    433:    Level: advanced

    435: .seealso: LMEAppendOptionsPrefix(), LMEGetOptionsPrefix()
    436: @*/
    437: PetscErrorCode LMESetOptionsPrefix(LME lme,const char *prefix)
    438: {
    440:   if (!lme->V) LMEGetBV(lme,&lme->V);
    441:   BVSetOptionsPrefix(lme->V,prefix);
    442:   PetscObjectSetOptionsPrefix((PetscObject)lme,prefix);
    443:   PetscFunctionReturn(0);
    444: }

    446: /*@C
    447:    LMEAppendOptionsPrefix - Appends to the prefix used for searching for all
    448:    LME options in the database.

    450:    Logically Collective on lme

    452:    Input Parameters:
    453: +  lme - the linear matrix equation solver context
    454: -  prefix - the prefix string to prepend to all LME option requests

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

    460:    Level: advanced

    462: .seealso: LMESetOptionsPrefix(), LMEGetOptionsPrefix()
    463: @*/
    464: PetscErrorCode LMEAppendOptionsPrefix(LME lme,const char *prefix)
    465: {
    467:   if (!lme->V) LMEGetBV(lme,&lme->V);
    468:   BVAppendOptionsPrefix(lme->V,prefix);
    469:   PetscObjectAppendOptionsPrefix((PetscObject)lme,prefix);
    470:   PetscFunctionReturn(0);
    471: }

    473: /*@C
    474:    LMEGetOptionsPrefix - Gets the prefix used for searching for all
    475:    LME options in the database.

    477:    Not Collective

    479:    Input Parameters:
    480: .  lme - the linear matrix equation solver context

    482:    Output Parameters:
    483: .  prefix - pointer to the prefix string used is returned

    485:    Note:
    486:    On the Fortran side, the user should pass in a string 'prefix' of
    487:    sufficient length to hold the prefix.

    489:    Level: advanced

    491: .seealso: LMESetOptionsPrefix(), LMEAppendOptionsPrefix()
    492: @*/
    493: PetscErrorCode LMEGetOptionsPrefix(LME lme,const char *prefix[])
    494: {
    497:   PetscObjectGetOptionsPrefix((PetscObject)lme,prefix);
    498:   PetscFunctionReturn(0);
    499: }