OpenRadioss 2025.1.11
OpenRadioss project
Loading...
Searching...
No Matches
zsytrs_3.f
Go to the documentation of this file.
1*> \brief \b ZSYTRS_3
2*
3* =========== DOCUMENTATION ===========
4*
5* Online html documentation available at
6* http://www.netlib.org/lapack/explore-html/
7*
8*> \htmlonly
9*> Download ZSYTRS_3 + dependencies
10*> <a href="http://www.netlib.org/cgi-bin/netlibfiles.tgz?format=tgz&filename=/lapack/lapack_routine/zsytrs_3.f">
11*> [TGZ]</a>
12*> <a href="http://www.netlib.org/cgi-bin/netlibfiles.zip?format=zip&filename=/lapack/lapack_routine/zsytrs_3.f">
13*> [ZIP]</a>
14*> <a href="http://www.netlib.org/cgi-bin/netlibfiles.txt?format=txt&filename=/lapack/lapack_routine/zsytrs_3.f">
15*> [TXT]</a>
16*> \endhtmlonly
17*
18* Definition:
19* ===========
20*
21* SUBROUTINE ZSYTRS_3( UPLO, N, NRHS, A, LDA, E, IPIV, B, LDB,
22* INFO )
23*
24* .. Scalar Arguments ..
25* CHARACTER UPLO
26* INTEGER INFO, LDA, LDB, N, NRHS
27* ..
28* .. Array Arguments ..
29* INTEGER IPIV( * )
30* COMPLEX*16 A( LDA, * ), B( LDB, * ), E( * )
31* ..
32*
33*
34*> \par Purpose:
35* =============
36*>
37*> \verbatim
38*> ZSYTRS_3 solves a system of linear equations A * X = B with a complex
39*> symmetric matrix A using the factorization computed
40*> by ZSYTRF_RK or ZSYTRF_BK:
41*>
42*> A = P*U*D*(U**T)*(P**T) or A = P*L*D*(L**T)*(P**T),
43*>
44*> where U (or L) is unit upper (or lower) triangular matrix,
45*> U**T (or L**T) is the transpose of U (or L), P is a permutation
46*> matrix, P**T is the transpose of P, and D is symmetric and block
47*> diagonal with 1-by-1 and 2-by-2 diagonal blocks.
48*>
49*> This algorithm is using Level 3 BLAS.
50*> \endverbatim
51*
52* Arguments:
53* ==========
54*
55*> \param[in] UPLO
56*> \verbatim
57*> UPLO is CHARACTER*1
58*> Specifies whether the details of the factorization are
59*> stored as an upper or lower triangular matrix:
60*> = 'U': Upper triangular, form is A = P*U*D*(U**T)*(P**T);
61*> = 'L': Lower triangular, form is A = P*L*D*(L**T)*(P**T).
62*> \endverbatim
63*>
64*> \param[in] N
65*> \verbatim
66*> N is INTEGER
67*> The order of the matrix A. N >= 0.
68*> \endverbatim
69*>
70*> \param[in] NRHS
71*> \verbatim
72*> NRHS is INTEGER
73*> The number of right hand sides, i.e., the number of columns
74*> of the matrix B. NRHS >= 0.
75*> \endverbatim
76*>
77*> \param[in] A
78*> \verbatim
79*> A is COMPLEX*16 array, dimension (LDA,N)
80*> Diagonal of the block diagonal matrix D and factors U or L
81*> as computed by ZSYTRF_RK and ZSYTRF_BK:
82*> a) ONLY diagonal elements of the symmetric block diagonal
83*> matrix D on the diagonal of A, i.e. D(k,k) = A(k,k);
84*> (superdiagonal (or subdiagonal) elements of D
85*> should be provided on entry in array E), and
86*> b) If UPLO = 'U': factor U in the superdiagonal part of A.
87*> If UPLO = 'L': factor L in the subdiagonal part of A.
88*> \endverbatim
89*>
90*> \param[in] LDA
91*> \verbatim
92*> LDA is INTEGER
93*> The leading dimension of the array A. LDA >= max(1,N).
94*> \endverbatim
95*>
96*> \param[in] E
97*> \verbatim
98*> E is COMPLEX*16 array, dimension (N)
99*> On entry, contains the superdiagonal (or subdiagonal)
100*> elements of the symmetric block diagonal matrix D
101*> with 1-by-1 or 2-by-2 diagonal blocks, where
102*> If UPLO = 'U': E(i) = D(i-1,i),i=2:N, E(1) not referenced;
103*> If UPLO = 'L': E(i) = D(i+1,i),i=1:N-1, E(N) not referenced.
104*>
105*> NOTE: For 1-by-1 diagonal block D(k), where
106*> 1 <= k <= N, the element E(k) is not referenced in both
107*> UPLO = 'U' or UPLO = 'L' cases.
108*> \endverbatim
109*>
110*> \param[in] IPIV
111*> \verbatim
112*> IPIV is INTEGER array, dimension (N)
113*> Details of the interchanges and the block structure of D
114*> as determined by ZSYTRF_RK or ZSYTRF_BK.
115*> \endverbatim
116*>
117*> \param[in,out] B
118*> \verbatim
119*> B is COMPLEX*16 array, dimension (LDB,NRHS)
120*> On entry, the right hand side matrix B.
121*> On exit, the solution matrix X.
122*> \endverbatim
123*>
124*> \param[in] LDB
125*> \verbatim
126*> LDB is INTEGER
127*> The leading dimension of the array B. LDB >= max(1,N).
128*> \endverbatim
129*>
130*> \param[out] INFO
131*> \verbatim
132*> INFO is INTEGER
133*> = 0: successful exit
134*> < 0: if INFO = -i, the i-th argument had an illegal value
135*> \endverbatim
136*
137* Authors:
138* ========
139*
140*> \author Univ. of Tennessee
141*> \author Univ. of California Berkeley
142*> \author Univ. of Colorado Denver
143*> \author NAG Ltd.
144*
145*> \ingroup complex16SYcomputational
146*
147*> \par Contributors:
148* ==================
149*>
150*> \verbatim
151*>
152*> June 2017, Igor Kozachenko,
153*> Computer Science Division,
154*> University of California, Berkeley
155*>
156*> September 2007, Sven Hammarling, Nicholas J. Higham, Craig Lucas,
157*> School of Mathematics,
158*> University of Manchester
159*>
160*> \endverbatim
161*
162* =====================================================================
163 SUBROUTINE zsytrs_3( UPLO, N, NRHS, A, LDA, E, IPIV, B, LDB,
164 $ INFO )
165*
166* -- LAPACK computational routine --
167* -- LAPACK is a software package provided by Univ. of Tennessee, --
168* -- Univ. of California Berkeley, Univ. of Colorado Denver and NAG Ltd..--
169*
170* .. Scalar Arguments ..
171 CHARACTER UPLO
172 INTEGER INFO, LDA, LDB, N, NRHS
173* ..
174* .. Array Arguments ..
175 INTEGER IPIV( * )
176 COMPLEX*16 A( LDA, * ), B( LDB, * ), E( * )
177* ..
178*
179* =====================================================================
180*
181* .. Parameters ..
182 COMPLEX*16 ONE
183 parameter( one = ( 1.0d+0,0.0d+0 ) )
184* ..
185* .. Local Scalars ..
186 LOGICAL UPPER
187 INTEGER I, J, K, KP
188 COMPLEX*16 AK, AKM1, AKM1K, BK, BKM1, DENOM
189* ..
190* .. External Functions ..
191 LOGICAL LSAME
192 EXTERNAL lsame
193* ..
194* .. External Subroutines ..
195 EXTERNAL zscal, zswap, ztrsm, xerbla
196* ..
197* .. Intrinsic Functions ..
198 INTRINSIC abs, max
199* ..
200* .. Executable Statements ..
201*
202 info = 0
203 upper = lsame( uplo, 'U' )
204 IF( .NOT.upper .AND. .NOT.lsame( uplo, 'L' ) ) THEN
205 info = -1
206 ELSE IF( n.LT.0 ) THEN
207 info = -2
208 ELSE IF( nrhs.LT.0 ) THEN
209 info = -3
210 ELSE IF( lda.LT.max( 1, n ) ) THEN
211 info = -5
212 ELSE IF( ldb.LT.max( 1, n ) ) THEN
213 info = -9
214 END IF
215 IF( info.NE.0 ) THEN
216 CALL xerbla( 'ZSYTRS_3', -info )
217 RETURN
218 END IF
219*
220* Quick return if possible
221*
222 IF( n.EQ.0 .OR. nrhs.EQ.0 )
223 $ RETURN
224*
225 IF( upper ) THEN
226*
227* Begin Upper
228*
229* Solve A*X = B, where A = U*D*U**T.
230*
231* P**T * B
232*
233* Interchange rows K and IPIV(K) of matrix B in the same order
234* that the formation order of IPIV(I) vector for Upper case.
235*
236* (We can do the simple loop over IPIV with decrement -1,
237* since the ABS value of IPIV(I) represents the row index
238* of the interchange with row i in both 1x1 and 2x2 pivot cases)
239*
240 DO k = n, 1, -1
241 kp = abs( ipiv( k ) )
242 IF( kp.NE.k ) THEN
243 CALL zswap( nrhs, b( k, 1 ), ldb, b( kp, 1 ), ldb )
244 END IF
245 END DO
246*
247* Compute (U \P**T * B) -> B [ (U \P**T * B) ]
248*
249 CALL ztrsm( 'L', 'u', 'n', 'u', N, NRHS, ONE, A, LDA, B, LDB )
250*
251* Compute D \ B -> B [ D \ (U \P**T * B) ]
252*
253 I = N
254.GE. DO WHILE ( I1 )
255.GT. IF( IPIV( I )0 ) THEN
256 CALL ZSCAL( NRHS, ONE / A( I, I ), B( I, 1 ), LDB )
257.GT. ELSE IF ( I1 ) THEN
258 AKM1K = E( I )
259 AKM1 = A( I-1, I-1 ) / AKM1K
260 AK = A( I, I ) / AKM1K
261 DENOM = AKM1*AK - ONE
262 DO J = 1, NRHS
263 BKM1 = B( I-1, J ) / AKM1K
264 BK = B( I, J ) / AKM1K
265 B( I-1, J ) = ( AK*BKM1-BK ) / DENOM
266 B( I, J ) = ( AKM1*BK-BKM1 ) / DENOM
267 END DO
268 I = I - 1
269 END IF
270 I = I - 1
271 END DO
272*
273* Compute (U**T \ B) -> B [ U**T \ (D \ (U \P**T * B) ) ]
274*
275 CALL ZTRSM( 'l', 'u', 't', 'u', N, NRHS, ONE, A, LDA, B, LDB )
276*
277* P * B [ P * (U**T \ (D \ (U \P**T * B) )) ]
278*
279* Interchange rows K and IPIV(K) of matrix B in reverse order
280* from the formation order of IPIV(I) vector for Upper case.
281*
282* (We can do the simple loop over IPIV with increment 1,
283* since the ABS value of IPIV(I) represents the row index
284* of the interchange with row i in both 1x1 and 2x2 pivot cases)
285*
286 DO K = 1, N, 1
287 KP = ABS( IPIV( K ) )
288.NE. IF( KPK ) THEN
289 CALL ZSWAP( NRHS, B( K, 1 ), LDB, B( KP, 1 ), LDB )
290 END IF
291 END DO
292*
293 ELSE
294*
295* Begin Lower
296*
297* Solve A*X = B, where A = L*D*L**T.
298*
299* P**T * B
300* Interchange rows K and IPIV(K) of matrix B in the same order
301* that the formation order of IPIV(I) vector for Lower case.
302*
303* (We can do the simple loop over IPIV with increment 1,
304* since the ABS value of IPIV(I) represents the row index
305* of the interchange with row i in both 1x1 and 2x2 pivot cases)
306*
307 DO K = 1, N, 1
308 KP = ABS( IPIV( K ) )
309.NE. IF( KPK ) THEN
310 CALL ZSWAP( NRHS, B( K, 1 ), LDB, B( KP, 1 ), LDB )
311 END IF
312 END DO
313*
314* Compute (L \P**T * B) -> B [ (L \P**T * B) ]
315*
316 CALL ZTRSM( 'l', 'l', 'n', 'u', N, NRHS, ONE, A, LDA, B, LDB )
317*
318* Compute D \ B -> B [ D \ (L \P**T * B) ]
319*
320 I = 1
321.LE. DO WHILE ( IN )
322.GT. IF( IPIV( I )0 ) THEN
323 CALL ZSCAL( NRHS, ONE / A( I, I ), B( I, 1 ), LDB )
324.LT. ELSE IF( IN ) THEN
325 AKM1K = E( I )
326 AKM1 = A( I, I ) / AKM1K
327 AK = A( I+1, I+1 ) / AKM1K
328 DENOM = AKM1*AK - ONE
329 DO J = 1, NRHS
330 BKM1 = B( I, J ) / AKM1K
331 BK = B( I+1, J ) / AKM1K
332 B( I, J ) = ( AK*BKM1-BK ) / DENOM
333 B( I+1, J ) = ( AKM1*BK-BKM1 ) / DENOM
334 END DO
335 I = I + 1
336 END IF
337 I = I + 1
338 END DO
339*
340* Compute (L**T \ B) -> B [ L**T \ (D \ (L \P**T * B) ) ]
341*
342 CALL ZTRSM('l', 'l', 't', 'u', N, NRHS, ONE, A, LDA, B, LDB )
343*
344* P * B [ P * (L**T \ (D \ (L \P**T * B) )) ]
345*
346* Interchange rows K and IPIV(K) of matrix B in reverse order
347* from the formation order of IPIV(I) vector for Lower case.
348*
349* (We can do the simple loop over IPIV with decrement -1,
350* since the ABS value of IPIV(I) represents the row index
351* of the interchange with row i in both 1x1 and 2x2 pivot cases)
352*
353 DO K = N, 1, -1
354 KP = ABS( IPIV( K ) )
355.NE. IF( KPK ) THEN
356 CALL ZSWAP( NRHS, B( K, 1 ), LDB, B( KP, 1 ), LDB )
357 END IF
358 END DO
359*
360* END Lower
361*
362 END IF
363*
364 RETURN
365*
366* End of ZSYTRS_3
367*
368 END
subroutine xerbla(srname, info)
XERBLA
Definition xerbla.f:60
subroutine zsytrs_3(uplo, n, nrhs, a, lda, e, ipiv, b, ldb, info)
ZSYTRS_3
Definition zsytrs_3.f:165
subroutine zswap(n, zx, incx, zy, incy)
ZSWAP
Definition zswap.f:81
subroutine zscal(n, za, zx, incx)
ZSCAL
Definition zscal.f:78
subroutine ztrsm(side, uplo, transa, diag, m, n, alpha, a, lda, b, ldb)
ZTRSM
Definition ztrsm.f:180
#define max(a, b)
Definition macros.h:21