Statistiques
| Révision :

root / src / lapack / double / dlasv2.f @ 1

Historique | Voir | Annoter | Télécharger (6,6 ko)

1 1 equemene
      SUBROUTINE DLASV2( F, G, H, SSMIN, SSMAX, SNR, CSR, SNL, CSL )
2 1 equemene
*
3 1 equemene
*  -- LAPACK auxiliary routine (version 3.2) --
4 1 equemene
*  -- LAPACK is a software package provided by Univ. of Tennessee,    --
5 1 equemene
*  -- Univ. of California Berkeley, Univ. of Colorado Denver and NAG Ltd..--
6 1 equemene
*     November 2006
7 1 equemene
*
8 1 equemene
*     .. Scalar Arguments ..
9 1 equemene
      DOUBLE PRECISION   CSL, CSR, F, G, H, SNL, SNR, SSMAX, SSMIN
10 1 equemene
*     ..
11 1 equemene
*
12 1 equemene
*  Purpose
13 1 equemene
*  =======
14 1 equemene
*
15 1 equemene
*  DLASV2 computes the singular value decomposition of a 2-by-2
16 1 equemene
*  triangular matrix
17 1 equemene
*     [  F   G  ]
18 1 equemene
*     [  0   H  ].
19 1 equemene
*  On return, abs(SSMAX) is the larger singular value, abs(SSMIN) is the
20 1 equemene
*  smaller singular value, and (CSL,SNL) and (CSR,SNR) are the left and
21 1 equemene
*  right singular vectors for abs(SSMAX), giving the decomposition
22 1 equemene
*
23 1 equemene
*     [ CSL  SNL ] [  F   G  ] [ CSR -SNR ]  =  [ SSMAX   0   ]
24 1 equemene
*     [-SNL  CSL ] [  0   H  ] [ SNR  CSR ]     [  0    SSMIN ].
25 1 equemene
*
26 1 equemene
*  Arguments
27 1 equemene
*  =========
28 1 equemene
*
29 1 equemene
*  F       (input) DOUBLE PRECISION
30 1 equemene
*          The (1,1) element of the 2-by-2 matrix.
31 1 equemene
*
32 1 equemene
*  G       (input) DOUBLE PRECISION
33 1 equemene
*          The (1,2) element of the 2-by-2 matrix.
34 1 equemene
*
35 1 equemene
*  H       (input) DOUBLE PRECISION
36 1 equemene
*          The (2,2) element of the 2-by-2 matrix.
37 1 equemene
*
38 1 equemene
*  SSMIN   (output) DOUBLE PRECISION
39 1 equemene
*          abs(SSMIN) is the smaller singular value.
40 1 equemene
*
41 1 equemene
*  SSMAX   (output) DOUBLE PRECISION
42 1 equemene
*          abs(SSMAX) is the larger singular value.
43 1 equemene
*
44 1 equemene
*  SNL     (output) DOUBLE PRECISION
45 1 equemene
*  CSL     (output) DOUBLE PRECISION
46 1 equemene
*          The vector (CSL, SNL) is a unit left singular vector for the
47 1 equemene
*          singular value abs(SSMAX).
48 1 equemene
*
49 1 equemene
*  SNR     (output) DOUBLE PRECISION
50 1 equemene
*  CSR     (output) DOUBLE PRECISION
51 1 equemene
*          The vector (CSR, SNR) is a unit right singular vector for the
52 1 equemene
*          singular value abs(SSMAX).
53 1 equemene
*
54 1 equemene
*  Further Details
55 1 equemene
*  ===============
56 1 equemene
*
57 1 equemene
*  Any input parameter may be aliased with any output parameter.
58 1 equemene
*
59 1 equemene
*  Barring over/underflow and assuming a guard digit in subtraction, all
60 1 equemene
*  output quantities are correct to within a few units in the last
61 1 equemene
*  place (ulps).
62 1 equemene
*
63 1 equemene
*  In IEEE arithmetic, the code works correctly if one matrix element is
64 1 equemene
*  infinite.
65 1 equemene
*
66 1 equemene
*  Overflow will not occur unless the largest singular value itself
67 1 equemene
*  overflows or is within a few ulps of overflow. (On machines with
68 1 equemene
*  partial overflow, like the Cray, overflow may occur if the largest
69 1 equemene
*  singular value is within a factor of 2 of overflow.)
70 1 equemene
*
71 1 equemene
*  Underflow is harmless if underflow is gradual. Otherwise, results
72 1 equemene
*  may correspond to a matrix modified by perturbations of size near
73 1 equemene
*  the underflow threshold.
74 1 equemene
*
75 1 equemene
* =====================================================================
76 1 equemene
*
77 1 equemene
*     .. Parameters ..
78 1 equemene
      DOUBLE PRECISION   ZERO
