00001 /* slaror.f -- translated by f2c (version 20061008). 00002 You must link the resulting object file with libf2c: 00003 on Microsoft Windows system, link with libf2c.lib; 00004 on Linux or Unix systems, link with .../path/to/libf2c.a -lm 00005 or, if you install libf2c.a in a standard place, with -lf2c -lm 00006 -- in that order, at the end of the command line, as in 00007 cc *.o -lf2c -lm 00008 Source for libf2c is in /netlib/f2c/libf2c.zip, e.g., 00009 00010 http://www.netlib.org/f2c/libf2c.zip 00011 */ 00012 00013 #include "f2c.h" 00014 #include "blaswrap.h" 00015 00016 /* Table of constant values */ 00017 00018 static real c_b9 = 0.f; 00019 static real c_b10 = 1.f; 00020 static integer c__3 = 3; 00021 static integer c__1 = 1; 00022 00023 /* Subroutine */ int slaror_(char *side, char *init, integer *m, integer *n, 00024 real *a, integer *lda, integer *iseed, real *x, integer *info) 00025 { 00026 /* System generated locals */ 00027 integer a_dim1, a_offset, i__1, i__2; 00028 real r__1; 00029 00030 /* Builtin functions */ 00031 double r_sign(real *, real *); 00032 00033 /* Local variables */ 00034 integer j, kbeg, jcol; 00035 extern /* Subroutine */ int sger_(integer *, integer *, real *, real *, 00036 integer *, real *, integer *, real *, integer *); 00037 integer irow; 00038 extern doublereal snrm2_(integer *, real *, integer *); 00039 extern logical lsame_(char *, char *); 00040 extern /* Subroutine */ int sscal_(integer *, real *, real *, integer *), 00041 sgemv_(char *, integer *, integer *, real *, real *, integer *, 00042 real *, integer *, real *, real *, integer *); 00043 integer ixfrm, itype, nxfrm; 00044 real xnorm; 00045 extern /* Subroutine */ int xerbla_(char *, integer *); 00046 real factor; 00047 extern doublereal slarnd_(integer *, integer *); 00048 extern /* Subroutine */ int slaset_(char *, integer *, integer *, real *, 00049 real *, real *, integer *); 00050 real xnorms; 00051 00052 00053 /* -- LAPACK auxiliary test routine (version 3.1) -- */ 00054 /* Univ. of Tennessee, Univ. of California Berkeley and NAG Ltd.. */ 00055 /* November 2006 */ 00056 00057 /* .. Scalar Arguments .. */ 00058 /* .. */ 00059 /* .. Array Arguments .. */ 00060 /* .. */ 00061 00062 /* Purpose */ 00063 /* ======= */ 00064 00065 /* SLAROR pre- or post-multiplies an M by N matrix A by a random */ 00066 /* orthogonal matrix U, overwriting A. A may optionally be initialized */ 00067 /* to the identity matrix before multiplying by U. U is generated using */ 00068 /* the method of G.W. Stewart (SIAM J. Numer. Anal. 17, 1980, 403-409). */ 00069 00070 /* Arguments */ 00071 /* ========= */ 00072 00073 /* SIDE (input) CHARACTER*1 */ 00074 /* Specifies whether A is multiplied on the left or right by U. */ 00075 /* = 'L': Multiply A on the left (premultiply) by U */ 00076 /* = 'R': Multiply A on the right (postmultiply) by U' */ 00077 /* = 'C' or 'T': Multiply A on the left by U and the right */ 00078 /* by U' (Here, U' means U-transpose.) */ 00079 00080 /* INIT (input) CHARACTER*1 */ 00081 /* Specifies whether or not A should be initialized to the */ 00082 /* identity matrix. */ 00083 /* = 'I': Initialize A to (a section of) the identity matrix */ 00084 /* before applying U. */ 00085 /* = 'N': No initialization. Apply U to the input matrix A. */ 00086 00087 /* INIT = 'I' may be used to generate square or rectangular */ 00088 /* orthogonal matrices: */ 00089 00090 /* For M = N and SIDE = 'L' or 'R', the rows will be orthogonal */ 00091 /* to each other, as will the columns. */ 00092 00093 /* If M < N, SIDE = 'R' produces a dense matrix whose rows are */ 00094 /* orthogonal and whose columns are not, while SIDE = 'L' */ 00095 /* produces a matrix whose rows are orthogonal, and whose first */ 00096 /* M columns are orthogonal, and whose remaining columns are */ 00097 /* zero. */ 00098 00099 /* If M > N, SIDE = 'L' produces a dense matrix whose columns */ 00100 /* are orthogonal and whose rows are not, while SIDE = 'R' */ 00101 /* produces a matrix whose columns are orthogonal, and whose */ 00102 /* first M rows are orthogonal, and whose remaining rows are */ 00103 /* zero. */ 00104 00105 /* M (input) INTEGER */ 00106 /* The number of rows of A. */ 00107 00108 /* N (input) INTEGER */ 00109 /* The number of columns of A. */ 00110 00111 /* A (input/output) REAL array, dimension (LDA, N) */ 00112 /* On entry, the array A. */ 00113 /* On exit, overwritten by U A ( if SIDE = 'L' ), */ 00114 /* or by A U ( if SIDE = 'R' ), */ 00115 /* or by U A U' ( if SIDE = 'C' or 'T'). */ 00116 00117 /* LDA (input) INTEGER */ 00118 /* The leading dimension of the array A. LDA >= max(1,M). */ 00119 00120 /* ISEED (input/output) INTEGER array, dimension (4) */ 00121 /* On entry ISEED specifies the seed of the random number */ 00122 /* generator. The array elements should be between 0 and 4095; */ 00123 /* if not they will be reduced mod 4096. Also, ISEED(4) must */ 00124 /* be odd. The random number generator uses a linear */ 00125 /* congruential sequence limited to small integers, and so */ 00126 /* should produce machine independent random numbers. The */ 00127 /* values of ISEED are changed on exit, and can be used in the */ 00128 /* next call to SLAROR to continue the same random number */ 00129 /* sequence. */ 00130 00131 /* X (workspace) REAL array, dimension (3*MAX( M, N )) */ 00132 /* Workspace of length */ 00133 /* 2*M + N if SIDE = 'L', */ 00134 /* 2*N + M if SIDE = 'R', */ 00135 /* 3*N if SIDE = 'C' or 'T'. */ 00136 00137 /* INFO (output) INTEGER */ 00138 /* An error flag. It is set to: */ 00139 /* = 0: normal return */ 00140 /* < 0: if INFO = -k, the k-th argument had an illegal value */ 00141 /* = 1: if the random numbers generated by SLARND are bad. */ 00142 00143 /* ===================================================================== */ 00144 00145 /* .. Parameters .. */ 00146 /* .. */ 00147 /* .. Local Scalars .. */ 00148 /* .. */ 00149 /* .. External Functions .. */ 00150 /* .. */ 00151 /* .. External Subroutines .. */ 00152 /* .. */ 00153 /* .. Intrinsic Functions .. */ 00154 /* .. */ 00155 /* .. Executable Statements .. */ 00156 00157 /* Parameter adjustments */ 00158 a_dim1 = *lda; 00159 a_offset = 1 + a_dim1; 00160 a -= a_offset; 00161 --iseed; 00162 --x; 00163 00164 /* Function Body */ 00165 if (*n == 0 || *m == 0) { 00166 return 0; 00167 } 00168 00169 itype = 0; 00170 if (lsame_(side, "L")) { 00171 itype = 1; 00172 } else if (lsame_(side, "R")) { 00173 itype = 2; 00174 } else if (lsame_(side, "C") || lsame_(side, "T")) { 00175 itype = 3; 00176 } 00177 00178 /* Check for argument errors. */ 00179 00180 *info = 0; 00181 if (itype == 0) { 00182 *info = -1; 00183 } else if (*m < 0) { 00184 *info = -3; 00185 } else if (*n < 0 || itype == 3 && *n != *m) { 00186 *info = -4; 00187 } else if (*lda < *m) { 00188 *info = -6; 00189 } 00190 if (*info != 0) { 00191 i__1 = -(*info); 00192 xerbla_("SLAROR", &i__1); 00193 return 0; 00194 } 00195 00196 if (itype == 1) { 00197 nxfrm = *m; 00198 } else { 00199 nxfrm = *n; 00200 } 00201 00202 /* Initialize A to the identity matrix if desired */ 00203 00204 if (lsame_(init, "I")) { 00205 slaset_("Full", m, n, &c_b9, &c_b10, &a[a_offset], lda); 00206 } 00207 00208 /* If no rotation possible, multiply by random +/-1 */ 00209 00210 /* Compute rotation by computing Householder transformations */ 00211 /* H(2), H(3), ..., H(nhouse) */ 00212 00213 i__1 = nxfrm; 00214 for (j = 1; j <= i__1; ++j) { 00215 x[j] = 0.f; 00216 /* L10: */ 00217 } 00218 00219 i__1 = nxfrm; 00220 for (ixfrm = 2; ixfrm <= i__1; ++ixfrm) { 00221 kbeg = nxfrm - ixfrm + 1; 00222 00223 /* Generate independent normal( 0, 1 ) random numbers */ 00224 00225 i__2 = nxfrm; 00226 for (j = kbeg; j <= i__2; ++j) { 00227 x[j] = slarnd_(&c__3, &iseed[1]); 00228 /* L20: */ 00229 } 00230 00231 /* Generate a Householder transformation from the random vector X */ 00232 00233 xnorm = snrm2_(&ixfrm, &x[kbeg], &c__1); 00234 xnorms = r_sign(&xnorm, &x[kbeg]); 00235 r__1 = -x[kbeg]; 00236 x[kbeg + nxfrm] = r_sign(&c_b10, &r__1); 00237 factor = xnorms * (xnorms + x[kbeg]); 00238 if (dabs(factor) < 1e-20f) { 00239 *info = 1; 00240 xerbla_("SLAROR", info); 00241 return 0; 00242 } else { 00243 factor = 1.f / factor; 00244 } 00245 x[kbeg] += xnorms; 00246 00247 /* Apply Householder transformation to A */ 00248 00249 if (itype == 1 || itype == 3) { 00250 00251 /* Apply H(k) from the left. */ 00252 00253 sgemv_("T", &ixfrm, n, &c_b10, &a[kbeg + a_dim1], lda, &x[kbeg], & 00254 c__1, &c_b9, &x[(nxfrm << 1) + 1], &c__1); 00255 r__1 = -factor; 00256 sger_(&ixfrm, n, &r__1, &x[kbeg], &c__1, &x[(nxfrm << 1) + 1], & 00257 c__1, &a[kbeg + a_dim1], lda); 00258 00259 } 00260 00261 if (itype == 2 || itype == 3) { 00262 00263 /* Apply H(k) from the right. */ 00264 00265 sgemv_("N", m, &ixfrm, &c_b10, &a[kbeg * a_dim1 + 1], lda, &x[ 00266 kbeg], &c__1, &c_b9, &x[(nxfrm << 1) + 1], &c__1); 00267 r__1 = -factor; 00268 sger_(m, &ixfrm, &r__1, &x[(nxfrm << 1) + 1], &c__1, &x[kbeg], & 00269 c__1, &a[kbeg * a_dim1 + 1], lda); 00270 00271 } 00272 /* L30: */ 00273 } 00274 00275 r__1 = slarnd_(&c__3, &iseed[1]); 00276 x[nxfrm * 2] = r_sign(&c_b10, &r__1); 00277 00278 /* Scale the matrix A by D. */ 00279 00280 if (itype == 1 || itype == 3) { 00281 i__1 = *m; 00282 for (irow = 1; irow <= i__1; ++irow) { 00283 sscal_(n, &x[nxfrm + irow], &a[irow + a_dim1], lda); 00284 /* L40: */ 00285 } 00286 } 00287 00288 if (itype == 2 || itype == 3) { 00289 i__1 = *n; 00290 for (jcol = 1; jcol <= i__1; ++jcol) { 00291 sscal_(m, &x[nxfrm + jcol], &a[jcol * a_dim1 + 1], &c__1); 00292 /* L50: */ 00293 } 00294 } 00295 return 0; 00296 00297 /* End of SLAROR */ 00298 00299 } /* slaror_ */