LAPACK 3.12.1
LAPACK: Linear Algebra PACKage
Loading...
Searching...
No Matches
zcposv.f
Go to the documentation of this file.
1*> \brief <b> ZCPOSV computes the solution to system of linear equations A * X = B for PO matrices</b>
2*
3* =========== DOCUMENTATION ===========
4*
5* Online html documentation available at
6* http://www.netlib.org/lapack/explore-html/
7*
8*> Download ZCPOSV + dependencies
9*> <a href="http://www.netlib.org/cgi-bin/netlibfiles.tgz?format=tgz&filename=/lapack/lapack_routine/zcposv.f">
10*> [TGZ]</a>
11*> <a href="http://www.netlib.org/cgi-bin/netlibfiles.zip?format=zip&filename=/lapack/lapack_routine/zcposv.f">
12*> [ZIP]</a>
13*> <a href="http://www.netlib.org/cgi-bin/netlibfiles.txt?format=txt&filename=/lapack/lapack_routine/zcposv.f">
14*> [TXT]</a>
15*
16* Definition:
17* ===========
18*
19* SUBROUTINE ZCPOSV( UPLO, N, NRHS, A, LDA, B, LDB, X, LDX, WORK,
20* SWORK, RWORK, ITER, INFO )
21*
22* .. Scalar Arguments ..
23* CHARACTER UPLO
24* INTEGER INFO, ITER, LDA, LDB, LDX, N, NRHS
25* ..
26* .. Array Arguments ..
27* DOUBLE PRECISION RWORK( * )
28* COMPLEX SWORK( * )
29* COMPLEX*16 A( LDA, * ), B( LDB, * ), WORK( N, * ),
30* $ X( LDX, * )
31* ..
32*
33*
34*> \par Purpose:
35* =============
36*>
37*> \verbatim
38*>
39*> ZCPOSV computes the solution to a complex system of linear equations
40*> A * X = B,
41*> where A is an N-by-N Hermitian positive definite matrix and X and B
42*> are N-by-NRHS matrices.
43*>
44*> ZCPOSV first attempts to factorize the matrix in COMPLEX and use this
45*> factorization within an iterative refinement procedure to produce a
46*> solution with COMPLEX*16 normwise backward error quality (see below).
47*> If the approach fails the method switches to a COMPLEX*16
48*> factorization and solve.
49*>
50*> The iterative refinement is not going to be a winning strategy if
51*> the ratio COMPLEX performance over COMPLEX*16 performance is too
52*> small. A reasonable strategy should take the number of right-hand
53*> sides and the size of the matrix into account. This might be done
54*> with a call to ILAENV in the future. Up to now, we always try
55*> iterative refinement.
56*>
57*> The iterative refinement process is stopped if
58*> ITER > ITERMAX
59*> or for all the RHS we have:
60*> RNRM < SQRT(N)*XNRM*ANRM*EPS*BWDMAX
61*> where
62*> o ITER is the number of the current iteration in the iterative
63*> refinement process
64*> o RNRM is the infinity-norm of the residual
65*> o XNRM is the infinity-norm of the solution
66*> o ANRM is the infinity-operator-norm of the matrix A
67*> o EPS is the machine epsilon returned by DLAMCH('Epsilon')
68*> The value ITERMAX and BWDMAX are fixed to 30 and 1.0D+00
69*> respectively.
70*> \endverbatim
71*
72* Arguments:
73* ==========
74*
75*> \param[in] UPLO
76*> \verbatim
77*> UPLO is CHARACTER*1
78*> = 'U': Upper triangle of A is stored;
79*> = 'L': Lower triangle of A is stored.
80*> \endverbatim
81*>
82*> \param[in] N
83*> \verbatim
84*> N is INTEGER
85*> The number of linear equations, i.e., the order of the
86*> matrix A. N >= 0.
87*> \endverbatim
88*>
89*> \param[in] NRHS
90*> \verbatim
91*> NRHS is INTEGER
92*> The number of right hand sides, i.e., the number of columns
93*> of the matrix B. NRHS >= 0.
94*> \endverbatim
95*>
96*> \param[in,out] A
97*> \verbatim
98*> A is COMPLEX*16 array,
99*> dimension (LDA,N)
100*> On entry, the Hermitian matrix A. If UPLO = 'U', the leading
101*> N-by-N upper triangular part of A contains the upper
102*> triangular part of the matrix A, and the strictly lower
103*> triangular part of A is not referenced. If UPLO = 'L', the
104*> leading N-by-N lower triangular part of A contains the lower
105*> triangular part of the matrix A, and the strictly upper
106*> triangular part of A is not referenced.
107*>
108*> Note that the imaginary parts of the diagonal
109*> elements need not be set and are assumed to be zero.
110*>
111*> On exit, if iterative refinement has been successfully used
112*> (INFO = 0 and ITER >= 0, see description below), then A is
113*> unchanged, if double precision factorization has been used
114*> (INFO = 0 and ITER < 0, see description below), then the
115*> array A contains the factor U or L from the Cholesky
116*> factorization A = U**H*U or A = L*L**H.
117*> \endverbatim
118*>
119*> \param[in] LDA
120*> \verbatim
121*> LDA is INTEGER
122*> The leading dimension of the array A. LDA >= max(1,N).
123*> \endverbatim
124*>
125*> \param[in] B
126*> \verbatim
127*> B is COMPLEX*16 array, dimension (LDB,NRHS)
128*> The N-by-NRHS right hand side matrix B.
129*> \endverbatim
130*>
131*> \param[in] LDB
132*> \verbatim
133*> LDB is INTEGER
134*> The leading dimension of the array B. LDB >= max(1,N).
135*> \endverbatim
136*>
137*> \param[out] X
138*> \verbatim
139*> X is COMPLEX*16 array, dimension (LDX,NRHS)
140*> If INFO = 0, the N-by-NRHS solution matrix X.
141*> \endverbatim
142*>
143*> \param[in] LDX
144*> \verbatim
145*> LDX is INTEGER
146*> The leading dimension of the array X. LDX >= max(1,N).
147*> \endverbatim
148*>
149*> \param[out] WORK
150*> \verbatim
151*> WORK is COMPLEX*16 array, dimension (N,NRHS)
152*> This array is used to hold the residual vectors.
153*> \endverbatim
154*>
155*> \param[out] SWORK
156*> \verbatim
157*> SWORK is COMPLEX array, dimension (N*(N+NRHS))
158*> This array is used to use the single precision matrix and the
159*> right-hand sides or solutions in single precision.
160*> \endverbatim
161*>
162*> \param[out] RWORK
163*> \verbatim
164*> RWORK is DOUBLE PRECISION array, dimension (N)
165*> \endverbatim
166*>
167*> \param[out] ITER
168*> \verbatim
169*> ITER is INTEGER
170*> < 0: iterative refinement has failed, COMPLEX*16
171*> factorization has been performed
172*> -1 : the routine fell back to full precision for
173*> implementation- or machine-specific reasons
174*> -2 : narrowing the precision induced an overflow,
175*> the routine fell back to full precision
176*> -3 : failure of CPOTRF
177*> -31: stop the iterative refinement after the 30th
178*> iterations
179*> > 0: iterative refinement has been successfully used.
180*> Returns the number of iterations
181*> \endverbatim
182*>
183*> \param[out] INFO
184*> \verbatim
185*> INFO is INTEGER
186*> = 0: successful exit
187*> < 0: if INFO = -i, the i-th argument had an illegal value
188*> > 0: if INFO = i, the leading principal minor of order i
189*> of (COMPLEX*16) A is not positive, so the factorization
190*> could not be completed, and the solution has not been
191*> computed.
192*> \endverbatim
193*
194* Authors:
195* ========
196*
197*> \author Univ. of Tennessee
198*> \author Univ. of California Berkeley
199*> \author Univ. of Colorado Denver
200*> \author NAG Ltd.
201*
202*> \ingroup posv_mixed
203*
204* =====================================================================
205 SUBROUTINE zcposv( UPLO, N, NRHS, A, LDA, B, LDB, X, LDX, WORK,
206 $ SWORK, RWORK, ITER, INFO )
207*
208* -- LAPACK driver routine --
209* -- LAPACK is a software package provided by Univ. of Tennessee, --
210* -- Univ. of California Berkeley, Univ. of Colorado Denver and NAG Ltd..--
211*
212* .. Scalar Arguments ..
213 CHARACTER UPLO
214 INTEGER INFO, ITER, LDA, LDB, LDX, N, NRHS
215* ..
216* .. Array Arguments ..
217 DOUBLE PRECISION RWORK( * )
218 COMPLEX SWORK( * )
219 COMPLEX*16 A( LDA, * ), B( LDB, * ), WORK( N, * ),
220 $ x( ldx, * )
221* ..
222*
223* =====================================================================
224*
225* .. Parameters ..
226 LOGICAL DOITREF
227 parameter( doitref = .true. )
228*
229 INTEGER ITERMAX
230 parameter( itermax = 30 )
231*
232 DOUBLE PRECISION BWDMAX
233 parameter( bwdmax = 1.0e+00 )
234*
235 COMPLEX*16 NEGONE, ONE
236 parameter( negone = ( -1.0d+00, 0.0d+00 ),
237 $ one = ( 1.0d+00, 0.0d+00 ) )
238*
239* .. Local Scalars ..
240 INTEGER I, IITER, PTSA, PTSX
241 DOUBLE PRECISION ANRM, CTE, EPS, RNRM, XNRM
242 COMPLEX*16 ZDUM
243*
244* .. External Subroutines ..
245 EXTERNAL zaxpy, zhemm, zlacpy, zlat2c, zlag2c,
246 $ clag2z,
248* ..
249* .. External Functions ..
250 INTEGER IZAMAX
251 DOUBLE PRECISION DLAMCH, ZLANHE
252 LOGICAL LSAME
253 EXTERNAL izamax, dlamch, zlanhe, lsame
254* ..
255* .. Intrinsic Functions ..
256 INTRINSIC abs, dble, max, sqrt
257* .. Statement Functions ..
258 DOUBLE PRECISION CABS1
259* ..
260* .. Statement Function definitions ..
261 cabs1( zdum ) = abs( dble( zdum ) ) + abs( dimag( zdum ) )
262* ..
263* .. Executable Statements ..
264*
265 info = 0
266 iter = 0
267*
268* Test the input parameters.
269*
270 IF( .NOT.lsame( uplo, 'U' ) .AND.
271 $ .NOT.lsame( uplo, 'L' ) ) THEN
272 info = -1
273 ELSE IF( n.LT.0 ) THEN
274 info = -2
275 ELSE IF( nrhs.LT.0 ) THEN
276 info = -3
277 ELSE IF( lda.LT.max( 1, n ) ) THEN
278 info = -5
279 ELSE IF( ldb.LT.max( 1, n ) ) THEN
280 info = -7
281 ELSE IF( ldx.LT.max( 1, n ) ) THEN
282 info = -9
283 END IF
284 IF( info.NE.0 ) THEN
285 CALL xerbla( 'ZCPOSV', -info )
286 RETURN
287 END IF
288*
289* Quick return if (N.EQ.0).
290*
291 IF( n.EQ.0 )
292 $ RETURN
293*
294* Skip single precision iterative refinement if a priori slower
295* than double precision factorization.
296*
297 IF( .NOT.doitref ) THEN
298 iter = -1
299 GO TO 40
300 END IF
301*
302* Compute some constants.
303*
304 anrm = zlanhe( 'I', uplo, n, a, lda, rwork )
305 eps = dlamch( 'Epsilon' )
306 cte = anrm*eps*sqrt( dble( n ) )*bwdmax
307*
308* Set the indices PTSA, PTSX for referencing SA and SX in SWORK.
309*
310 ptsa = 1
311 ptsx = ptsa + n*n
312*
313* Convert B from double precision to single precision and store the
314* result in SX.
315*
316 CALL zlag2c( n, nrhs, b, ldb, swork( ptsx ), n, info )
317*
318 IF( info.NE.0 ) THEN
319 iter = -2
320 GO TO 40
321 END IF
322*
323* Convert A from double precision to single precision and store the
324* result in SA.
325*
326 CALL zlat2c( uplo, n, a, lda, swork( ptsa ), n, info )
327*
328 IF( info.NE.0 ) THEN
329 iter = -2
330 GO TO 40
331 END IF
332*
333* Compute the Cholesky factorization of SA.
334*
335 CALL cpotrf( uplo, n, swork( ptsa ), n, info )
336*
337 IF( info.NE.0 ) THEN
338 iter = -3
339 GO TO 40
340 END IF
341*
342* Solve the system SA*SX = SB.
343*
344 CALL cpotrs( uplo, n, nrhs, swork( ptsa ), n, swork( ptsx ), n,
345 $ info )
346*
347* Convert SX back to COMPLEX*16
348*
349 CALL clag2z( n, nrhs, swork( ptsx ), n, x, ldx, info )
350*
351* Compute R = B - AX (R is WORK).
352*
353 CALL zlacpy( 'All', n, nrhs, b, ldb, work, n )
354*
355 CALL zhemm( 'Left', uplo, n, nrhs, negone, a, lda, x, ldx, one,
356 $ work, n )
357*
358* Check whether the NRHS normwise backward errors satisfy the
359* stopping criterion. If yes, set ITER=0 and return.
360*
361 DO i = 1, nrhs
362 xnrm = cabs1( x( izamax( n, x( 1, i ), 1 ), i ) )
363 rnrm = cabs1( work( izamax( n, work( 1, i ), 1 ), i ) )
364 IF( rnrm.GT.xnrm*cte )
365 $ GO TO 10
366 END DO
367*
368* If we are here, the NRHS normwise backward errors satisfy the
369* stopping criterion. We are good to exit.
370*
371 iter = 0
372 RETURN
373*
374 10 CONTINUE
375*
376 DO 30 iiter = 1, itermax
377*
378* Convert R (in WORK) from double precision to single precision
379* and store the result in SX.
380*
381 CALL zlag2c( n, nrhs, work, n, swork( ptsx ), n, info )
382*
383 IF( info.NE.0 ) THEN
384 iter = -2
385 GO TO 40
386 END IF
387*
388* Solve the system SA*SX = SR.
389*
390 CALL cpotrs( uplo, n, nrhs, swork( ptsa ), n, swork( ptsx ),
391 $ n,
392 $ info )
393*
394* Convert SX back to double precision and update the current
395* iterate.
396*
397 CALL clag2z( n, nrhs, swork( ptsx ), n, work, n, info )
398*
399 DO i = 1, nrhs
400 CALL zaxpy( n, one, work( 1, i ), 1, x( 1, i ), 1 )
401 END DO
402*
403* Compute R = B - AX (R is WORK).
404*
405 CALL zlacpy( 'All', n, nrhs, b, ldb, work, n )
406*
407 CALL zhemm( 'L', uplo, n, nrhs, negone, a, lda, x, ldx, one,
408 $ work, n )
409*
410* Check whether the NRHS normwise backward errors satisfy the
411* stopping criterion. If yes, set ITER=IITER>0 and return.
412*
413 DO i = 1, nrhs
414 xnrm = cabs1( x( izamax( n, x( 1, i ), 1 ), i ) )
415 rnrm = cabs1( work( izamax( n, work( 1, i ), 1 ), i ) )
416 IF( rnrm.GT.xnrm*cte )
417 $ GO TO 20
418 END DO
419*
420* If we are here, the NRHS normwise backward errors satisfy the
421* stopping criterion, we are good to exit.
422*
423 iter = iiter
424*
425 RETURN
426*
427 20 CONTINUE
428*
429 30 CONTINUE
430*
431* If we are at this place of the code, this is because we have
432* performed ITER=ITERMAX iterations and never satisfied the
433* stopping criterion, set up the ITER flag accordingly and follow
434* up on double precision routine.
435*
436 iter = -itermax - 1
437*
438 40 CONTINUE
439*
440* Single-precision iterative refinement failed to converge to a
441* satisfactory solution, so we resort to double precision.
442*
443 CALL zpotrf( uplo, n, a, lda, info )
444*
445 IF( info.NE.0 )
446 $ RETURN
447*
448 CALL zlacpy( 'All', n, nrhs, b, ldb, x, ldx )
449 CALL zpotrs( uplo, n, nrhs, a, lda, x, ldx, info )
450*
451 RETURN
452*
453* End of ZCPOSV
454*
455 END
subroutine xerbla(srname, info)
Definition cblat2.f:3285
subroutine clag2z(m, n, sa, ldsa, a, lda, info)
CLAG2Z converts a complex single precision matrix to a complex double precision matrix.
Definition clag2z.f:101
subroutine zlag2c(m, n, a, lda, sa, ldsa, info)
ZLAG2C converts a complex double precision matrix to a complex single precision matrix.
Definition zlag2c.f:105
subroutine zlat2c(uplo, n, a, lda, sa, ldsa, info)
ZLAT2C converts a double complex triangular matrix to a complex triangular matrix.
Definition zlat2c.f:109
subroutine zaxpy(n, za, zx, incx, zy, incy)
ZAXPY
Definition zaxpy.f:88
subroutine zhemm(side, uplo, m, n, alpha, a, lda, b, ldb, beta, c, ldc)
ZHEMM
Definition zhemm.f:191
subroutine zlacpy(uplo, m, n, a, lda, b, ldb)
ZLACPY copies all or part of one two-dimensional array to another.
Definition zlacpy.f:101
subroutine zcposv(uplo, n, nrhs, a, lda, b, ldb, x, ldx, work, swork, rwork, iter, info)
ZCPOSV computes the solution to system of linear equations A * X = B for PO matrices
Definition zcposv.f:207
subroutine zpotrf(uplo, n, a, lda, info)
ZPOTRF
Definition zpotrf.f:105
subroutine cpotrf(uplo, n, a, lda, info)
CPOTRF
Definition cpotrf.f:105
subroutine cpotrs(uplo, n, nrhs, a, lda, b, ldb, info)
CPOTRS
Definition cpotrs.f:108
subroutine zpotrs(uplo, n, nrhs, a, lda, b, ldb, info)
ZPOTRS
Definition zpotrs.f:108