LAPACK  3.9.1
LAPACK: Linear Algebra PACKage

◆ cunmbr()

subroutine cunmbr ( character  VECT,
character  SIDE,
character  TRANS,
integer  M,
integer  N,
integer  K,
complex, dimension( lda, * )  A,
integer  LDA,
complex, dimension( * )  TAU,
complex, dimension( ldc, * )  C,
integer  LDC,
complex, dimension( * )  WORK,
integer  LWORK,
integer  INFO 
)

CUNMBR

Download CUNMBR + dependencies [TGZ] [ZIP] [TXT]

Purpose:
 If VECT = 'Q', CUNMBR overwrites the general complex M-by-N matrix C
 with
                 SIDE = 'L'     SIDE = 'R'
 TRANS = 'N':      Q * C          C * Q
 TRANS = 'C':      Q**H * C       C * Q**H

 If VECT = 'P', CUNMBR overwrites the general complex M-by-N matrix C
 with
                 SIDE = 'L'     SIDE = 'R'
 TRANS = 'N':      P * C          C * P
 TRANS = 'C':      P**H * C       C * P**H

 Here Q and P**H are the unitary matrices determined by CGEBRD when
 reducing a complex matrix A to bidiagonal form: A = Q * B * P**H. Q
 and P**H are defined as products of elementary reflectors H(i) and
 G(i) respectively.

 Let nq = m if SIDE = 'L' and nq = n if SIDE = 'R'. Thus nq is the
 order of the unitary matrix Q or P**H that is applied.

 If VECT = 'Q', A is assumed to have been an NQ-by-K matrix:
 if nq >= k, Q = H(1) H(2) . . . H(k);
 if nq < k, Q = H(1) H(2) . . . H(nq-1).

 If VECT = 'P', A is assumed to have been a K-by-NQ matrix:
 if k < nq, P = G(1) G(2) . . . G(k);
 if k >= nq, P = G(1) G(2) . . . G(nq-1).
Parameters
[in]VECT
          VECT is CHARACTER*1
          = 'Q': apply Q or Q**H;
          = 'P': apply P or P**H.
[in]SIDE
          SIDE is CHARACTER*1
          = 'L': apply Q, Q**H, P or P**H from the Left;
          = 'R': apply Q, Q**H, P or P**H from the Right.
[in]TRANS
          TRANS is CHARACTER*1
          = 'N':  No transpose, apply Q or P;
          = 'C':  Conjugate transpose, apply Q**H or P**H.
[in]M
          M is INTEGER
          The number of rows of the matrix C. M >= 0.
[in]N
          N is INTEGER
          The number of columns of the matrix C. N >= 0.
[in]K
          K is INTEGER
          If VECT = 'Q', the number of columns in the original
          matrix reduced by CGEBRD.
          If VECT = 'P', the number of rows in the original
          matrix reduced by CGEBRD.
          K >= 0.
[in]A
          A is COMPLEX array, dimension
                                (LDA,min(nq,K)) if VECT = 'Q'
                                (LDA,nq)        if VECT = 'P'
          The vectors which define the elementary reflectors H(i) and
          G(i), whose products determine the matrices Q and P, as
          returned by CGEBRD.
[in]LDA
          LDA is INTEGER
          The leading dimension of the array A.
          If VECT = 'Q', LDA >= max(1,nq);
          if VECT = 'P', LDA >= max(1,min(nq,K)).
[in]TAU
          TAU is COMPLEX array, dimension (min(nq,K))
          TAU(i) must contain the scalar factor of the elementary
          reflector H(i) or G(i) which determines Q or P, as returned
          by CGEBRD in the array argument TAUQ or TAUP.
[in,out]C
          C is COMPLEX array, dimension (LDC,N)
          On entry, the M-by-N matrix C.
          On exit, C is overwritten by Q*C or Q**H*C or C*Q**H or C*Q
          or P*C or P**H*C or C*P or C*P**H.
[in]LDC
          LDC is INTEGER
          The leading dimension of the array C. LDC >= max(1,M).
[out]WORK
          WORK is COMPLEX array, dimension (MAX(1,LWORK))
          On exit, if INFO = 0, WORK(1) returns the optimal LWORK.
