Actual source code: random.c

      2: /*
      3:     This file contains routines for interfacing to random number generators.
      4:     This provides more than just an interface to some system random number
      5:     generator:

      7:     Numbers can be shuffled for use as random tuples

      9:     Multiple random number generators may be used

     11:     We are still not sure what interface we want here.  There should be
     12:     one to reinitialize and set the seed.
     13:  */

     15: #include <petsc/private/randomimpl.h>

     17: /*@
     18:    PetscRandomGetValue - Generates a random number.  Call this after first calling
     19:    PetscRandomCreate().

     21:    Not Collective

     23:    Input Parameter:
     24: .  r  - the random number generator context

     26:    Output Parameter:
     27: .  val - the value

     29:    Level: intermediate

     31:    Notes:
     32:    Use VecSetRandom() to set the elements of a vector to random numbers.

     34:    When PETSc is compiled for complex numbers this returns a complex number with random real and complex parts.
     35:    Use PetscRandomGetValueReal() to get a random real number.

     37:    To get a complex number with only a random real part, first call PetscRandomSetInterval() with a equal
     38:    low and high imaginary part. Similarly to get a complex number with only a random imaginary part call
     39:    PetscRandomSetInterval() with a equal low and high real part.

     41:    Example of Usage:
     42: .vb
     43:       PetscRandomCreate(PETSC_COMM_WORLD,&r);
     44:       PetscRandomGetValue(r,&value1);
     45:       PetscRandomGetValue(r,&value2);
     46:       PetscRandomGetValue(r,&value3);
     47:       PetscRandomDestroy(&r);
     48: .ve

     50: .seealso: PetscRandomCreate(), PetscRandomDestroy(), VecSetRandom(), PetscRandomGetValueReal()
     51: @*/
     52: PetscErrorCode  PetscRandomGetValue(PetscRandom r,PetscScalar *val)
     53: {
     56:   if (!r->ops->getvalue) {
     58:     (*r->ops->getvalues)(r,1,val);
     59:   } else {
     60:     (*r->ops->getvalue)(r,val);
     61:   }
     62:   PetscObjectStateIncrease((PetscObject)r);
     63:   return 0;
     64: }

     66: /*@
     67:    PetscRandomGetValueReal - Generates a real random number.  Call this after first calling
     68:    PetscRandomCreate().

     70:    Not Collective

     72:    Input Parameter:
     73: .  r  - the random number generator context

     75:    Output Parameter:
     76: .  val - the value

     78:    Level: intermediate

     80:    Notes:
     81:    Use VecSetRandom() to set the elements of a vector to random numbers.

     83:    Example of Usage:
     84: .vb
     85:       PetscRandomCreate(PETSC_COMM_WORLD,&r);
     86:       PetscRandomGetValueReal(r,&value1);
     87:       PetscRandomGetValueReal(r,&value2);
     88:       PetscRandomGetValueReal(r,&value3);
     89:       PetscRandomDestroy(&r);
     90: .ve

     92: .seealso: PetscRandomCreate(), PetscRandomDestroy(), VecSetRandom(), PetscRandomGetValue()
     93: @*/
     94: PetscErrorCode  PetscRandomGetValueReal(PetscRandom r,PetscReal *val)
     95: {
     98:   if (!r->ops->getvaluereal) {
    100:     (*r->ops->getvaluesreal)(r,1,val);
    101:   } else {
    102:     (*r->ops->getvaluereal)(r,val);
    103:   }
    104:   PetscObjectStateIncrease((PetscObject)r);
    105:   return 0;
    106: }

    108: /*@
    109:    PetscRandomGetValues - Generates a sequence of random numbers.  Call this after first calling
    110:    PetscRandomCreate().

    112:    Not Collective

    114:    Input Parameters:
    115: +  r  - the random number generator context
    116: -  n  - number of random numbers to generate

    118:    Output Parameter:
    119: .  val - the array to hold the values

    121:    Level: intermediate

    123:    Notes:
    124:    Use VecSetRandom() to set the elements of a vector to random numbers.

    126:    When PETSc is compiled for complex numbers this returns an array of complex numbers with random real and complex parts.
    127:    Use PetscRandomGetValuesReal() to get an array of random real numbers.

    129: .seealso: PetscRandomCreate(), PetscRandomDestroy(), VecSetRandom(), PetscRandomGetValue()
    130: @*/
    131: PetscErrorCode  PetscRandomGetValues(PetscRandom r, PetscInt n, PetscScalar *val)
    132: {
    135:   if (!r->ops->getvalues) {
    136:     PetscInt i;
    138:     for (i = 0; i < n; i++) {
    139:       (*r->ops->getvalue)(r,val+i);
    140:     }
    141:   } else {
    142:     (*r->ops->getvalues)(r,n,val);
    143:   }
    144:   PetscObjectStateIncrease((PetscObject)r);
    145:   return 0;
    146: }

    148: /*@
    149:    PetscRandomGetValuesReal - Generates a sequence of real random numbers.  Call this after first calling
    150:    PetscRandomCreate().

    152:    Not Collective

    154:    Input Parameters:
    155: +  r  - the random number generator context
    156: -  n  - number of random numbers to generate

    158:    Output Parameter:
    159: .  val - the array to hold the values

    161:    Level: intermediate

    163:    Notes:
    164:    Use VecSetRandom() to set the elements of a vector to random numbers.

    166: .seealso: PetscRandomCreate(), PetscRandomDestroy(), VecSetRandom(), PetscRandomGetValues()
    167: @*/
    168: PetscErrorCode  PetscRandomGetValuesReal(PetscRandom r, PetscInt n, PetscReal *val)
    169: {
    172:   if (!r->ops->getvaluesreal) {
    173:     PetscInt i;
    175:     for (i = 0; i < n; i++) {
    176:       (*r->ops->getvaluereal)(r,val+i);
    177:     }
    178:   } else {
    179:     (*r->ops->getvaluesreal)(r,n,val);
    180:   }
    181:   PetscObjectStateIncrease((PetscObject)r);
    182:   return 0;
    183: }

    185: /*@
    186:    PetscRandomGetInterval - Gets the interval over which the random numbers
    187:    will be randomly distributed.  By default, this interval is [0,1).

    189:    Not collective

    191:    Input Parameter:
    192: .  r  - the random number generator context

    194:    Output Parameters:
    195: +  low - The lower bound of the interval
    196: -  high - The upper bound of the interval

    198:    Level: intermediate

    200: .seealso: PetscRandomCreate(), PetscRandomSetInterval()
    201: @*/
    202: PetscErrorCode  PetscRandomGetInterval(PetscRandom r,PetscScalar *low,PetscScalar *high)
    203: {
    205:   if (low) {
    207:     *low = r->low;
    208:   }
    209:   if (high) {
    211:     *high = r->low+r->width;
    212:   }
    213:   return 0;
    214: }

    216: /*@
    217:    PetscRandomSetInterval - Sets the interval over which the random numbers
    218:    will be randomly distributed.  By default, this interval is [0,1).

    220:    Not collective

    222:    Input Parameters:
    223: +  r  - the random number generator context
    224: .  low - The lower bound of the interval
    225: -  high - The upper bound of the interval

    227:    Level: intermediate

    229:    Notes:
    230:     for complex numbers either the real part or the imaginary part of high must be greater than its low part; or both of them can be greater.
    231:     If the real or imaginary part of low and high are the same then that value is always returned in the real or imaginary part.

    233: .seealso: PetscRandomCreate(), PetscRandomGetInterval()
    234: @*/
    235: PetscErrorCode  PetscRandomSetInterval(PetscRandom r,PetscScalar low,PetscScalar high)
    236: {
    238: #if defined(PETSC_USE_COMPLEX)
    241: #else
    243: #endif
    244:   r->low   = low;
    245:   r->width = high-low;
    246:   r->iset  = PETSC_TRUE;
    247:   return 0;
    248: }