79 1 equemene
      PARAMETER          ( ZERO = 0.0D0 )
80 1 equemene
      DOUBLE PRECISION   HALF
81 1 equemene
      PARAMETER          ( HALF = 0.5D0 )
82 1 equemene
      DOUBLE PRECISION   ONE
83 1 equemene
      PARAMETER          ( ONE = 1.0D0 )
84 1 equemene
      DOUBLE PRECISION   TWO
85 1 equemene
      PARAMETER          ( TWO = 2.0D0 )
86 1 equemene
      DOUBLE PRECISION   FOUR
87 1 equemene
      PARAMETER          ( FOUR = 4.0D0 )
88 1 equemene
*     ..
89 1 equemene
*     .. Local Scalars ..
90 1 equemene
      LOGICAL            GASMAL, SWAP
91 1 equemene
      INTEGER            PMAX
92 1 equemene
      DOUBLE PRECISION   A, CLT, CRT, D, FA, FT, GA, GT, HA, HT, L, M,
93 1 equemene
     $                   MM, R, S, SLT, SRT, T, TEMP, TSIGN, TT
94 1 equemene
*     ..
95 1 equemene
*     .. Intrinsic Functions ..
96 1 equemene
      INTRINSIC          ABS, SIGN, SQRT
97 1 equemene
*     ..
98 1 equemene
*     .. External Functions ..
99 1 equemene
      DOUBLE PRECISION   DLAMCH
100 1 equemene
      EXTERNAL           DLAMCH
101 1 equemene
*     ..
102 1 equemene
*     .. Executable Statements ..
103 1 equemene
*
104 1 equemene
      FT = F
105 1 equemene
      FA = ABS( FT )
106 1 equemene
      HT = H
107 1 equemene
      HA = ABS( H )
108 1 equemene
*
109 1 equemene
*     PMAX points to the maximum absolute element of matrix
110 1 equemene
*       PMAX = 1 if F largest in absolute values
111 1 equemene
*       PMAX = 2 if G largest in absolute values
112 1 equemene
*       PMAX = 3 if H largest in absolute values
113 1 equemene
*
114 1 equemene
      PMAX = 1
115 1 equemene
      SWAP = ( HA.GT.FA )
116 1 equemene
      IF( SWAP ) THEN
117 1 equemene
         PMAX = 3
118 1 equemene
         TEMP = FT
119 1 equemene
         FT = HT
120 1 equemene
         HT = TEMP
121 1 equemene
         TEMP = FA
122 1 equemene
         FA = HA
123 1 equemene
         HA = TEMP
124 1 equemene
*
125 1 equemene
*        Now FA .ge. HA
126 1 equemene
*
127 1 equemene
      END IF
128 1 equemene
      GT = G
129 1 equemene
      GA = ABS( GT )
130 1 equemene
      IF( GA.EQ.ZERO ) THEN
131 1 equemene
*
132 1 equemene
*        Diagonal matrix
133 1 equemene
*
134 1 equemene
         SSMIN = HA
135 1 equemene
         SSMAX = FA
136 1 equemene
         CLT = ONE
137 1 equemene
         CRT = ONE
138 1 equemene
         SLT = ZERO
139 1 equemene
         SRT = ZERO
140 1 equemene
      ELSE
141 1 equemene
         GASMAL = .TRUE.
142 1 equemene
         IF( GA.GT.FA ) THEN
143 1 equemene
            PMAX = 2
144 1 equemene
            IF( ( FA / GA ).LT.DLAMCH( 'EPS' ) ) THEN
145 1 equemene
*
146 1 equemene
*              Case of very large GA
147 1 equemene
*
148 1 equemene
               GASMAL = .FALSE.
149 1 equemene
               SSMAX = GA
150 1 equemene
               IF( HA.GT.ONE ) THEN
151 1 equemene
                  SSMIN = FA / ( GA / HA )
152 1 equemene
               ELSE
153 1 equemene
                  SSMIN = ( FA / GA )*HA
154 1 equemene
               END IF
155 1 equemene
               CLT = ONE
156 1 equemene
               SLT = HT / GT
157 1 equemene
               SRT = ONE
158 1 equemene
               CRT = FT / GT
159 1 equemene
            END IF