[in]LWORK
          LWORK is INTEGER
          The dimension of the array WORK.
          If SIDE = 'L', LWORK >= max(1,N);
          if SIDE = 'R', LWORK >= max(1,M);
          if N = 0 or M = 0, LWORK >= 1.
          For optimum performance LWORK >= max(1,N*NB) if SIDE = 'L',
          and LWORK >= max(1,M*NB) if SIDE = 'R', where NB is the
          optimal blocksize. (NB = 0 if M = 0 or N = 0.)

          If LWORK = -1, then a workspace query is assumed; the routine
          only calculates the optimal size of the WORK array, returns
          this value as the first entry of the WORK array, and no error
          message related to LWORK is issued by XERBLA.
[out]INFO
          INFO is INTEGER
          = 0:  successful exit
          < 0:  if INFO = -i, the i-th argument had an illegal value
Author
Univ. of Tennessee
Univ. of California Berkeley
Univ. of Colorado Denver
NAG Ltd.

Definition at line 195 of file cunmbr.f.

197 *
198 * -- LAPACK computational routine --
199 * -- LAPACK is a software package provided by Univ. of Tennessee, --
200 * -- Univ. of California Berkeley, Univ. of Colorado Denver and NAG Ltd..--
201 *
202 * .. Scalar Arguments ..
203  CHARACTER SIDE, TRANS, VECT
204  INTEGER INFO, K, LDA, LDC, LWORK, M, N
205 * ..
206 * .. Array Arguments ..
207  COMPLEX A( LDA, * ), C( LDC, * ), TAU( * ),
208  $ WORK( * )
209 * ..
210 *
211 * =====================================================================
212 *
213 * .. Local Scalars ..
214  LOGICAL APPLYQ, LEFT, LQUERY, NOTRAN
215  CHARACTER TRANST
216  INTEGER I1, I2, IINFO, LWKOPT, MI, NB, NI, NQ, NW
217 * ..
218 * .. External Functions ..
219  LOGICAL LSAME
220  INTEGER ILAENV
221  EXTERNAL ilaenv, lsame
222 * ..
223 * .. External Subroutines ..
224  EXTERNAL cunmlq, cunmqr, xerbla
225 * ..
226 * .. Intrinsic Functions ..
227  INTRINSIC max, min
228 * ..
229 * .. Executable Statements ..
230 *
231 * Test the input arguments
232 *
233  info = 0
234  applyq = lsame( vect, 'Q' )
235  left = lsame( side, 'L' )
236  notran = lsame( trans, 'N' )
237  lquery = ( lwork.EQ.-1 )
238 *
239 * NQ is the order of Q or P and NW is the minimum dimension of WORK
240 *
241  IF( left ) THEN
242  nq = m
243  nw = n
244  ELSE
245  nq = n
246  nw = m
247  END IF
248  IF( m.EQ.0 .OR. n.EQ.0 ) THEN
249  nw = 0
250  END IF
251  IF( .NOT.applyq .AND. .NOT.lsame( vect, 'P' ) ) THEN
252  info = -1
253  ELSE IF( .NOT.left .AND. .NOT.lsame( side, 'R' ) ) THEN
254  info = -2
255  ELSE IF( .NOT.notran .AND. .NOT.lsame( trans, 'C' ) ) THEN
256  info = -3
257  ELSE IF( m.LT.0 ) THEN
258  info = -4
259  ELSE IF( n.LT.0 ) THEN
260  info = -5
261  ELSE IF( k.LT.0 ) THEN
262  info = -6
263  ELSE IF( ( applyq .AND. lda.LT.max( 1, nq ) ) .OR.
264  $ ( .NOT.applyq .AND. lda.LT.max( 1, min( nq, k ) ) ) )
265  $ THEN
266  info = -8
267  ELSE IF( ldc.LT.max( 1, m ) ) THEN
268  info = -11
269  ELSE IF( lwork.LT.max( 1, nw ) .AND. .NOT.lquery ) THEN
270  info = -13
271  END IF
272 *
273  IF( info.EQ.0 ) THEN
274  IF( nw.GT.0 ) THEN
275  IF( applyq ) THEN
276  IF( left ) THEN
277  nb = ilaenv( 1, 'CUNMQR', side // trans, m-1, n, m-1,
278  $ -1 )
279  ELSE
280  nb = ilaenv( 1, 'CUNMQR', side // trans, m, n-1, n-1,
281  $ -1 )
282  END IF
283  ELSE
284  IF( left ) THEN
285  nb = ilaenv( 1, 'CUNMLQ', side // trans, m-1, n, m-1,
286  $ -1 )
287  ELSE
288  nb = ilaenv( 1, 'CUNMLQ', side // trans, m, n-1, n-1,
289  $ -1 )
290  END IF
291  END IF
292  lwkopt = max( 1, nw*nb )
293  ELSE
294  lwkopt = 1
295  END IF
296  work( 1 ) = lwkopt
297  END IF
298 *
299  IF( info.NE.0 ) THEN
300  CALL xerbla( 'CUNMBR', -info )
301  RETURN
302  ELSE IF( lquery ) THEN
303  RETURN
304  END IF
305 *
306 * Quick return if possible
307 *
308  IF( m.EQ.0 .OR. n.EQ.0 )
309  $ RETURN
310 *
311  IF( applyq ) THEN
312 *
313 * Apply Q
314 *
315  IF( nq.GE.k ) THEN
316 *
317 * Q was determined by a call to CGEBRD with nq >= k
318 *
319  CALL cunmqr( side, trans, m, n, k, a, lda, tau, c, ldc,
320  $ work, lwork, iinfo )
321  ELSE IF( nq.GT.1 ) THEN
322 *
323 * Q was determined by a call to CGEBRD with nq < k
324 *
325  IF( left ) THEN
326  mi = m - 1
327  ni = n
328  i1 = 2
329  i2 = 1
330  ELSE
331  mi = m
332  ni = n - 1
333  i1 = 1
334  i2 = 2
335  END IF
336  CALL cunmqr( side, trans, mi, ni, nq-1, a( 2, 1 ), lda, tau,
337  $ c( i1, i2 ), ldc, work, lwork, iinfo )
338  END IF
339  ELSE
340 *
341 * Apply P
342 *
343  IF( notran ) THEN
344  transt = 'C'
345  ELSE
346  transt = 'N'
347  END IF
348  IF( nq.GT.k ) THEN
349 *
350 * P was determined by a call to CGEBRD with nq > k
351 *
352  CALL cunmlq( side, transt, m, n, k, a, lda, tau, c, ldc,
353  $ work, lwork, iinfo )
354  ELSE IF( nq.GT.1 ) THEN
355 *
356 * P was determined by a call to CGEBRD with nq <= k
357 *
358  IF( left ) THEN
359  mi = m - 1
360  ni = n
361  i1 = 2
362  i2 = 1
363  ELSE
364  mi = m
365  ni = n - 1
366  i1 = 1
367  i2 = 2
368  END IF
369  CALL cunmlq( side, transt, mi, ni, nq-1, a( 1, 2 ), lda,
370  $ tau, c( i1, i2 ), ldc, work, lwork, iinfo )
371  END IF
372  END IF
373  work( 1 ) = lwkopt
374  RETURN
375 *
376 * End of CUNMBR
377 *
integer function ilaenv(ISPEC, NAME, OPTS, N1, N2, N3, N4)
ILAENV
Definition: ilaenv.f:162
subroutine xerbla(SRNAME, INFO)
XERBLA
Definition: xerbla.f:60
logical function lsame(CA, CB)
LSAME
Definition: lsame.f:53
subroutine cunmlq(SIDE, TRANS, M, N, K, A, LDA, TAU, C, LDC, WORK, LWORK, INFO)
CUNMLQ
Definition: cunmlq.f:168
subroutine cunmqr(SIDE, TRANS, M, N, K, A, LDA, TAU, C, LDC, WORK, LWORK, INFO)
CUNMQR
Definition: cunmqr.f:168
Here is the call graph for this function:
Here is the caller graph for this function: