LAPACK 3.3.1
Linear Algebra PACKage
|
00001 SUBROUTINE ZHFRK( TRANSR, UPLO, TRANS, N, K, ALPHA, A, LDA, BETA, 00002 $ C ) 00003 * 00004 * -- LAPACK routine (version 3.3.1) -- 00005 * 00006 * -- Contributed by Julien Langou of the Univ. of Colorado Denver -- 00007 * -- April 2011 -- 00008 * 00009 * -- LAPACK is a software package provided by Univ. of Tennessee, -- 00010 * -- Univ. of California Berkeley, Univ. of Colorado Denver and NAG Ltd..-- 00011 * 00012 * .. 00013 * .. Scalar Arguments .. 00014 DOUBLE PRECISION ALPHA, BETA 00015 INTEGER K, LDA, N 00016 CHARACTER TRANS, TRANSR, UPLO 00017 * .. 00018 * .. Array Arguments .. 00019 COMPLEX*16 A( LDA, * ), C( * ) 00020 * .. 00021 * 00022 * Purpose 00023 * ======= 00024 * 00025 * Level 3 BLAS like routine for C in RFP Format. 00026 * 00027 * ZHFRK performs one of the Hermitian rank--k operations 00028 * 00029 * C := alpha*A*A**H + beta*C, 00030 * 00031 * or 00032 * 00033 * C := alpha*A**H*A + beta*C, 00034 * 00035 * where alpha and beta are real scalars, C is an n--by--n Hermitian 00036 * matrix and A is an n--by--k matrix in the first case and a k--by--n 00037 * matrix in the second case. 00038 * 00039 * Arguments 00040 * ========== 00041 * 00042 * TRANSR (input) CHARACTER*1 00043 * = 'N': The Normal Form of RFP A is stored; 00044 * = 'C': The Conjugate-transpose Form of RFP A is stored. 00045 * 00046 * UPLO (input) CHARACTER*1 00047 * On entry, UPLO specifies whether the upper or lower 00048 * triangular part of the array C is to be referenced as 00049 * follows: 00050 * 00051 * UPLO = 'U' or 'u' Only the upper triangular part of C 00052 * is to be referenced. 00053 * 00054 * UPLO = 'L' or 'l' Only the lower triangular part of C 00055 * is to be referenced. 00056 * 00057 * Unchanged on exit. 00058 * 00059 * TRANS (input) CHARACTER*1 00060 * On entry, TRANS specifies the operation to be performed as 00061 * follows: 00062 * 00063 * TRANS = 'N' or 'n' C := alpha*A*A**H + beta*C. 00064 * 00065 * TRANS = 'C' or 'c' C := alpha*A**H*A + beta*C. 00066 * 00067 * Unchanged on exit. 00068 * 00069 * N (input) INTEGER 00070 * On entry, N specifies the order of the matrix C. N must be 00071 * at least zero. 00072 * Unchanged on exit. 00073 * 00074 * K (input) INTEGER 00075 * On entry with TRANS = 'N' or 'n', K specifies the number 00076 * of columns of the matrix A, and on entry with 00077 * TRANS = 'C' or 'c', K specifies the number of rows of the 00078 * matrix A. K must be at least zero. 00079 * Unchanged on exit. 00080 * 00081 * ALPHA (input) DOUBLE PRECISION 00082 * On entry, ALPHA specifies the scalar alpha. 00083 * Unchanged on exit. 00084 * 00085 * A (input) COMPLEX*16 array of DIMENSION (LDA,ka) 00086 * where KA 00087 * is K when TRANS = 'N' or 'n', and is N otherwise. Before 00088 * entry with TRANS = 'N' or 'n', the leading N--by--K part of 00089 * the array A must contain the matrix A, otherwise the leading 00090 * K--by--N part of the array A must contain the matrix A. 00091 * Unchanged on exit. 00092 * 00093 * LDA (input) INTEGER 00094 * On entry, LDA specifies the first dimension of A as declared 00095 * in the calling (sub) program. When TRANS = 'N' or 'n' 00096 * then LDA must be at least max( 1, n ), otherwise LDA must 00097 * be at least max( 1, k ). 00098 * Unchanged on exit. 00099 * 00100 * BETA (input) DOUBLE PRECISION 00101 * On entry, BETA specifies the scalar beta. 00102 * Unchanged on exit. 00103 * 00104 * C (input/output) COMPLEX*16 array, dimension (N*(N+1)/2) 00105 * On entry, the matrix A in RFP Format. RFP Format is 00106 * described by TRANSR, UPLO and N. Note that the imaginary 00107 * parts of the diagonal elements need not be set, they are 00108 * assumed to be zero, and on exit they are set to zero. 00109 * 00110 * ===================================================================== 00111 * 00112 * .. Parameters .. 00113 DOUBLE PRECISION ONE, ZERO 00114 COMPLEX*16 CZERO 00115 PARAMETER ( ONE = 1.0D+0, ZERO = 0.0D+0 ) 00116 PARAMETER ( CZERO = ( 0.0D+0, 0.0D+0 ) ) 00117 * .. 00118 * .. Local Scalars .. 00119 LOGICAL LOWER, NORMALTRANSR, NISODD, NOTRANS 00120 INTEGER INFO, NROWA, J, NK, N1, N2 00121 COMPLEX*16 CALPHA, CBETA 00122 * .. 00123 * .. External Functions .. 00124 LOGICAL LSAME 00125 EXTERNAL LSAME 00126 * .. 00127 * .. External Subroutines .. 00128 EXTERNAL XERBLA, ZGEMM, ZHERK 00129 * .. 00130 * .. Intrinsic Functions .. 00131 INTRINSIC MAX, DCMPLX 00132 * .. 00133 * .. Executable Statements .. 00134 * 00135 * 00136 * Test the input parameters. 00137 * 00138 INFO = 0 00139 NORMALTRANSR = LSAME( TRANSR, 'N' ) 00140 LOWER = LSAME( UPLO, 'L' ) 00141 NOTRANS = LSAME( TRANS, 'N' ) 00142 * 00143 IF( NOTRANS ) THEN 00144 NROWA = N 00145 ELSE 00146 NROWA = K 00147 END IF 00148 * 00149 IF( .NOT.NORMALTRANSR .AND. .NOT.LSAME( TRANSR, 'C' ) ) THEN 00150 INFO = -1 00151 ELSE IF( .NOT.LOWER .AND. .NOT.LSAME( UPLO, 'U' ) ) THEN 00152 INFO = -2 00153 ELSE IF( .NOT.NOTRANS .AND. .NOT.LSAME( TRANS, 'C' ) ) THEN 00154 INFO = -3 00155 ELSE IF( N.LT.0 ) THEN 00156 INFO = -4 00157 ELSE IF( K.LT.0 ) THEN 00158 INFO = -5 00159 ELSE IF( LDA.LT.MAX( 1, NROWA ) ) THEN 00160 INFO = -8 00161 END IF 00162 IF( INFO.NE.0 ) THEN 00163 CALL XERBLA( 'ZHFRK ', -INFO ) 00164 RETURN 00165 END IF 00166 * 00167 * Quick return if possible. 00168 * 00169 * The quick return case: ((ALPHA.EQ.0).AND.(BETA.NE.ZERO)) is not 00170 * done (it is in ZHERK for example) and left in the general case. 00171 * 00172 IF( ( N.EQ.0 ) .OR. ( ( ( ALPHA.EQ.ZERO ) .OR. ( K.EQ.0 ) ) .AND. 00173 $ ( BETA.EQ.ONE ) ) )RETURN 00174 * 00175 IF( ( ALPHA.EQ.ZERO ) .AND. ( BETA.EQ.ZERO ) ) THEN 00176 DO J = 1, ( ( N*( N+1 ) ) / 2 ) 00177 C( J ) = CZERO 00178 END DO 00179 RETURN 00180 END IF 00181 * 00182 CALPHA = DCMPLX( ALPHA, ZERO ) 00183 CBETA = DCMPLX( BETA, ZERO ) 00184 * 00185 * C is N-by-N. 00186 * If N is odd, set NISODD = .TRUE., and N1 and N2. 00187 * If N is even, NISODD = .FALSE., and NK. 00188 * 00189 IF( MOD( N, 2 ).EQ.0 ) THEN 00190 NISODD = .FALSE. 00191 NK = N / 2 00192 ELSE 00193 NISODD = .TRUE. 00194 IF( LOWER ) THEN 00195 N2 = N / 2 00196 N1 = N - N2 00197 ELSE 00198 N1 = N / 2 00199 N2 = N - N1 00200 END IF 00201 END IF 00202 * 00203 IF( NISODD ) THEN 00204 * 00205 * N is odd 00206 * 00207 IF( NORMALTRANSR ) THEN 00208 * 00209 * N is odd and TRANSR = 'N' 00210 * 00211 IF( LOWER ) THEN 00212 * 00213 * N is odd, TRANSR = 'N', and UPLO = 'L' 00214 * 00215 IF( NOTRANS ) THEN 00216 * 00217 * N is odd, TRANSR = 'N', UPLO = 'L', and TRANS = 'N' 00218 * 00219 CALL ZHERK( 'L', 'N', N1, K, ALPHA, A( 1, 1 ), LDA, 00220 $ BETA, C( 1 ), N ) 00221 CALL ZHERK( 'U', 'N', N2, K, ALPHA, A( N1+1, 1 ), LDA, 00222 $ BETA, C( N+1 ), N ) 00223 CALL ZGEMM( 'N', 'C', N2, N1, K, CALPHA, A( N1+1, 1 ), 00224 $ LDA, A( 1, 1 ), LDA, CBETA, C( N1+1 ), N ) 00225 * 00226 ELSE 00227 * 00228 * N is odd, TRANSR = 'N', UPLO = 'L', and TRANS = 'C' 00229 * 00230 CALL ZHERK( 'L', 'C', N1, K, ALPHA, A( 1, 1 ), LDA, 00231 $ BETA, C( 1 ), N ) 00232 CALL ZHERK( 'U', 'C', N2, K, ALPHA, A( 1, N1+1 ), LDA, 00233 $ BETA, C( N+1 ), N ) 00234 CALL ZGEMM( 'C', 'N', N2, N1, K, CALPHA, A( 1, N1+1 ), 00235 $ LDA, A( 1, 1 ), LDA, CBETA, C( N1+1 ), N ) 00236 * 00237 END IF 00238 * 00239 ELSE 00240 * 00241 * N is odd, TRANSR = 'N', and UPLO = 'U' 00242 * 00243 IF( NOTRANS ) THEN 00244 * 00245 * N is odd, TRANSR = 'N', UPLO = 'U', and TRANS = 'N' 00246 * 00247 CALL ZHERK( 'L', 'N', N1, K, ALPHA, A( 1, 1 ), LDA, 00248 $ BETA, C( N2+1 ), N ) 00249 CALL ZHERK( 'U', 'N', N2, K, ALPHA, A( N2, 1 ), LDA, 00250 $ BETA, C( N1+1 ), N ) 00251 CALL ZGEMM( 'N', 'C', N1, N2, K, CALPHA, A( 1, 1 ), 00252 $ LDA, A( N2, 1 ), LDA, CBETA, C( 1 ), N ) 00253 * 00254 ELSE 00255 * 00256 * N is odd, TRANSR = 'N', UPLO = 'U', and TRANS = 'C' 00257 * 00258 CALL ZHERK( 'L', 'C', N1, K, ALPHA, A( 1, 1 ), LDA, 00259 $ BETA, C( N2+1 ), N ) 00260 CALL ZHERK( 'U', 'C', N2, K, ALPHA, A( 1, N2 ), LDA, 00261 $ BETA, C( N1+1 ), N ) 00262 CALL ZGEMM( 'C', 'N', N1, N2, K, CALPHA, A( 1, 1 ), 00263 $ LDA, A( 1, N2 ), LDA, CBETA, C( 1 ), N ) 00264 * 00265 END IF 00266 * 00267 END IF 00268 * 00269 ELSE 00270 * 00271 * N is odd, and TRANSR = 'C' 00272 * 00273 IF( LOWER ) THEN 00274 * 00275 * N is odd, TRANSR = 'C', and UPLO = 'L' 00276 * 00277 IF( NOTRANS ) THEN 00278 * 00279 * N is odd, TRANSR = 'C', UPLO = 'L', and TRANS = 'N' 00280 * 00281 CALL ZHERK( 'U', 'N', N1, K, ALPHA, A( 1, 1 ), LDA, 00282 $ BETA, C( 1 ), N1 ) 00283 CALL ZHERK( 'L', 'N', N2, K, ALPHA, A( N1+1, 1 ), LDA, 00284 $ BETA, C( 2 ), N1 ) 00285 CALL ZGEMM( 'N', 'C', N1, N2, K, CALPHA, A( 1, 1 ), 00286 $ LDA, A( N1+1, 1 ), LDA, CBETA, 00287 $ C( N1*N1+1 ), N1 ) 00288 * 00289 ELSE 00290 * 00291 * N is odd, TRANSR = 'C', UPLO = 'L', and TRANS = 'C' 00292 * 00293 CALL ZHERK( 'U', 'C', N1, K, ALPHA, A( 1, 1 ), LDA, 00294 $ BETA, C( 1 ), N1 ) 00295 CALL ZHERK( 'L', 'C', N2, K, ALPHA, A( 1, N1+1 ), LDA, 00296 $ BETA, C( 2 ), N1 ) 00297 CALL ZGEMM( 'C', 'N', N1, N2, K, CALPHA, A( 1, 1 ), 00298 $ LDA, A( 1, N1+1 ), LDA, CBETA, 00299 $ C( N1*N1+1 ), N1 ) 00300 * 00301 END IF 00302 * 00303 ELSE 00304 * 00305 * N is odd, TRANSR = 'C', and UPLO = 'U' 00306 * 00307 IF( NOTRANS ) THEN 00308 * 00309 * N is odd, TRANSR = 'C', UPLO = 'U', and TRANS = 'N' 00310 * 00311 CALL ZHERK( 'U', 'N', N1, K, ALPHA, A( 1, 1 ), LDA, 00312 $ BETA, C( N2*N2+1 ), N2 ) 00313 CALL ZHERK( 'L', 'N', N2, K, ALPHA, A( N1+1, 1 ), LDA, 00314 $ BETA, C( N1*N2+1 ), N2 ) 00315 CALL ZGEMM( 'N', 'C', N2, N1, K, CALPHA, A( N1+1, 1 ), 00316 $ LDA, A( 1, 1 ), LDA, CBETA, C( 1 ), N2 ) 00317 * 00318 ELSE 00319 * 00320 * N is odd, TRANSR = 'C', UPLO = 'U', and TRANS = 'C' 00321 * 00322 CALL ZHERK( 'U', 'C', N1, K, ALPHA, A( 1, 1 ), LDA, 00323 $ BETA, C( N2*N2+1 ), N2 ) 00324 CALL ZHERK( 'L', 'C', N2, K, ALPHA, A( 1, N1+1 ), LDA, 00325 $ BETA, C( N1*N2+1 ), N2 ) 00326 CALL ZGEMM( 'C', 'N', N2, N1, K, CALPHA, A( 1, N1+1 ), 00327 $ LDA, A( 1, 1 ), LDA, CBETA, C( 1 ), N2 ) 00328 * 00329 END IF 00330 * 00331 END IF 00332 * 00333 END IF 00334 * 00335 ELSE 00336 * 00337 * N is even 00338 * 00339 IF( NORMALTRANSR ) THEN 00340 * 00341 * N is even and TRANSR = 'N' 00342 * 00343 IF( LOWER ) THEN 00344 * 00345 * N is even, TRANSR = 'N', and UPLO = 'L' 00346 * 00347 IF( NOTRANS ) THEN 00348 * 00349 * N is even, TRANSR = 'N', UPLO = 'L', and TRANS = 'N' 00350 * 00351 CALL ZHERK( 'L', 'N', NK, K, ALPHA, A( 1, 1 ), LDA, 00352 $ BETA, C( 2 ), N+1 ) 00353 CALL ZHERK( 'U', 'N', NK, K, ALPHA, A( NK+1, 1 ), LDA, 00354 $ BETA, C( 1 ), N+1 ) 00355 CALL ZGEMM( 'N', 'C', NK, NK, K, CALPHA, A( NK+1, 1 ), 00356 $ LDA, A( 1, 1 ), LDA, CBETA, C( NK+2 ), 00357 $ N+1 ) 00358 * 00359 ELSE 00360 * 00361 * N is even, TRANSR = 'N', UPLO = 'L', and TRANS = 'C' 00362 * 00363 CALL ZHERK( 'L', 'C', NK, K, ALPHA, A( 1, 1 ), LDA, 00364 $ BETA, C( 2 ), N+1 ) 00365 CALL ZHERK( 'U', 'C', NK, K, ALPHA, A( 1, NK+1 ), LDA, 00366 $ BETA, C( 1 ), N+1 ) 00367 CALL ZGEMM( 'C', 'N', NK, NK, K, CALPHA, A( 1, NK+1 ), 00368 $ LDA, A( 1, 1 ), LDA, CBETA, C( NK+2 ), 00369 $ N+1 ) 00370 * 00371 END IF 00372 * 00373 ELSE 00374 * 00375 * N is even, TRANSR = 'N', and UPLO = 'U' 00376 * 00377 IF( NOTRANS ) THEN 00378 * 00379 * N is even, TRANSR = 'N', UPLO = 'U', and TRANS = 'N' 00380 * 00381 CALL ZHERK( 'L', 'N', NK, K, ALPHA, A( 1, 1 ), LDA, 00382 $ BETA, C( NK+2 ), N+1 ) 00383 CALL ZHERK( 'U', 'N', NK, K, ALPHA, A( NK+1, 1 ), LDA, 00384 $ BETA, C( NK+1 ), N+1 ) 00385 CALL ZGEMM( 'N', 'C', NK, NK, K, CALPHA, A( 1, 1 ), 00386 $ LDA, A( NK+1, 1 ), LDA, CBETA, C( 1 ), 00387 $ N+1 ) 00388 * 00389 ELSE 00390 * 00391 * N is even, TRANSR = 'N', UPLO = 'U', and TRANS = 'C' 00392 * 00393 CALL ZHERK( 'L', 'C', NK, K, ALPHA, A( 1, 1 ), LDA, 00394 $ BETA, C( NK+2 ), N+1 ) 00395 CALL ZHERK( 'U', 'C', NK, K, ALPHA, A( 1, NK+1 ), LDA, 00396 $ BETA, C( NK+1 ), N+1 ) 00397 CALL ZGEMM( 'C', 'N', NK, NK, K, CALPHA, A( 1, 1 ), 00398 $ LDA, A( 1, NK+1 ), LDA, CBETA, C( 1 ), 00399 $ N+1 ) 00400 * 00401 END IF 00402 * 00403 END IF 00404 * 00405 ELSE 00406 * 00407 * N is even, and TRANSR = 'C' 00408 * 00409 IF( LOWER ) THEN 00410 * 00411 * N is even, TRANSR = 'C', and UPLO = 'L' 00412 * 00413 IF( NOTRANS ) THEN 00414 * 00415 * N is even, TRANSR = 'C', UPLO = 'L', and TRANS = 'N' 00416 * 00417 CALL ZHERK( 'U', 'N', NK, K, ALPHA, A( 1, 1 ), LDA, 00418 $ BETA, C( NK+1 ), NK ) 00419 CALL ZHERK( 'L', 'N', NK, K, ALPHA, A( NK+1, 1 ), LDA, 00420 $ BETA, C( 1 ), NK ) 00421 CALL ZGEMM( 'N', 'C', NK, NK, K, CALPHA, A( 1, 1 ), 00422 $ LDA, A( NK+1, 1 ), LDA, CBETA, 00423 $ C( ( ( NK+1 )*NK )+1 ), NK ) 00424 * 00425 ELSE 00426 * 00427 * N is even, TRANSR = 'C', UPLO = 'L', and TRANS = 'C' 00428 * 00429 CALL ZHERK( 'U', 'C', NK, K, ALPHA, A( 1, 1 ), LDA, 00430 $ BETA, C( NK+1 ), NK ) 00431 CALL ZHERK( 'L', 'C', NK, K, ALPHA, A( 1, NK+1 ), LDA, 00432 $ BETA, C( 1 ), NK ) 00433 CALL ZGEMM( 'C', 'N', NK, NK, K, CALPHA, A( 1, 1 ), 00434 $ LDA, A( 1, NK+1 ), LDA, CBETA, 00435 $ C( ( ( NK+1 )*NK )+1 ), NK ) 00436 * 00437 END IF 00438 * 00439 ELSE 00440 * 00441 * N is even, TRANSR = 'C', and UPLO = 'U' 00442 * 00443 IF( NOTRANS ) THEN 00444 * 00445 * N is even, TRANSR = 'C', UPLO = 'U', and TRANS = 'N' 00446 * 00447 CALL ZHERK( 'U', 'N', NK, K, ALPHA, A( 1, 1 ), LDA, 00448 $ BETA, C( NK*( NK+1 )+1 ), NK ) 00449 CALL ZHERK( 'L', 'N', NK, K, ALPHA, A( NK+1, 1 ), LDA, 00450 $ BETA, C( NK*NK+1 ), NK ) 00451 CALL ZGEMM( 'N', 'C', NK, NK, K, CALPHA, A( NK+1, 1 ), 00452 $ LDA, A( 1, 1 ), LDA, CBETA, C( 1 ), NK ) 00453 * 00454 ELSE 00455 * 00456 * N is even, TRANSR = 'C', UPLO = 'U', and TRANS = 'C' 00457 * 00458 CALL ZHERK( 'U', 'C', NK, K, ALPHA, A( 1, 1 ), LDA, 00459 $ BETA, C( NK*( NK+1 )+1 ), NK ) 00460 CALL ZHERK( 'L', 'C', NK, K, ALPHA, A( 1, NK+1 ), LDA, 00461 $ BETA, C( NK*NK+1 ), NK ) 00462 CALL ZGEMM( 'C', 'N', NK, NK, K, CALPHA, A( 1, NK+1 ), 00463 $ LDA, A( 1, 1 ), LDA, CBETA, C( 1 ), NK ) 00464 * 00465 END IF 00466 * 00467 END IF 00468 * 00469 END IF 00470 * 00471 END IF 00472 * 00473 RETURN 00474 * 00475 * End of ZHFRK 00476 * 00477 END