⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 lapacksubs.f

📁 利用离散偶极近似方法计算散射体的电磁场。 DDA 方法
💻 F
📖 第 1 页 / 共 5 页
字号:
*  =====================================================================**     .. Parameters ..      REAL               ONE      PARAMETER          ( ONE = 1.0E+0 )*     ..*     .. Local Scalars ..      INTEGER            I      REAL               AII*     ..*     .. External Subroutines ..      EXTERNAL           SLARF, SLARFG, XERBLA*     ..*     .. Intrinsic Functions ..      INTRINSIC          MAX, MIN*     ..*     .. Executable Statements ..**     Test the input parameters*      INFO = 0      IF( N.LT.0 ) THEN         INFO = -1      ELSE IF( ILO.LT.1 .OR. ILO.GT.MAX( 1, N ) ) THEN         INFO = -2      ELSE IF( IHI.LT.MIN( ILO, N ) .OR. IHI.GT.N ) THEN         INFO = -3      ELSE IF( LDA.LT.MAX( 1, N ) ) THEN         INFO = -5      END IF      IF( INFO.NE.0 ) THEN         CALL XERBLA( 'SGEHD2', -INFO )         RETURN      END IF*      DO 10 I = ILO, IHI - 1**        Compute elementary reflector H(i) to annihilate A(i+2:ihi,i)*         CALL SLARFG( IHI-I, A( I+1, I ), A( MIN( I+2, N ), I ), 1,     $                TAU( I ) )         AII = A( I+1, I )         A( I+1, I ) = ONE**        Apply H(i) to A(1:ihi,i+1:ihi) from the right*         CALL SLARF( 'Right', IHI, IHI-I, A( I+1, I ), 1, TAU( I ),     $               A( 1, I+1 ), LDA, WORK )**        Apply H(i) to A(i+1:ihi,i+1:n) from the left*         CALL SLARF( 'Left', IHI-I, N-I, A( I+1, I ), 1, TAU( I ),     $               A( I+1, I+1 ), LDA, WORK )*         A( I+1, I ) = AII   10 CONTINUE*      RETURN**     End of SGEHD2*      END      SUBROUTINE SGEHRD( N, ILO, IHI, A, LDA, TAU, WORK, LWORK, INFO )**  -- LAPACK routine (version 3.0) --*     Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd.,*     Courant Institute, Argonne National Lab, and Rice University*     June 30, 1999**     .. Scalar Arguments ..      INTEGER            IHI, ILO, INFO, LDA, LWORK, N*     ..*     .. Array Arguments ..      REAL               A( LDA, * ), TAU( * ), WORK( * )*     ..**  Purpose*  =======**  SGEHRD reduces a real general matrix A to upper Hessenberg form H by*  an orthogonal similarity transformation:  Q' * A * Q = H .**  Arguments*  =========**  N       (input) INTEGER*          The order of the matrix A.  N >= 0.**  ILO     (input) INTEGER*  IHI     (input) INTEGER*          It is assumed that A is already upper triangular in rows*          and columns 1:ILO-1 and IHI+1:N. ILO and IHI are normally*          set by a previous call to SGEBAL; otherwise they should be*          set to 1 and N respectively. See Further Details.*          1 <= ILO <= IHI <= N, if N > 0; ILO=1 and IHI=0, if N=0.**  A       (input/output) REAL array, dimension (LDA,N)*          On entry, the N-by-N general matrix to be reduced.*          On exit, the upper triangle and the first subdiagonal of A*          are overwritten with the upper Hessenberg matrix H, and the*          elements below the first subdiagonal, with the array TAU,*          represent the orthogonal matrix Q as a product of elementary*          reflectors. See Further Details.**  LDA     (input) INTEGER*          The leading dimension of the array A.  LDA >= max(1,N).**  TAU     (output) REAL array, dimension (N-1)*          The scalar factors of the elementary reflectors (see Further*          Details). Elements 1:ILO-1 and IHI:N-1 of TAU are set to*          zero.**  WORK    (workspace/output) REAL array, dimension (LWORK)*          On exit, if INFO = 0, WORK(1) returns the optimal LWORK.**  LWORK   (input) INTEGER*          The length of the array WORK.  LWORK >= max(1,N).*          For optimum performance LWORK >= N*NB, where NB is the*          optimal blocksize.**          If LWORK = -1, then a workspace query is assumed; the routine*          only calculates the optimal size of the WORK array, returns*          this value as the first entry of the WORK array, and no error*          message related to LWORK is issued by XERBLA.**  INFO    (output) INTEGER*          = 0:  successful exit*          < 0:  if INFO = -i, the i-th argument had an illegal value.**  Further Details*  ===============**  The matrix Q is represented as a product of (ihi-ilo) elementary*  reflectors**     Q = H(ilo) H(ilo+1) . . . H(ihi-1).**  Each H(i) has the form**     H(i) = I - tau * v * v'**  where tau is a real scalar, and v is a real vector with*  v(1:i) = 0, v(i+1) = 1 and v(ihi+1:n) = 0; v(i+2:ihi) is stored on*  exit in A(i+2:ihi,i), and tau in TAU(i).**  The contents of A are illustrated by the following example, with*  n = 7, ilo = 2 and ihi = 6:**  on entry,                        on exit,**  ( a   a   a   a   a   a   a )    (  a   a   h   h   h   h   a )*  (     a   a   a   a   a   a )    (      a   h   h   h   h   a )*  (     a   a   a   a   a   a )    (      h   h   h   h   h   h )*  (     a   a   a   a   a   a )    (      v2  h   h   h   h   h )*  (     a   a   a   a   a   a )    (      v2  v3  h   h   h   h )*  (     a   a   a   a   a   a )    (      v2  v3  v4  h   h   h )*  (                         a )    (                          a )**  where a denotes an element of the original matrix A, h denotes a*  modified element of the upper Hessenberg matrix H, and vi denotes an*  element of the vector defining H(i).**  =====================================================================**     .. Parameters ..      INTEGER            NBMAX, LDT      PARAMETER          ( NBMAX = 64, LDT = NBMAX+1 )      REAL               ZERO, ONE      PARAMETER          ( ZERO = 0.0E+0, ONE = 1.0E+0 )*     ..*     .. Local Scalars ..      LOGICAL            LQUERY      INTEGER            I, IB, IINFO, IWS, LDWORK, LWKOPT, NB, NBMIN,     $                   NH, NX      REAL               EI*     ..*     .. Local Arrays ..      REAL               T( LDT, NBMAX )*     ..*     .. External Subroutines ..      EXTERNAL           SGEHD2, SGEMM, SLAHRD, SLARFB, XERBLA*     ..*     .. Intrinsic Functions ..      INTRINSIC          MAX, MIN*     ..*     .. External Functions ..      INTEGER            ILAENV      EXTERNAL           ILAENV*     ..*     .. Executable Statements ..**     Test the input parameters*      INFO = 0      NB = MIN( NBMAX, ILAENV( 1, 'SGEHRD', ' ', N, ILO, IHI, -1 ) )      LWKOPT = N*NB      WORK( 1 ) = LWKOPT      LQUERY = ( LWORK.EQ.-1 )      IF( N.LT.0 ) THEN         INFO = -1      ELSE IF( ILO.LT.1 .OR. ILO.GT.MAX( 1, N ) ) THEN         INFO = -2      ELSE IF( IHI.LT.MIN( ILO, N ) .OR. IHI.GT.N ) THEN         INFO = -3      ELSE IF( LDA.LT.MAX( 1, N ) ) THEN         INFO = -5      ELSE IF( LWORK.LT.MAX( 1, N ) .AND. .NOT.LQUERY ) THEN         INFO = -8      END IF      IF( INFO.NE.0 ) THEN         CALL XERBLA( 'SGEHRD', -INFO )         RETURN      ELSE IF( LQUERY ) THEN         RETURN      END IF**     Set elements 1:ILO-1 and IHI:N-1 of TAU to zero*      DO 10 I = 1, ILO - 1         TAU( I ) = ZERO   10 CONTINUE      DO 20 I = MAX( 1, IHI ), N - 1         TAU( I ) = ZERO   20 CONTINUE**     Quick return if possible*      NH = IHI - ILO + 1      IF( NH.LE.1 ) THEN         WORK( 1 ) = 1         RETURN      END IF**     Determine the block size.*      NB = MIN( NBMAX, ILAENV( 1, 'SGEHRD', ' ', N, ILO, IHI, -1 ) )      NBMIN = 2      IWS = 1      IF( NB.GT.1 .AND. NB.LT.NH ) THEN**        Determine when to cross over from blocked to unblocked code*        (last block is always handled by unblocked code).*         NX = MAX( NB, ILAENV( 3, 'SGEHRD', ' ', N, ILO, IHI, -1 ) )         IF( NX.LT.NH ) THEN**           Determine if workspace is large enough for blocked code.*            IWS = N*NB            IF( LWORK.LT.IWS ) THEN**              Not enough workspace to use optimal NB:  determine the*              minimum value of NB, and reduce NB or force use of*              unblocked code.*               NBMIN = MAX( 2, ILAENV( 2, 'SGEHRD', ' ', N, ILO, IHI,     $                 -1 ) )               IF( LWORK.GE.N*NBMIN ) THEN                  NB = LWORK / N               ELSE                  NB = 1               END IF            END IF         END IF      END IF      LDWORK = N*      IF( NB.LT.NBMIN .OR. NB.GE.NH ) THEN**        Use unblocked code below*         I = ILO*      ELSE**        Use blocked code*         DO 30 I = ILO, IHI - 1 - NX, NB            IB = MIN( NB, IHI-I )**           Reduce columns i:i+ib-1 to Hessenberg form, returning the*           matrices V and T of the block reflector H = I - V*T*V'*           which performs the reduction, and also the matrix Y = A*V*T*            CALL SLAHRD( IHI, I, IB, A( 1, I ), LDA, TAU( I ), T, LDT,     $                   WORK, LDWORK )**           Apply the block reflector H to A(1:ihi,i+ib:ihi) from the*           right, computing  A := A - Y * V'. V(i+ib,ib-1) must be set*           to 1.*            EI = A( I+IB, I+IB-1 )            A( I+IB, I+IB-1 ) = ONE            CALL SGEMM( 'No transpose', 'Transpose', IHI, IHI-I-IB+1,     $                  IB, -ONE, WORK, LDWORK, A( I+IB, I ), LDA, ONE,     $                  A( 1, I+IB ), LDA )            A( I+IB, I+IB-1 ) = EI**           Apply the block reflector H to A(i+1:ihi,i+ib:n) from the*           left*            CALL SLARFB( 'Left', 'Transpose', 'Forward', 'Columnwise',     $                   IHI-I, N-I-IB+1, IB, A( I+1, I ), LDA, T, LDT,     $                   A( I+1, I+IB ), LDA, WORK, LDWORK )   30    CONTINUE      END IF**     Use unblocked code to reduce the rest of the matrix*      CALL SGEHD2( N, I, IHI, A, LDA, TAU, WORK, IINFO )      WORK( 1 ) = IWS*      RETURN**     End of SGEHRD*      END      SUBROUTINE SHSEQR( JOB, COMPZ, N, ILO, IHI, H, LDH, WR, WI, Z,     $                   LDZ, WORK, LWORK, INFO )**  -- LAPACK routine (version 3.0) --*     Univ. of Tennessee, Univ. of California Berkeley, NAG Ltd.,*     Courant Institute, Argonne National Lab, and Rice University*     June 30, 1999**     .. Scalar Arguments ..      CHARACTER          COMPZ, JOB      INTEGER            IHI, ILO, INFO, LDH, LDZ, LWORK, N*     ..*     .. Array Arguments ..      REAL               H( LDH, * ), WI( * ), WORK( * ), WR( * ),     $                   Z( LDZ, * )*     ..**  Purpose*  =======**  SHSEQR computes the eigenvalues of a real upper Hessenberg matrix H*  and, optionally, the matrices T and Z from the Schur decomposition*  H = Z T Z**T, where T is an upper quasi-triangular matrix (the Schur*  form), and Z is the orthogonal matrix of Schur vectors.**  Optionally Z may be postmultiplied into an input orthogonal matrix Q,*  so that this routine can give the Schur factorization of a matrix A*  which has been reduced to the Hessenberg form H by the orthogonal*  matrix Q:  A = Q*H*Q**T = (QZ)*T*(QZ)**T.**  Arguments*  =========**  JOB     (input) CHARACTER*1*          = 'E':  compute eigenvalues only;*          = 'S':  compute eigenvalues and the Schur form T.**  COMPZ   (input) CHARACTER*1*          = 'N':  no Schur vectors are computed;*          = 'I':  Z is initialized to the unit matrix and the matrix Z*                  of Schur vectors of H is returned;*          = 'V':  Z must contain an orthogonal matrix Q on entry, and*                  the product Q*Z is returned.**  N       (input) INTEGER*          The order of the matrix H.  N >= 0.**  ILO     (input) INTEGER*  IHI     (input) INTEGER*          It is assumed that H is already upper triangular in rows*          and columns 1:ILO-1 and IHI+1:N. ILO and IHI are normally*          set by a previous call to SGEBAL, and then passed to SGEHRD*          when the matrix output by SGEBAL is reduced to Hessenberg*          form. Otherwise ILO and IHI should be set to 1 and N*          respectively.*          1 <= ILO <= IHI <= N, if N > 0; ILO=1 and IHI=0, if N=0.**  H       (input/output) REAL array, dimension (LDH,N)*          On entry, the upper Hessenberg matrix H.*          On exit, if JOB = 'S', H contains the upper quasi-triangular*          matrix T from the Schur decomposition (the Schur form);*          2-by-2 diagonal blocks (corresponding to complex conjugate*          pairs of eigenvalues) are returned in standard form, with*          H(i,i) = H(i+1,i+1) and H(i+1,i)*H(i,i+1) < 0. If JOB = 'E',*          the contents of H are unspecified on exit.**  LDH     (input) INTEGER*          The leading dimension of the array H. LDH >= max(1,N).**  WR      (output) REAL array, dimension (N)*  WI      (output) REAL array, dimension (N)*          The real and imaginary parts, respectively, of the computed*          eigenvalues. If two eigenvalues are computed as a complex*          conjugate pair, they are stored in consecutive elements of*          WR and WI, say the i-th and (i+1)th, with WI(i) > 0 and*          WI(i+1) < 0. If JOB = 'S', the eigenvalues are stored in the*          same order as on the diagonal of the Schur form returned in*          H, with WR(i) = H(i,i) and, if H(i:i+1,i:i+1) is a 2-by-2*          diagonal block, WI(i) = sqrt(H(i+1,i)*H(i,i+1)) and*          WI(i+1) = -WI(i).**  Z       (input/output) REAL array, dimension (LDZ,N)*          If COMPZ = 'N': Z is not referenced.*          If COMPZ = 'I': on entry, Z need not be set, and on exit, Z*          contains the orthogonal matrix Z of the Schur vectors of H.*          If COMPZ = 'V': on entry Z must contain an N-by-N matrix Q,*          which is assumed to be equal to the unit matrix except for*          the submatrix Z(ILO:IHI,ILO:IHI); on exit Z contains Q*Z.*          Normally Q is the orthogonal matrix generated by SORGHR after*          the call to SGEHRD which formed the Hessenberg matrix H.**  LDZ     (input) INTEGER*          The leading dimension of the array Z.*          LDZ >= max(1,N) if COMPZ = 'I' or 'V'; LDZ >= 1 otherwise.**  WORK    (workspace/output) REAL array, dimension (LWORK)*          On exit, if INFO = 0, WORK(1) returns the optimal LWORK.**  LWORK   (input) INTEGER*          The dimension of the array WORK.  LWORK >= max(1,N).**          If LWORK = -1, then a workspace query is assumed; the routine*          only calculates the optimal size of the WORK array, returns*          this value as the first entry of the WORK array, and no error*          message related to LWORK is issued by XERBLA.**  INFO    (output) INTEGER

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -