00001 SUBROUTINE SGSVJ1( JOBV, M, N, N1, A, LDA, D, SVA, MV, V, LDV,
00002 + EPS, SFMIN, TOL, NSWEEP, WORK, LWORK, INFO )
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018 IMPLICIT NONE
00019
00020
00021 REAL EPS, SFMIN, TOL
00022 INTEGER INFO, LDA, LDV, LWORK, M, MV, N, N1, NSWEEP
00023 CHARACTER*1 JOBV
00024
00025
00026 REAL A( LDA, * ), D( N ), SVA( N ), V( LDV, * ),
00027 + WORK( LWORK )
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042
00043
00044
00045
00046
00047
00048
00049
00050
00051
00052
00053
00054
00055
00056
00057
00058
00059
00060
00061
00062
00063
00064
00065
00066
00067
00068
00069
00070
00071
00072
00073
00074
00075
00076
00077
00078
00079
00080
00081
00082
00083
00084
00085
00086
00087
00088
00089
00090
00091
00092
00093
00094
00095
00096
00097
00098
00099
00100
00101
00102
00103
00104
00105
00106
00107
00108
00109
00110
00111
00112
00113
00114
00115
00116
00117
00118
00119
00120
00121
00122
00123
00124
00125
00126
00127
00128
00129
00130
00131
00132
00133
00134
00135
00136
00137
00138
00139
00140
00141
00142
00143
00144
00145
00146
00147
00148
00149
00150
00151
00152
00153
00154
00155
00156
00157
00158
00159
00160
00161
00162
00163 REAL ZERO, HALF, ONE, TWO
00164 PARAMETER ( ZERO = 0.0E0, HALF = 0.5E0, ONE = 1.0E0,
00165 + TWO = 2.0E0 )
00166
00167
00168 REAL AAPP, AAPP0, AAPQ, AAQQ, APOAQ, AQOAP, BIG,
00169 + BIGTHETA, CS, LARGE, MXAAPQ, MXSINJ, ROOTBIG,
00170 + ROOTEPS, ROOTSFMIN, ROOTTOL, SMALL, SN, T,
00171 + TEMP1, THETA, THSIGN
00172 INTEGER BLSKIP, EMPTSW, i, ibr, igl, IERR, IJBLSK,
00173 + ISWROT, jbc, jgl, KBL, MVL, NOTROT, nblc, nblr,
00174 + p, PSKIPPED, q, ROWSKIP, SWBAND
00175 LOGICAL APPLV, ROTOK, RSVEC
00176
00177
00178 REAL FASTR( 5 )
00179
00180
00181 INTRINSIC ABS, AMAX1, FLOAT, MIN0, SIGN, SQRT
00182
00183
00184 REAL SDOT, SNRM2
00185 INTEGER ISAMAX
00186 LOGICAL LSAME
00187 EXTERNAL ISAMAX, LSAME, SDOT, SNRM2
00188
00189
00190 EXTERNAL SAXPY, SCOPY, SLASCL, SLASSQ, SROTM, SSWAP
00191
00192
00193
00194
00195
00196 APPLV = LSAME( JOBV, 'A' )
00197 RSVEC = LSAME( JOBV, 'V' )
00198 IF( .NOT.( RSVEC .OR. APPLV .OR. LSAME( JOBV, 'N' ) ) ) THEN
00199 INFO = -1
00200 ELSE IF( M.LT.0 ) THEN
00201 INFO = -2
00202 ELSE IF( ( N.LT.0 ) .OR. ( N.GT.M ) ) THEN
00203 INFO = -3
00204 ELSE IF( N1.LT.0 ) THEN
00205 INFO = -4
00206 ELSE IF( LDA.LT.M ) THEN
00207 INFO = -6
00208 ELSE IF( MV.LT.0 ) THEN
00209 INFO = -9
00210 ELSE IF( LDV.LT.M ) THEN
00211 INFO = -11
00212 ELSE IF( TOL.LE.EPS ) THEN
00213 INFO = -14
00214 ELSE IF( NSWEEP.LT.0 ) THEN
00215 INFO = -15
00216 ELSE IF( LWORK.LT.M ) THEN
00217 INFO = -17
00218 ELSE
00219 INFO = 0
00220 END IF
00221
00222
00223 IF( INFO.NE.0 ) THEN
00224 CALL XERBLA( 'SGSVJ1', -INFO )
00225 RETURN
00226 END IF
00227
00228 IF( RSVEC ) THEN
00229 MVL = N
00230 ELSE IF( APPLV ) THEN
00231 MVL = MV
00232 END IF
00233 RSVEC = RSVEC .OR. APPLV
00234
00235 ROOTEPS = SQRT( EPS )
00236 ROOTSFMIN = SQRT( SFMIN )
00237 SMALL = SFMIN / EPS
00238 BIG = ONE / SFMIN
00239 ROOTBIG = ONE / ROOTSFMIN
00240 LARGE = BIG / SQRT( FLOAT( M*N ) )
00241 BIGTHETA = ONE / ROOTEPS
00242 ROOTTOL = SQRT( TOL )
00243
00244
00245
00246
00247
00248 EMPTSW = N1*( N-N1 )
00249 NOTROT = 0
00250 FASTR( 1 ) = ZERO
00251
00252
00253
00254 KBL = MIN0( 8, N )
00255 NBLR = N1 / KBL
00256 IF( ( NBLR*KBL ).NE.N1 )NBLR = NBLR + 1
00257
00258
00259
00260 NBLC = ( N-N1 ) / KBL
00261 IF( ( NBLC*KBL ).NE.( N-N1 ) )NBLC = NBLC + 1
00262 BLSKIP = ( KBL**2 ) + 1
00263
00264
00265 ROWSKIP = MIN0( 5, KBL )
00266
00267 SWBAND = 0
00268
00269
00270
00271
00272
00273
00274
00275
00276
00277
00278
00279
00280
00281 DO 1993 i = 1, NSWEEP
00282
00283
00284 MXAAPQ = ZERO
00285 MXSINJ = ZERO
00286 ISWROT = 0
00287
00288 NOTROT = 0
00289 PSKIPPED = 0
00290
00291 DO 2000 ibr = 1, NBLR
00292
00293 igl = ( ibr-1 )*KBL + 1
00294
00295
00296
00297
00298
00299 igl = ( ibr-1 )*KBL + 1
00300
00301 DO 2010 jbc = 1, NBLC
00302
00303 jgl = N1 + ( jbc-1 )*KBL + 1
00304
00305
00306
00307 IJBLSK = 0
00308 DO 2100 p = igl, MIN0( igl+KBL-1, N1 )
00309
00310 AAPP = SVA( p )
00311
00312 IF( AAPP.GT.ZERO ) THEN
00313
00314 PSKIPPED = 0
00315
00316 DO 2200 q = jgl, MIN0( jgl+KBL-1, N )
00317
00318 AAQQ = SVA( q )
00319
00320 IF( AAQQ.GT.ZERO ) THEN
00321 AAPP0 = AAPP
00322
00323
00324
00325
00326
00327 IF( AAQQ.GE.ONE ) THEN
00328 IF( AAPP.GE.AAQQ ) THEN
00329 ROTOK = ( SMALL*AAPP ).LE.AAQQ
00330 ELSE
00331 ROTOK = ( SMALL*AAQQ ).LE.AAPP
00332 END IF
00333 IF( AAPP.LT.( BIG / AAQQ ) ) THEN
00334 AAPQ = ( SDOT( M, A( 1, p ), 1, A( 1,
00335 + q ), 1 )*D( p )*D( q ) / AAQQ )
00336 + / AAPP
00337 ELSE
00338 CALL SCOPY( M, A( 1, p ), 1, WORK, 1 )
00339 CALL SLASCL( 'G', 0, 0, AAPP, D( p ),
00340 + M, 1, WORK, LDA, IERR )
00341 AAPQ = SDOT( M, WORK, 1, A( 1, q ),
00342 + 1 )*D( q ) / AAQQ
00343 END IF
00344 ELSE
00345 IF( AAPP.GE.AAQQ ) THEN
00346 ROTOK = AAPP.LE.( AAQQ / SMALL )
00347 ELSE
00348 ROTOK = AAQQ.LE.( AAPP / SMALL )
00349 END IF
00350 IF( AAPP.GT.( SMALL / AAQQ ) ) THEN
00351 AAPQ = ( SDOT( M, A( 1, p ), 1, A( 1,
00352 + q ), 1 )*D( p )*D( q ) / AAQQ )
00353 + / AAPP
00354 ELSE
00355 CALL SCOPY( M, A( 1, q ), 1, WORK, 1 )
00356 CALL SLASCL( 'G', 0, 0, AAQQ, D( q ),
00357 + M, 1, WORK, LDA, IERR )
00358 AAPQ = SDOT( M, WORK, 1, A( 1, p ),
00359 + 1 )*D( p ) / AAPP
00360 END IF
00361 END IF
00362
00363 MXAAPQ = AMAX1( MXAAPQ, ABS( AAPQ ) )
00364
00365
00366
00367 IF( ABS( AAPQ ).GT.TOL ) THEN
00368 NOTROT = 0
00369
00370 PSKIPPED = 0
00371 ISWROT = ISWROT + 1
00372
00373 IF( ROTOK ) THEN
00374
00375 AQOAP = AAQQ / AAPP
00376 APOAQ = AAPP / AAQQ
00377 THETA = -HALF*ABS( AQOAP-APOAQ ) / AAPQ
00378 IF( AAQQ.GT.AAPP0 )THETA = -THETA
00379
00380 IF( ABS( THETA ).GT.BIGTHETA ) THEN
00381 T = HALF / THETA
00382 FASTR( 3 ) = T*D( p ) / D( q )
00383 FASTR( 4 ) = -T*D( q ) / D( p )
00384 CALL SROTM( M, A( 1, p ), 1,
00385 + A( 1, q ), 1, FASTR )
00386 IF( RSVEC )CALL SROTM( MVL,
00387 + V( 1, p ), 1,
00388 + V( 1, q ), 1,
00389 + FASTR )
00390 SVA( q ) = AAQQ*SQRT( AMAX1( ZERO,
00391 + ONE+T*APOAQ*AAPQ ) )
00392 AAPP = AAPP*SQRT( AMAX1( ZERO,
00393 + ONE-T*AQOAP*AAPQ ) )
00394 MXSINJ = AMAX1( MXSINJ, ABS( T ) )
00395 ELSE
00396
00397
00398
00399 THSIGN = -SIGN( ONE, AAPQ )
00400 IF( AAQQ.GT.AAPP0 )THSIGN = -THSIGN
00401 T = ONE / ( THETA+THSIGN*
00402 + SQRT( ONE+THETA*THETA ) )
00403 CS = SQRT( ONE / ( ONE+T*T ) )
00404 SN = T*CS
00405 MXSINJ = AMAX1( MXSINJ, ABS( SN ) )
00406 SVA( q ) = AAQQ*SQRT( AMAX1( ZERO,
00407 + ONE+T*APOAQ*AAPQ ) )
00408 AAPP = AAPP*SQRT( ONE-T*AQOAP*AAPQ )
00409
00410 APOAQ = D( p ) / D( q )
00411 AQOAP = D( q ) / D( p )
00412 IF( D( p ).GE.ONE ) THEN
00413
00414 IF( D( q ).GE.ONE ) THEN
00415 FASTR( 3 ) = T*APOAQ
00416 FASTR( 4 ) = -T*AQOAP
00417 D( p ) = D( p )*CS
00418 D( q ) = D( q )*CS
00419 CALL SROTM( M, A( 1, p ), 1,
00420 + A( 1, q ), 1,
00421 + FASTR )
00422 IF( RSVEC )CALL SROTM( MVL,
00423 + V( 1, p ), 1, V( 1, q ),
00424 + 1, FASTR )
00425 ELSE
00426 CALL SAXPY( M, -T*AQOAP,
00427 + A( 1, q ), 1,
00428 + A( 1, p ), 1 )
00429 CALL SAXPY( M, CS*SN*APOAQ,
00430 + A( 1, p ), 1,
00431 + A( 1, q ), 1 )
00432 IF( RSVEC ) THEN
00433 CALL SAXPY( MVL, -T*AQOAP,
00434 + V( 1, q ), 1,
00435 + V( 1, p ), 1 )
00436 CALL SAXPY( MVL,
00437 + CS*SN*APOAQ,
00438 + V( 1, p ), 1,
00439 + V( 1, q ), 1 )
00440 END IF
00441 D( p ) = D( p )*CS
00442 D( q ) = D( q ) / CS
00443 END IF
00444 ELSE
00445 IF( D( q ).GE.ONE ) THEN
00446 CALL SAXPY( M, T*APOAQ,
00447 + A( 1, p ), 1,
00448 + A( 1, q ), 1 )
00449 CALL SAXPY( M, -CS*SN*AQOAP,
00450 + A( 1, q ), 1,
00451 + A( 1, p ), 1 )
00452 IF( RSVEC ) THEN
00453 CALL SAXPY( MVL, T*APOAQ,
00454 + V( 1, p ), 1,
00455 + V( 1, q ), 1 )
00456 CALL SAXPY( MVL,
00457 + -CS*SN*AQOAP,
00458 + V( 1, q ), 1,
00459 + V( 1, p ), 1 )
00460 END IF
00461 D( p ) = D( p ) / CS
00462 D( q ) = D( q )*CS
00463 ELSE
00464 IF( D( p ).GE.D( q ) ) THEN
00465 CALL SAXPY( M, -T*AQOAP,
00466 + A( 1, q ), 1,
00467 + A( 1, p ), 1 )
00468 CALL SAXPY( M, CS*SN*APOAQ,
00469 + A( 1, p ), 1,
00470 + A( 1, q ), 1 )
00471 D( p ) = D( p )*CS
00472 D( q ) = D( q ) / CS
00473 IF( RSVEC ) THEN
00474 CALL SAXPY( MVL,
00475 + -T*AQOAP,
00476 + V( 1, q ), 1,
00477 + V( 1, p ), 1 )
00478 CALL SAXPY( MVL,
00479 + CS*SN*APOAQ,
00480 + V( 1, p ), 1,
00481 + V( 1, q ), 1 )
00482 END IF
00483 ELSE
00484 CALL SAXPY( M, T*APOAQ,
00485 + A( 1, p ), 1,
00486 + A( 1, q ), 1 )
00487 CALL SAXPY( M,
00488 + -CS*SN*AQOAP,
00489 + A( 1, q ), 1,
00490 + A( 1, p ), 1 )
00491 D( p ) = D( p ) / CS
00492 D( q ) = D( q )*CS
00493 IF( RSVEC ) THEN
00494 CALL SAXPY( MVL,
00495 + T*APOAQ, V( 1, p ),
00496 + 1, V( 1, q ), 1 )
00497 CALL SAXPY( MVL,
00498 + -CS*SN*AQOAP,
00499 + V( 1, q ), 1,
00500 + V( 1, p ), 1 )
00501 END IF
00502 END IF
00503 END IF
00504 END IF
00505 END IF
00506
00507 ELSE
00508 IF( AAPP.GT.AAQQ ) THEN
00509 CALL SCOPY( M, A( 1, p ), 1, WORK,
00510 + 1 )
00511 CALL SLASCL( 'G', 0, 0, AAPP, ONE,
00512 + M, 1, WORK, LDA, IERR )
00513 CALL SLASCL( 'G', 0, 0, AAQQ, ONE,
00514 + M, 1, A( 1, q ), LDA,
00515 + IERR )
00516 TEMP1 = -AAPQ*D( p ) / D( q )
00517 CALL SAXPY( M, TEMP1, WORK, 1,
00518 + A( 1, q ), 1 )
00519 CALL SLASCL( 'G', 0, 0, ONE, AAQQ,
00520 + M, 1, A( 1, q ), LDA,
00521 + IERR )
00522 SVA( q ) = AAQQ*SQRT( AMAX1( ZERO,
00523 + ONE-AAPQ*AAPQ ) )
00524 MXSINJ = AMAX1( MXSINJ, SFMIN )
00525 ELSE
00526 CALL SCOPY( M, A( 1, q ), 1, WORK,
00527 + 1 )
00528 CALL SLASCL( 'G', 0, 0, AAQQ, ONE,
00529 + M, 1, WORK, LDA, IERR )
00530 CALL SLASCL( 'G', 0, 0, AAPP, ONE,
00531 + M, 1, A( 1, p ), LDA,
00532 + IERR )
00533 TEMP1 = -AAPQ*D( q ) / D( p )
00534 CALL SAXPY( M, TEMP1, WORK, 1,
00535 + A( 1, p ), 1 )
00536 CALL SLASCL( 'G', 0, 0, ONE, AAPP,
00537 + M, 1, A( 1, p ), LDA,
00538 + IERR )
00539 SVA( p ) = AAPP*SQRT( AMAX1( ZERO,
00540 + ONE-AAPQ*AAPQ ) )
00541 MXSINJ = AMAX1( MXSINJ, SFMIN )
00542 END IF
00543 END IF
00544
00545
00546
00547
00548 IF( ( SVA( q ) / AAQQ )**2.LE.ROOTEPS )
00549 + THEN
00550 IF( ( AAQQ.LT.ROOTBIG ) .AND.
00551 + ( AAQQ.GT.ROOTSFMIN ) ) THEN
00552 SVA( q ) = SNRM2( M, A( 1, q ), 1 )*
00553 + D( q )
00554 ELSE
00555 T = ZERO
00556 AAQQ = ZERO
00557 CALL SLASSQ( M, A( 1, q ), 1, T,
00558 + AAQQ )
00559 SVA( q ) = T*SQRT( AAQQ )*D( q )
00560 END IF
00561 END IF
00562 IF( ( AAPP / AAPP0 )**2.LE.ROOTEPS ) THEN
00563 IF( ( AAPP.LT.ROOTBIG ) .AND.
00564 + ( AAPP.GT.ROOTSFMIN ) ) THEN
00565 AAPP = SNRM2( M, A( 1, p ), 1 )*
00566 + D( p )
00567 ELSE
00568 T = ZERO
00569 AAPP = ZERO
00570 CALL SLASSQ( M, A( 1, p ), 1, T,
00571 + AAPP )
00572 AAPP = T*SQRT( AAPP )*D( p )
00573 END IF
00574 SVA( p ) = AAPP
00575 END IF
00576
00577 ELSE
00578 NOTROT = NOTROT + 1
00579
00580 PSKIPPED = PSKIPPED + 1
00581 IJBLSK = IJBLSK + 1
00582 END IF
00583 ELSE
00584 NOTROT = NOTROT + 1
00585 PSKIPPED = PSKIPPED + 1
00586 IJBLSK = IJBLSK + 1
00587 END IF
00588
00589
00590 IF( ( i.LE.SWBAND ) .AND. ( IJBLSK.GE.BLSKIP ) )
00591 + THEN
00592 SVA( p ) = AAPP
00593 NOTROT = 0
00594 GO TO 2011
00595 END IF
00596 IF( ( i.LE.SWBAND ) .AND.
00597 + ( PSKIPPED.GT.ROWSKIP ) ) THEN
00598 AAPP = -AAPP
00599 NOTROT = 0
00600 GO TO 2203
00601 END IF
00602
00603
00604 2200 CONTINUE
00605
00606 2203 CONTINUE
00607
00608 SVA( p ) = AAPP
00609
00610 ELSE
00611 IF( AAPP.EQ.ZERO )NOTROT = NOTROT +
00612 + MIN0( jgl+KBL-1, N ) - jgl + 1
00613 IF( AAPP.LT.ZERO )NOTROT = 0
00614
00615 END IF
00616
00617 2100 CONTINUE
00618
00619 2010 CONTINUE
00620
00621 2011 CONTINUE
00622
00623 DO 2012 p = igl, MIN0( igl+KBL-1, N )
00624 SVA( p ) = ABS( SVA( p ) )
00625 2012 CONTINUE
00626
00627 2000 CONTINUE
00628
00629
00630
00631 IF( ( SVA( N ).LT.ROOTBIG ) .AND. ( SVA( N ).GT.ROOTSFMIN ) )
00632 + THEN
00633 SVA( N ) = SNRM2( M, A( 1, N ), 1 )*D( N )
00634 ELSE
00635 T = ZERO
00636 AAPP = ZERO
00637 CALL SLASSQ( M, A( 1, N ), 1, T, AAPP )
00638 SVA( N ) = T*SQRT( AAPP )*D( N )
00639 END IF
00640
00641
00642
00643 IF( ( i.LT.SWBAND ) .AND. ( ( MXAAPQ.LE.ROOTTOL ) .OR.
00644 + ( ISWROT.LE.N ) ) )SWBAND = i
00645
00646 IF( ( i.GT.SWBAND+1 ) .AND. ( MXAAPQ.LT.FLOAT( N )*TOL ) .AND.
00647 + ( FLOAT( N )*MXAAPQ*MXSINJ.LT.TOL ) ) THEN
00648 GO TO 1994
00649 END IF
00650
00651
00652 IF( NOTROT.GE.EMPTSW )GO TO 1994
00653
00654 1993 CONTINUE
00655
00656
00657
00658 INFO = NSWEEP - 1
00659 GO TO 1995
00660 1994 CONTINUE
00661
00662
00663
00664 INFO = 0
00665
00666 1995 CONTINUE
00667
00668
00669
00670 DO 5991 p = 1, N - 1
00671 q = ISAMAX( N-p+1, SVA( p ), 1 ) + p - 1
00672 IF( p.NE.q ) THEN
00673 TEMP1 = SVA( p )
00674 SVA( p ) = SVA( q )
00675 SVA( q ) = TEMP1
00676 TEMP1 = D( p )
00677 D( p ) = D( q )
00678 D( q ) = TEMP1
00679 CALL SSWAP( M, A( 1, p ), 1, A( 1, q ), 1 )
00680 IF( RSVEC )CALL SSWAP( MVL, V( 1, p ), 1, V( 1, q ), 1 )
00681 END IF
00682 5991 CONTINUE
00683
00684 RETURN
00685
00686
00687
00688 END