160 1 equemene
         END IF
161 1 equemene
         IF( GASMAL ) THEN
162 1 equemene
*
163 1 equemene
*           Normal case
164 1 equemene
*
165 1 equemene
            D = FA - HA
166 1 equemene
            IF( D.EQ.FA ) THEN
167 1 equemene
*
168 1 equemene
*              Copes with infinite F or H
169 1 equemene
*
170 1 equemene
               L = ONE
171 1 equemene
            ELSE
172 1 equemene
               L = D / FA
173 1 equemene
            END IF
174 1 equemene
*
175 1 equemene
*           Note that 0 .le. L .le. 1
176 1 equemene
*
177 1 equemene
            M = GT / FT
178 1 equemene
*
179 1 equemene
*           Note that abs(M) .le. 1/macheps
180 1 equemene
*
181 1 equemene
            T = TWO - L
182 1 equemene
*
183 1 equemene
*           Note that T .ge. 1
184 1 equemene
*
185 1 equemene
            MM = M*M
186 1 equemene
            TT = T*T
187 1 equemene
            S = SQRT( TT+MM )
188 1 equemene
*
189 1 equemene
*           Note that 1 .le. S .le. 1 + 1/macheps
190 1 equemene
*
191 1 equemene
            IF( L.EQ.ZERO ) THEN
192 1 equemene
               R = ABS( M )
193 1 equemene
            ELSE
194 1 equemene
               R = SQRT( L*L+MM )
195 1 equemene
            END IF
196 1 equemene
*
197 1 equemene
*           Note that 0 .le. R .le. 1 + 1/macheps
198 1 equemene
*
199 1 equemene
            A = HALF*( S+R )
200 1 equemene
*
201 1 equemene
*           Note that 1 .le. A .le. 1 + abs(M)
202 1 equemene
*
203 1 equemene
            SSMIN = HA / A
204 1 equemene
            SSMAX = FA*A
205 1 equemene
            IF( MM.EQ.ZERO ) THEN
206 1 equemene
*
207 1 equemene
*              Note that M is very tiny
208 1 equemene
*
209 1 equemene
               IF( L.EQ.ZERO ) THEN
210 1 equemene
                  T = SIGN( TWO, FT )*SIGN( ONE, GT )
211 1 equemene
               ELSE
212 1 equemene
                  T = GT / SIGN( D, FT ) + M / T
213 1 equemene
               END IF
214 1 equemene
            ELSE
215 1 equemene
               T = ( M / ( S+T )+M / ( R+L ) )*( ONE+A )
216 1 equemene
            END IF
217 1 equemene
            L = SQRT( T*T+FOUR )
218 1 equemene
            CRT = TWO / L
219 1 equemene
            SRT = T / L
220 1 equemene
            CLT = ( CRT+SRT*M ) / A
221 1 equemene
            SLT = ( HT / FT )*SRT / A
222 1 equemene
         END IF
223 1 equemene
      END IF
224 1 equemene
      IF( SWAP ) THEN
225 1 equemene
         CSL = SRT
226 1 equemene
         SNL = CRT
227 1 equemene
         CSR = SLT
228 1 equemene
         SNR = CLT
229 1 equemene
      ELSE
230 1 equemene
         CSL = CLT
231 1 equemene
         SNL = SLT
232 1 equemene
         CSR = CRT
233 1 equemene
         SNR = SRT
234 1 equemene
      END IF
235 1 equemene
*
236 1 equemene
*     Correct signs of SSMAX and SSMIN
237 1 equemene
*
238 1 equemene
      IF( PMAX.EQ.1 )
239 1 equemene
     $   TSIGN = SIGN( ONE, CSR )*SIGN( ONE, CSL )*SIGN( ONE, F )
240 1 equemene
      IF( PMAX.EQ.2 )
241 1 equemene
     $   TSIGN = SIGN( ONE, SNR )*SIGN( ONE, CSL )*SIGN( ONE, G )
242 1 equemene
      IF( PMAX.EQ.3 )
243 1 equemene
     $   TSIGN = SIGN( ONE, SNR )*SIGN( ONE, SNL )*SIGN( ONE, H )
244 1 equemene
      SSMAX = SIGN( SSMAX, TSIGN )
245 1 equemene
      SSMIN = SIGN( SSMIN, TSIGN*SIGN( ONE, F )*SIGN( ONE, H ) )
246 1 equemene
      RETURN
247 1 equemene
*
248 1 equemene
*     End of DLASV2
249 1 equemene
*
250 1 equemene
      END