318 SUBROUTINE dstemr( JOBZ, RANGE, N, D, E, VL, VU, IL, IU,
319 $ M, W, Z, LDZ, NZC, ISUPPZ, TRYRAC, WORK, LWORK,
320 $ IWORK, LIWORK, INFO )
327 CHARACTER JOBZ, RANGE
329 INTEGER IL, INFO, IU, LDZ, NZC, LIWORK, LWORK, M, N
330 DOUBLE PRECISION VL, VU
333 INTEGER ISUPPZ( * ), IWORK( * )
334 DOUBLE PRECISION D( * ), E( * ), W( * ), WORK( * )
335 DOUBLE PRECISION Z( LDZ, * )
341 DOUBLE PRECISION ZERO, ONE, FOUR, MINRGP
342 PARAMETER ( ZERO = 0.0d0, one = 1.0d0,
347 LOGICAL ALLEIG, INDEIG, LQUERY, VALEIG, WANTZ, ZQUERY
348 INTEGER I, IBEGIN, IEND, IFIRST, IIL, IINDBL, IINDW,
349 $ iindwk, iinfo, iinspl, iiu, ilast, in, indd,
350 $ inde2, inderr, indgp, indgrs, indwrk, itmp,
351 $ itmp2, j, jblk, jj, liwmin, lwmin, nsplit,
352 $ nzcmin, offset, wbegin, wend
353 DOUBLE PRECISION BIGNUM, CS, EPS, PIVMIN, R1, R2, RMAX, RMIN,
354 $ RTOL1, RTOL2, SAFMIN, SCALE, SMLNUM, SN,
355 $ thresh, tmp, tnrm, wl, wu
360 DOUBLE PRECISION DLAMCH, DLANST
361 EXTERNAL lsame, dlamch, dlanst
376 wantz = lsame( jobz,
'V' )
377 alleig = lsame( range,
'A' )
378 valeig = lsame( range,
'V' )
379 indeig = lsame( range,
'I' )
381 lquery = ( ( lwork.EQ.-1 ).OR.( liwork.EQ.-1 ) )
382 zquery = ( nzc.EQ.-1 )
408 ELSEIF( indeig )
THEN
415 IF( .NOT.( wantz .OR. lsame( jobz,
'N' ) ) )
THEN
417 ELSE IF( .NOT.( alleig .OR. valeig .OR. indeig ) )
THEN
419 ELSE IF( n.LT.0 )
THEN
421 ELSE IF( valeig .AND. n.GT.0 .AND. wu.LE.wl )
THEN
423 ELSE IF( indeig .AND. ( iil.LT.1 .OR. iil.GT.n ) )
THEN
425 ELSE IF( indeig .AND. ( iiu.LT.iil .OR. iiu.GT.n ) )
THEN
427 ELSE IF( ldz.LT.1 .OR. ( wantz .AND. ldz.LT.n ) )
THEN
429 ELSE IF( lwork.LT.lwmin .AND. .NOT.lquery )
THEN
431 ELSE IF( liwork.LT.liwmin .AND. .NOT.lquery )
THEN
437 safmin = dlamch(
'Safe minimum' )
438 eps = dlamch(
'Precision' )
439 smlnum = safmin / eps
440 bignum = one / smlnum
441 rmin = sqrt( smlnum )
448 IF( wantz .AND. alleig )
THEN
450 ELSE IF( wantz .AND. valeig )
THEN
451 CALL dlarrc( 't
', N, VL, VU, D, E, SAFMIN,
452 $ NZCMIN, ITMP, ITMP2, INFO )
453.AND.
ELSE IF( WANTZ INDEIG ) THEN
459.AND..EQ.
IF( ZQUERY INFO0 ) THEN
461.LT..AND..NOT.
ELSE IF( NZCNZCMIN ZQUERY ) THEN
468 CALL XERBLA( 'dstemr', -INFO )
471.OR.
ELSE IF( LQUERY ZQUERY ) THEN
482.OR.
IF( ALLEIG INDEIG ) THEN
486.LT..AND..GE.
IF( WLD( 1 ) WUD( 1 ) ) THEN
491.AND..NOT.
IF( WANTZ(ZQUERY) ) THEN
500.NOT.
IF( WANTZ ) THEN
501 CALL DLAE2( D(1), E(1), D(2), R1, R2 )
502.AND..NOT.
ELSE IF( WANTZ(ZQUERY) ) THEN
503 CALL DLAEV2( D(1), E(1), D(2), R1, R2, CS, SN )
506.AND..GT..AND.
$ (VALEIG(R2WL)
508.AND..EQ.
$ (INDEIG(IIL1)) ) THEN
511.AND..NOT.
IF( WANTZ(ZQUERY) ) THEN
530.AND..GT..AND.
$ (VALEIG(R1WL)
532.AND..EQ.
$ (INDEIG(IIU2)) ) THEN
535.AND..NOT.
IF( WANTZ(ZQUERY) ) THEN
577 TNRM = DLANST( 'm
', N, D, E )
578.GT..AND..LT.
IF( TNRMZERO TNRMRMIN ) THEN
580.GT.
ELSE IF( TNRMRMAX ) THEN
583.NE.
IF( SCALEONE ) THEN
584 CALL DSCAL( N, SCALE, D, 1 )
585 CALL DSCAL( N-1, SCALE, E, 1 )
605 CALL DLARRR( N, D, E, IINFO )
621 CALL DCOPY(N,D,1,WORK(INDD),1)
625 WORK( INDE2+J-1 ) = E(J)**2
629.NOT.
IF( WANTZ ) THEN
639 RTOL2 = MAX( SQRT(EPS)*5.0D-3, FOUR * EPS )
641 CALL DLARRE( RANGE, N, WL, WU, IIL, IIU, D, E,
642 $ WORK(INDE2), RTOL1, RTOL2, THRESH, NSPLIT,
643 $ IWORK( IINSPL ), M, W, WORK( INDERR ),
644 $ WORK( INDGP ), IWORK( IINDBL ),
645 $ IWORK( IINDW ), WORK( INDGRS ), PIVMIN,
646 $ WORK( INDWRK ), IWORK( IINDWK ), IINFO )
647.NE.
IF( IINFO0 ) THEN
648 INFO = 10 + ABS( IINFO )
661 CALL DLARRV( N, WL, WU, D, E,
662 $ PIVMIN, IWORK( IINSPL ), M,
663 $ 1, M, MINRGP, RTOL1, RTOL2,
664 $ W, WORK( INDERR ), WORK( INDGP ), IWORK( IINDBL ),
665 $ IWORK( IINDW ), WORK( INDGRS ), Z, LDZ,
666 $ ISUPPZ, WORK( INDWRK ), IWORK( IINDWK ), IINFO )
667.NE.
IF( IINFO0 ) THEN
668 INFO = 20 + ABS( IINFO )
678 ITMP = IWORK( IINDBL+J-1 )
679 W( J ) = W( J ) + E( IWORK( IINSPL+ITMP-1 ) )
689 DO 39 JBLK = 1, IWORK( IINDBL+M-1 )
690 IEND = IWORK( IINSPL+JBLK-1 )
691 IN = IEND - IBEGIN + 1
696.EQ.
IF( IWORK( IINDBL+WEND )JBLK ) THEN
701.LT.
IF( WENDWBEGIN ) THEN
706 OFFSET = IWORK(IINDW+WBEGIN-1)-1
707 IFIRST = IWORK(IINDW+WBEGIN-1)
708 ILAST = IWORK(IINDW+WEND-1)
711 $ WORK(INDD+IBEGIN-1), WORK(INDE2+IBEGIN-1),
712 $ IFIRST, ILAST, RTOL2, OFFSET, W(WBEGIN),
713 $ WORK( INDERR+WBEGIN-1 ),
714 $ WORK( INDWRK ), IWORK( IINDWK ), PIVMIN,
723.NE.
IF( SCALEONE ) THEN
724 CALL DSCAL( M, ONE / SCALE, W, 1 )
733.GT..OR..EQ.
IF( NSPLIT1 N2 ) THEN
734.NOT.
IF( WANTZ ) THEN
735 CALL DLASRT( 'i
', M, W, IINFO )
736.NE.
IF( IINFO0 ) THEN
745.LT.
IF( W( JJ )TMP ) THEN
754 CALL DSWAP( N, Z( 1, I ), 1, Z( 1, J ), 1 )
755 ITMP = ISUPPZ( 2*I-1 )
756 ISUPPZ( 2*I-1 ) = ISUPPZ( 2*J-1 )
757 ISUPPZ( 2*J-1 ) = ITMP
759 ISUPPZ( 2*I ) = ISUPPZ( 2*J )
subroutine dlarrr(n, d, e, info)
DLARRR performs tests to decide whether the symmetric tridiagonal matrix T warrants expensive computa...
subroutine dlarrj(n, d, e2, ifirst, ilast, rtol, offset, w, werr, work, iwork, pivmin, spdiam, info)
DLARRJ performs refinement of the initial estimates of the eigenvalues of the matrix T.
subroutine dlarrc(jobt, n, vl, vu, d, e, pivmin, eigcnt, lcnt, rcnt, info)
DLARRC computes the number of eigenvalues of the symmetric tridiagonal matrix.
subroutine dlae2(a, b, c, rt1, rt2)
DLAE2 computes the eigenvalues of a 2-by-2 symmetric matrix.
subroutine dlarre(range, n, vl, vu, il, iu, d, e, e2, rtol1, rtol2, spltol, nsplit, isplit, m, w, werr, wgap, iblock, indexw, gers, pivmin, work, iwork, info)
DLARRE given the tridiagonal matrix T, sets small off-diagonal elements to zero and for each unreduce...
subroutine dlaev2(a, b, c, rt1, rt2, cs1, sn1)
DLAEV2 computes the eigenvalues and eigenvectors of a 2-by-2 symmetric/Hermitian matrix.
subroutine dlasrt(id, n, d, info)
DLASRT sorts numbers in increasing or decreasing order.
subroutine xerbla(srname, info)
XERBLA
subroutine dlarrv(n, vl, vu, d, l, pivmin, isplit, m, dol, dou, minrgp, rtol1, rtol2, w, werr, wgap, iblock, indexw, gers, z, ldz, isuppz, work, iwork, info)
DLARRV computes the eigenvectors of the tridiagonal matrix T = L D LT given L, D and the eigenvalues ...
subroutine dstemr(jobz, range, n, d, e, vl, vu, il, iu, m, w, z, ldz, nzc, isuppz, tryrac, work, lwork, iwork, liwork, info)
DSTEMR
subroutine dscal(n, da, dx, incx)
DSCAL
subroutine dswap(n, dx, incx, dy, incy)
DSWAP
subroutine dcopy(n, dx, incx, dy, incy)
DCOPY