TESTING/EIG/zchkst.f(3)

πŸ“¦
version 3.12.1 Β· 2 versions
, in arch rolling

πŸŽ€ NAME πŸŽ€

TESTING/EIG/zchkst.f β€” okay so before we even get into it, this page is from the Library Functions Manual, and the whole vibe here is that one file. That's it. That's the name. Short, sweet, iconic πŸ’…


✨ SYNOPSIS ✨

πŸ¦‹ Functions/Subroutines πŸ¦‹

  • subroutine zchkst (nsizes, nn, ntypes, dotype, iseed, thresh, nounit, a, lda, ap, sd, se, d1, d2, d3, d4, d5, wa1, wa2, wa3, wr, u, ldu, v, vp, tau, z, work, lwork, rwork, lrwork, iwork, liwork, result, info) β€” the one and only ZCHKST, bestie. Yes, look at all those arguments. She's that girl. πŸ‘‘

🌸 Function/Subroutine Documentation 🌸

πŸ’– subroutine zchkst πŸ’–

The full signature, in all her glory β€” and ngl she's got a LOT going on, so here it is laid out exactly, no cap:

subroutine zchkst (integer nsizes, integer, dimension( * ) nn, integer
    ntypes, logical, dimension( * ) dotype, integer, dimension( 4 ) iseed,
    double precision thresh, integer nounit, complex*16, dimension( lda, * )
    a, integer lda, complex*16, dimension( * ) ap, double precision,
    dimension( * ) sd, double precision, dimension( * ) se, double
    precision, dimension( * ) d1, double precision, dimension( * ) d2,
    double precision, dimension( * ) d3, double precision, dimension( * )
    d4, double precision, dimension( * ) d5, double precision, dimension( *
    ) wa1, double precision, dimension( * ) wa2, double precision,
    dimension( * ) wa3, double precision, dimension( * ) wr, complex*16,
    dimension( ldu, * ) u, integer ldu, complex*16, dimension( ldu, * ) v,
    complex*16, dimension( * ) vp, complex*16, dimension( * ) tau,
    complex*16, dimension( ldu, * ) z, complex*16, dimension( * ) work,
    integer lwork, double precision, dimension( * ) rwork, integer lrwork,
    integer, dimension( * ) iwork, integer liwork, double precision,
    dimension( * ) result, integer info)

ZCHKST 🫢

Okay so real talk β€” that argument list is long, so here's every single one of them broken out with her exact declared type, because we do not skip deets in this house πŸ’€βœ¨

  • integer nsizes β€” integer, bestie.
  • integer, dimension( * ) nn β€” array of integers, dimension *.
  • integer ntypes β€” integer.
  • logical, dimension( * ) dotype β€” array of logicals, dimension *.
  • integer, dimension( 4 ) iseed β€” array of integers, dimension 4 (yes, specifically 4, not *, don't come for her).
  • double precision thresh β€” double precision scalar.
  • integer nounit β€” integer.
  • complex*16, dimension( lda, * ) a β€” 2-D complex*16 array, dimension ( lda, * ).
  • integer lda β€” integer.
  • complex*16, dimension( * ) ap β€” complex*16 array, dimension *.
  • double precision, dimension( * ) sd β€” double precision array, dimension *.
  • double precision, dimension( * ) se β€” same energy, dimension *.
  • double precision, dimension( * ) d1 β€” yup, *.
  • double precision, dimension( * ) d2 β€” 🌈 another one.
  • double precision, dimension( * ) d3 β€” she keeps going.
  • double precision, dimension( * ) d4 β€” iconic, no notes.
  • double precision, dimension( * ) d5 β€” the last of the d-squad πŸ’œ
  • double precision, dimension( * ) wa1 β€” double precision array.
  • double precision, dimension( * ) wa2 β€” double precision array.
  • double precision, dimension( * ) wa3 β€” double precision array.
  • double precision, dimension( * ) wr β€” double precision array.
  • complex*16, dimension( ldu, * ) u β€” 2-D complex*16, dimension ( ldu, * ).
  • integer ldu β€” integer (and yes, she's the leading dimension for u, v and z β€” the way she multi-tasks 😭).
  • complex*16, dimension( ldu, * ) v β€” 2-D complex*16, dimension ( ldu, * ).
  • complex*16, dimension( * ) vp β€” complex*16 array, dimension *.
  • complex*16, dimension( * ) tau β€” complex*16 array, dimension *.
  • complex*16, dimension( ldu, * ) z β€” 2-D complex*16, dimension ( ldu, * ).
  • complex*16, dimension( * ) work β€” complex*16 workspace array, dimension *.
  • integer lwork β€” integer.
  • double precision, dimension( * ) rwork β€” double precision array, dimension *.
  • integer lrwork β€” integer.
  • integer, dimension( * ) iwork β€” integer array, dimension *.
  • integer liwork β€” integer.
  • double precision, dimension( * ) result β€” double precision array, dimension *.
  • integer info β€” integer. The classic. The main character of every LAPACK-adjacent signature 🌟
Fr fr, that's the whole parameter list β€” every single argument, exact types, nothing merged, nothing dropped. Copy-paste her into your code and she'll be happy. πŸ’–

🧚 Purpose 🧚

okay so this is where the Purpose: section starts β€” and that's literally where this part of the page stops, bestie. The deets keep rolling in the next bit, so don't close the tab πŸ¦‹βœ¨

ZUNGTR builds the matrix U out of whatever's sitting in V and TAU, and ZUPGTR does the exact same glow-up for VP and TAU. Iconic, no notes. ✨

ZSTEQR factors S as Z D1 Z*, where Z is the unitary matrix of eigenvectors and D1 is a diagonal matrix with the eigenvalues chillin' on the diagonal. D2? That's the matrix of eigenvalues you get when Z is not computed. Two moods, same tea.

DSTERF computes D3, the matrix of eigenvalues, via the PWK method β€” which is giving "eigenvalues only, no eigenvectors, we don't do plus-ones" πŸ’€

ZPTEQR factors S as Z4 D4 Z4*, for a Hermitian positive definite tridiagonal matrix. D5 is the matrix of eigenvalues computed when Z is not computed.

DSTEBZ computes selected eigenvalues. WA1, WA2, and WA3 denote eigenvalues computed to high absolute accuracy, with different range options. WR denotes eigenvalues computed to high relative accuracy. Know the difference, bestie, it matters 🫢

ZSTEIN computes Y, the eigenvectors of S, given the eigenvalues.

ZSTEDC factors S as Z D1 Z*, where Z is the unitary matrix of eigenvectors and D1 is diagonal with the eigenvalues on the diagonal ('I' option). It may also update an input unitary matrix β€” usually the output from ZHETRD/ZUNGTR or ZHPTRD/ZUPGTR (that's the 'V' option). And it may also just compute eigenvalues (the 'N' option). Versatile queen πŸ‘‘

ZSTEMR factors S as Z D1 Z*, where Z is the unitary matrix of eigenvectors and D1 is diagonal with the eigenvalues on the diagonal ('I' option). ZSTEMR uses the Relatively Robust Representation whenever possible. Fancy. 🌸


When ZCHKST is called, a number of matrix sizes and a number of matrix types are specified. For each size and each type of matrix, one matrix gets generated and used to test the Hermitian eigenroutines. For each matrix, a whole pile of tests runs:

  • (1) β€” | A - V S V* | / ( |A| n ulp ) for ZHETRD( UPLO='U', ... )
  • (2) β€” | I - UV* | / ( n ulp ) for ZUNGTR( UPLO='U', ... )
  • (3) β€” | A - V S V* | / ( |A| n ulp ) for ZHETRD( UPLO='L', ... )
  • (4) β€” | I - UV* | / ( n ulp ) for ZUNGTR( UPLO='L', ... )
  • (5-8) β€” same as 1-4, but for ZHPTRD and ZUPGTR. Same energy, packed format.
  • (9) β€” | S - Z D Z* | / ( |S| n ulp ) for ZSTEQR('V',...)
  • (10) β€” | I - ZZ* | / ( n ulp ) for ZSTEQR('V',...)
  • (11) β€” | D1 - D2 | / ( |D1| ulp ) for ZSTEQR('N',...)
  • (12) β€” | D1 - D3 | / ( |D1| ulp ) for DSTERF
  • (13) β€” 0 if the true eigenvalues (computed by sturm count) of S are within THRESH of those in D1. 2*THRESH if they are not. (Tested using DSTECH.)

For S positive definite:

  • (14) β€” | S - Z4 D4 Z4* | / ( |S| n ulp ) for ZPTEQR('V',...)
  • (15) β€” | I - Z4 Z4* | / ( n ulp ) for ZPTEQR('V',...)
  • (16) β€” | D4 - D5 | / ( 100 |D4| ulp ) for ZPTEQR('N',...)

When S is also diagonally dominant by the factor gamma < 1:

(17)    max | D4(i) - WR(i) | / ( |D4(i)| omega ) ,
         i
        omega = 2 (2n-1) ULP (1 + 8 gamma**2) / (1 - gamma)**4
                                             DSTEBZ( 'A', 'E', ...)
(18)    | WA1 - D3 | / ( |D3| ulp )          DSTEBZ( 'A', 'E', ...)
(19)    ( max { min | WA2(i)-WA3(j) | } +
           i     j
          max { min | WA3(i)-WA2(j) | } ) / ( |D3| ulp )
           i     j
                                             DSTEBZ( 'I', 'E', ...)
  • (20) β€” | S - Y WA1 Y* | / ( |S| n ulp ) via DSTEBZ, ZSTEIN
  • (21) β€” | I - Y Y* | / ( n ulp ) via DSTEBZ, ZSTEIN
  • (22) β€” | S - Z D Z* | / ( |S| n ulp ) for ZSTEDC('I')
  • (23) β€” | I - ZZ* | / ( n ulp ) for ZSTEDC('I')
  • (24) β€” | S - Z D Z* | / ( |S| n ulp ) for ZSTEDC('V')
  • (25) β€” | I - ZZ* | / ( n ulp ) for ZSTEDC('V')
  • (26) β€” | D1 - D2 | / ( |D1| ulp ) for ZSTEDC('V') and ZSTEDC('N')
Test 27 is disabled at the moment because ZSTEMR does not guarantee high relative accuracy. 🚨
(27)    max | D6(i) - WR(i) | / ( |D6(i)| omega ) ,
         i
        omega = 2 (2n-1) ULP (1 + 8 gamma**2) / (1 - gamma)**4
                                             ZSTEMR('V', 'A')
(28)    max | D6(i) - WR(i) | / ( |D6(i)| omega ) ,
         i
        omega = 2 (2n-1) ULP (1 + 8 gamma**2) / (1 - gamma)**4
                                             ZSTEMR('V', 'I')
Tests 29 through 34 are disabled at present because ZSTEMR does not handle partial spectrum requests. 😭
  • (29) β€” | S - Z D Z* | / ( |S| n ulp ) for ZSTEMR('V', 'I')
  • (30) β€” | I - ZZ* | / ( n ulp ) for ZSTEMR('V', 'I')
(31)    ( max { min | WA2(i)-WA3(j) | } +
           i     j
          max { min | WA3(i)-WA2(j) | } ) / ( |D3| ulp )
           i     j
        ZSTEMR('N', 'I') vs. CSTEMR('V', 'I')
  • (32) β€” | S - Z D Z* | / ( |S| n ulp ) for ZSTEMR('V', 'V')
  • (33) β€” | I - ZZ* | / ( n ulp ) for ZSTEMR('V', 'V')
(34)    ( max { min | WA2(i)-WA3(j) | } +
           i     j
          max { min | WA3(i)-WA2(j) | } ) / ( |D3| ulp )
           i     j
        ZSTEMR('N', 'V') vs. CSTEMR('V', 'V')
  • (35) β€” | S - Z D Z* | / ( |S| n ulp ) for ZSTEMR('V', 'A')
  • (36) β€” | I - ZZ* | / ( n ulp ) for ZSTEMR('V', 'A')
(37)    ( max { min | WA2(i)-WA3(j) | } +
           i     j
          max { min | WA3(i)-WA2(j) | } ) / ( |D3| ulp )
           i     j
        ZSTEMR('N', 'A') vs. CSTEMR('V', 'A')

The sizes are specified by an array NN(1:NSIZES) β€” each element NN(j) says one size. The types are specified by a logical array DOTYPE( 1:NTYPES ) β€” if DOTYPE(j) is .TRUE., then matrix type j gets generated. Currently the list of possible types is, and I'm obsessed with how thorough this is:

  • (1) β€” the zero matrix.
  • (2) β€” the identity matrix.
  • (3) β€” a diagonal matrix with evenly spaced entries 1, ..., ULP and random signs. (ULP = (first number larger than 1) - 1)
  • (4) β€” a diagonal matrix with geometrically spaced entries 1, ..., ULP and random signs.
  • (5) β€” a diagonal matrix with entries 1, ULP, ..., ULP and random signs.
  • (6) β€” same as (4), but multiplied by SQRT( overflow threshold ).
  • (7) β€” same as (4), but multiplied by SQRT( underflow threshold ).
  • (8) β€” a matrix of the form U* D U, where U is unitary and D has evenly spaced entries 1, ..., ULP with random signs on the diagonal.
  • (9) β€” a matrix of the form U* D U, where U is unitary and D has geometrically spaced entries 1, ..., ULP with random signs on the diagonal.
  • (10) β€” a matrix of the form U* D U, where U is unitary and D has entries 1, ULP,..., ULP with random signs on the diagonal.
  • (11) β€” same as (8), but multiplied by SQRT( overflow threshold ).
  • (12) β€” same as (8), but multiplied by SQRT( underflow threshold ).
  • (13) β€” Hermitian matrix with random entries chosen from (-1,1).
  • (14) β€” same as (13), but multiplied by SQRT( overflow threshold ).
  • (15) β€” same as (13), but multiplied by SQRT( underflow threshold ).
  • (16) β€” same as (8), but diagonal elements are all positive.
  • (17) β€” same as (9), but diagonal elements are all positive.
  • (18) β€” same as (10), but diagonal elements are all positive.
  • (19) β€” same as (16), but multiplied by SQRT( overflow threshold ).
  • (20) β€” same as (16), but multiplied by SQRT( underflow threshold ).
  • (21) β€” a diagonally dominant tridiagonal matrix with geometrically spaced diagonal entries 1, ..., ULP.

🌸 Parameters 🌸

NSIZES

NSIZES is INTEGER.

The number of sizes of matrices to use. If it's zero, ZCHKST does nothing β€” full couch potato mode 😴. It must be at least zero.

NN

NN is INTEGER array, dimension (NSIZES).

An array containing the sizes to be used for the matrices. Zero values get skipped. The values must be at least zero.

NTYPES

NTYPES is INTEGER.

The number of elements in DOTYPE. If it's zero, ZCHKST does nothing (again β€” iconically lazy). It must be at least zero.

If it is MAXTYP+1 and NSIZES is 1, then an additional type, MAXTYP+1, is defined, which is to use whatever matrix is already in A. Heads up though: this is only useful if DOTYPE(1:MAXTYP) is .FALSE. and DOTYPE(MAXTYP+1) is .TRUE.. iykyk πŸ’…

DOTYPE

…and DOTYPE is up next, bestie β€” its description keeps rolling in the next bit 🫢

  • DOTYPE β€” LOGICAL array, dimension (NTYPES). If DOTYPE(j) is .TRUE., then for each size in NN a matrix of that size and of type j will be generated ✨. And okay, the rules: if NTYPES is smaller than the maximum number of types defined (PARAMETER MAXTYP), then types NTYPES+1 through MAXTYP will not be generated. If NTYPES is larger than MAXTYP, DOTYPE(MAXTYP+1) through DOTYPE(NTYPES) will be ignored πŸ™ˆ. That's it, that's the whole vibe.
  • ISEED β€” INTEGER array, dimension (4). On entry, ISEED specifies the seed of the random number generator 🌱. The array elements should be between 0 and 4095; if not, they will be reduced mod 4096. Also β€” important β€” ISEED(4) must be odd (like, actually, no cap). The random number generator uses a linear congruential sequence limited to small integers, and so should produce machine independent random numbers. The values of ISEED are changed on exit, and can be used in the next call to ZCHKST to continue the same random number sequence. Slay, continuity πŸ’….
  • THRESH β€” DOUBLE PRECISION. A test will count as [failed] if the [error ratio], computed as described above, exceeds THRESH. Note that the error is scaled to be O(1), so THRESH should be a reasonably small multiple of 1, e.g., 10 or 100 πŸ”₯. In particular, it should not depend on the precision (single vs. double) or the size of the matrix. It must be at least zero. Like, zero is the floor, bestie.
  • NOUNIT β€” INTEGER. The FORTRAN unit number for printing out error messages (e.g., if a routine returns IINFO not equal to 0.) 🫢 Your little messenger pigeon for bad news.
  • A β€” COMPLEX*16 array of dimension ( LDA , max(NN) ). Used to hold the matrix whose eigenvalues are to be computed. On exit, A contains the last matrix actually used. Main character array, honestly πŸ‘‘.
  • LDA β€” INTEGER. The leading dimension of A. It must be at least 1 and at least max( NN ).
  • AP β€” COMPLEX*16 array of dimension ( max(NN)*max(NN+1)/2 ). The matrix A stored in packed format πŸŽ€.
  • SD β€” DOUBLE PRECISION array of dimension ( max(NN) ). The diagonal of the tridiagonal matrix computed by ZHETRD. On exit, SD and SE contain the tridiagonal form of the matrix in A.
  • SE β€” DOUBLE PRECISION array of dimension ( max(NN) ). The off-diagonal of the tridiagonal matrix computed by ZHETRD. On exit, SD and SE contain the tridiagonal form of the matrix in A. Besties, they come as a pair πŸ’–.
  • D1 β€” DOUBLE PRECISION array of dimension ( max(NN) ). The eigenvalues of A, as computed by ZSTEQR simultaneously with Z. On exit, the eigenvalues in D1 correspond with the matrix in A.
  • D2 β€” DOUBLE PRECISION array of dimension ( max(NN) ). The eigenvalues of A, as computed by ZSTEQR if Z is not computed. On exit, the eigenvalues in D2 correspond with the matrix in A.
  • D3 β€” DOUBLE PRECISION array of dimension ( max(NN) ). The eigenvalues of A, as computed by DSTERF. On exit, the eigenvalues in D3 correspond with the matrix in A. Three D's, three routines, three vibes ✨.
  • D4 β€” DOUBLE PRECISION array of dimension ( max(NN) ). The eigenvalues of A, as computed by ZPTEQR(V). ZPTEQR factors S as Z4 D4 Z4*. On exit, the eigenvalues in D4 correspond with the matrix in A.
  • D5 β€” DOUBLE PRECISION array of dimension ( max(NN) ). The eigenvalues of A, as computed by ZPTEQR(N) when Z is not computed. On exit, the eigenvalues in D4 correspond with the matrix in A. (Yes, it says D4 β€” I'm just passing along the message, don't come for me πŸ’€.)
  • WA1 β€” DOUBLE PRECISION array of dimension ( max(NN) ). All eigenvalues of A, computed to high absolute accuracy, with different range options, as computed by DSTEBZ.
  • WA2 β€” DOUBLE PRECISION array of dimension ( max(NN) ). Selected eigenvalues of A, computed to high absolute accuracy, with different range options, as computed by DSTEBZ. Choose random values for IL and IU, and ask for the IL-th through IU-th eigenvalues 🎲.
  • WA3 β€” DOUBLE PRECISION array of dimension ( max(NN) ). Selected eigenvalues of A, computed to high absolute accuracy, with different range options, as computed by DSTEBZ. Determine the values VL and VU of the IL-th and IU-th eigenvalues and ask for all eigenvalues in this range.
  • WR β€” DOUBLE PRECISION array of dimension ( max(NN) ). All eigenvalues of A, computed to high absolute accuracy, with different options, as computed by DSTEBZ.
  • U β€” COMPLEX*16 array of dimension ( LDU, max(NN) ). The unitary matrix computed by ZHETRD + ZUNGTR πŸ¦‹.
  • LDU β€” INTEGER. The leading dimension of U, Z, and V. It must be at least 1 and at least max( NN ). One number to rule all three, periodt πŸ’….
  • V β€” COMPLEX*16 array of dimension ( LDU, max(NN) ). The Housholder vectors computed by ZHETRD in reducing A to tridiagonal form. The vectors computed with UPLO='U' are in the upper triangle, and the vectors computed with UPLO='L' are in the lower triangle. (As described in ZHETRD, the sub- and superdiagonal are not set to 1, although the true Householder vector has a 1 in that position. The routines that use V, such as ZUNGTR, set those entries to 1 before using them, and then restore them later.) Like a friend who borrows your hoodie and puts it back exactly how it was 🫢.
  • VP β€” COMPLEX*16 array of dimension ( max(NN)*max(NN+1)/2 ). The matrix V stored in packed format.
  • TAU β€” COMPLEX*16 array of dimension ( max(NN) ). The Householder factors computed by ZHETRD in reducing A to tridiagonal form.
  • Z β€” COMPLEX*16 array of dimension ( LDU, max(NN) ). The unitary matrix of eigenvectors computed by ZSTEQR, ZPTEQR, and ZSTEIN 🌸.
  • WORK β€” COMPLEX*16 array of dimension ( LWORK ). Scratch space, doing the behind-the-scenes labour 😭.
  • LWORK β€” INTEGER. The number of entries in WORK. This must be at least
1 + 4 * Nmax + 2 * Nmax * lg Nmax + 3 * Nmax**2

where Nmax = max( NN(j), 2 ) and lg = log base 2. Math girlies stay winning πŸ“βœ¨.

  • IWORK β€” INTEGER array. Workspace.
  • LIWORK β€” INTEGER. The number of entries in IWORK. This must be at least
6 + 6*Nmax + 5 * Nmax * lg Nmax

where Nmax = max( NN(j), 2 ) and lg = log base 2. Yes it's a different formula from LWORK, don't mix them up bestie πŸ’€.

  • RWORK β€” DOUBLE PRECISION array. (That's the whole description. Short king πŸ‘‘.)
  • LRWORK β€” INTEGER. The number of entries in LRWORK (dimension( ??? ) πŸ™ˆ β€” yeah, the docs leave that one as a mystery, I'm not gonna invent an answer).
  • RESULT β€” DOUBLE PRECISION array, dimension (26). The values computed by the tests described above. The values are currently limited to 1/ulp, to avoid overflow. Twenty-six little report cards πŸ”₯.
  • INFO

INFO is INTEGER πŸ’–

  • If 0, then everything ran OK. Slay.
  • -1: NSIZES < 0
  • -2: Some NN(j) < 0
  • -3: NTYPES < 0
  • -5: THRESH < 0
  • -9: LDA < 1 or LDA < NMAX, where NMAX is max( NN(j) ).
  • -23: LDU < 1 or LDU < NMAX.
  • -29: LWORK too small.
  • If ZLATMR, CLATMS, ZHETRD, ZUNGTR, ZSTEQR, DSTERF, or ZUNMC2 returns an error code, the absolute value of it is returned.

🧚 Some Local Variables and Parameters 🧚

---- ----- --------- --- ----------

  • ZERO, ONE β€” real 0 and 1.
  • MAXTYP β€” the number of types defined.
  • NTEST β€” the number of tests performed, or which can be performed so far, for the current matrix.
  • NTESTT β€” the total number of tests performed so far.
  • NBLOCK β€” blocksize as returned by ENVIR.
  • NMAX β€” largest value in NN.
  • NMATS β€” the number of matrices generated so far.
  • NERRS β€” the number of tests which have exceeded THRESH so far.
  • COND, IMODE β€” values to be passed to the matrix generators.
  • ANORM β€” norm of A; passed to matrix generators.
  • OVFL, UNFL β€” overflow and underflow thresholds.
  • ULP, ULPINV β€” finest relative precision and its inverse.
  • RTOVFL, RTUNFL β€” square roots of the previous 2 values.

The following four arrays decode JTYPE:

  • KTYPE(j) β€” the general type (1-10) for type .
  • KMODE(j) β€” the MODE value to be passed to the matrix generator for type .
  • KMAGN(j) β€” the order of magnitude ( O(1), O(overflow^(1/2) ), O(underflow^(1/2) ) ).

🌸 Author 🌸

  • Univ. of Tennessee
  • Univ. of California Berkeley
  • Univ. of Colorado Denver
  • NAG Ltd.

Definition at line 599 of file zchkst.f.

πŸŽ€ Author πŸŽ€

Generated automatically by Doxygen for LAPACK from the source code.


Cute sign-off bestie: this one’s LAPACK Version 3.12.0, source TESTING/EIG/zchkst.f(3), and the footer doesn’t give a date β€” so that’s the whole vibe. Mwah πŸ’‹βœ¨

πŸ“¦ where this page comes from