130 int nargin = args.length ();
132#if defined (OCTAVE_QZ_DEBUG)
134 <<
", nargout = " << nargout << std::endl;
137 if (nargin < 2 || nargin > 3 || nargout > 6)
140 bool complex_case =
true;
144 std::string opt = args(2).xstring_value (
"qz: OPT must be a string");
148 if (args(0).iscomplex () || args(1).iscomplex ())
150 warning (
"qz: ignoring 'real' option with complex matrices");
154 complex_case =
false;
156 else if (opt ==
"complex")
159 error (
"qz: OPT must be 'real' or 'complex'");
162#if defined (OCTAVE_QZ_DEBUG)
167 F77_INT nn = to_f77_int (args(0).rows ());
168 F77_INT nc = to_f77_int (args(0).columns ());
170#if defined (OCTAVE_QZ_DEBUG)
171 octave_stdout <<
"Matrix A dimensions: (" << nn <<
',' << nc <<
')' << std::endl;
181 if (args(0).iscomplex ())
182 caa = args(0).complex_matrix_value ();
184 aa = args(0).matrix_value ();
186#if defined (OCTAVE_QZ_DEBUG)
191 F77_INT b_nr = to_f77_int (args(1).rows ());
192 F77_INT b_nc = to_f77_int (args(1).columns ());
194 if (nn != b_nc || nn != b_nr)
200 if (args(1).iscomplex ())
201 cbb = args(1).complex_matrix_value ();
203 bb = args(1).matrix_value ();
208 Matrix QQ (nn, nn), ZZ (nn, nn),
VR (nn, nn),
VL (nn, nn);
209 RowVector alphar (nn), alphai (nn), betar (nn);
213 char comp_q = (nargout >= 3 ?
'V' :
'N');
214 char comp_z = (nargout >= 4 ?
'V' :
'N');
217 if (comp_q ==
'V' || comp_z ==
'V')
219 double *QQptr = QQ.rwdata ();
220 double *ZZptr = ZZ.rwdata ();
221 std::fill_n (QQptr, QQ.numel (), 0.0);
222 std::fill_n (ZZptr, ZZ.numel (), 0.0);
223 for (
F77_INT i = 0; i < nn; i++)
231 const char bal_job =
'P';
232 RowVector lscale (nn), rscale (nn), work (6 * nn), rwork (nn);
236 if (args(0).isreal ())
239 if (args(1).isreal ())
245#if defined (OCTAVE_QZ_DEBUG)
247 octave_stdout <<
"qz: performing balancing; CQ =\n" <<
CQ << std::endl;
254 (F77_CONST_CHAR_ARG2 (&bal_job, 1),
257 nn, ilo, ihi, lscale.rwdata (),
258 rscale.rwdata (), work.rwdata (), info
259 F77_CHAR_ARG_LEN (1)));
263#if defined (OCTAVE_QZ_DEBUG)
265 octave_stdout <<
"qz: performing balancing; QQ =\n" << QQ << std::endl;
269 (F77_CONST_CHAR_ARG2 (&bal_job, 1),
271 nn, ilo, ihi, lscale.rwdata (),
272 rscale.rwdata (), work.rwdata (), info
273 F77_CHAR_ARG_LEN (1)));
278 char qz_job = (nargout < 2 ?
'E' :
'S');
285 math::qr<ComplexMatrix> cbqr (cbb);
289 caa = (cbqr.Q ().hermitian ()) * caa;
293 (F77_CONST_CHAR_ARG2 (&comp_q, 1),
294 F77_CONST_CHAR_ARG2 (&comp_z, 1),
300 F77_CHAR_ARG_LEN (1)));
305 (F77_CONST_CHAR_ARG2 (&qz_job, 1),
306 F77_CONST_CHAR_ARG2 (&comp_q, 1),
307 F77_CONST_CHAR_ARG2 (&comp_z, 1),
319 F77_CHAR_ARG_LEN (1)));
325 (F77_CONST_CHAR_ARG2 (&bal_job, 1),
326 F77_CONST_CHAR_ARG2 (
"L", 1),
327 nn, ilo, ihi, lscale.data (), rscale.data (),
330 F77_CHAR_ARG_LEN (1)));
337 (F77_CONST_CHAR_ARG2 (&bal_job, 1),
338 F77_CONST_CHAR_ARG2 (
"R", 1),
339 nn, ilo, ihi, lscale.data (), rscale.data (),
342 F77_CHAR_ARG_LEN (1)));
348#if defined (OCTAVE_QZ_DEBUG)
349 octave_stdout <<
"qz: performing qr decomposition of bb" << std::endl;
353 math::qr<Matrix> bqr (bb);
355#if defined (OCTAVE_QZ_DEBUG)
356 octave_stdout <<
"qz: qr (bb) done; now performing qz decomposition" << std::endl;
361#if defined (OCTAVE_QZ_DEBUG)
365 aa = (bqr.Q ()).transpose () * aa;
367#if defined (OCTAVE_QZ_DEBUG)
378#if defined (OCTAVE_QZ_DEBUG)
380 octave_stdout <<
"qz: comp_q = " << comp_q <<
", comp_z = " << comp_z << std::endl;
385 (F77_CONST_CHAR_ARG2 (&comp_q, 1),
386 F77_CONST_CHAR_ARG2 (&comp_z, 1),
387 nn, ilo, ihi, aa.
rwdata (),
388 nn, bb.
rwdata (), nn, QQ.rwdata (), nn,
389 ZZ.rwdata (), nn, info
391 F77_CHAR_ARG_LEN (1)));
398 (F77_CONST_CHAR_ARG2 (&qz_job, 1),
399 F77_CONST_CHAR_ARG2 (&comp_q, 1),
400 F77_CONST_CHAR_ARG2 (&comp_z, 1),
402 nn, alphar.rwdata (), alphai.rwdata (),
403 betar.
rwdata (), QQ.rwdata (), nn,
404 ZZ.rwdata (), nn, work.rwdata (), nn, info
407 F77_CHAR_ARG_LEN (1)));
412 (F77_CONST_CHAR_ARG2 (&bal_job, 1),
413 F77_CONST_CHAR_ARG2 (
"L", 1),
414 nn, ilo, ihi, lscale.data (), rscale.data (),
415 nn, QQ.rwdata (), nn, info
417 F77_CHAR_ARG_LEN (1)));
419#if defined (OCTAVE_QZ_DEBUG)
421 octave_stdout <<
"qz: balancing done; QQ=\n" << QQ << std::endl;
429 (F77_CONST_CHAR_ARG2 (&bal_job, 1),
430 F77_CONST_CHAR_ARG2 (
"R", 1),
431 nn, ilo, ihi, lscale.data (), rscale.data (),
432 nn, ZZ.rwdata (), nn, info
434 F77_CHAR_ARG_LEN (1)));
436#if defined (OCTAVE_QZ_DEBUG)
438 octave_stdout <<
"qz: balancing done; ZZ=\n" << ZZ << std::endl;
448 char side = (nargout == 5 ?
'R' :
'B');
463 (F77_CONST_CHAR_ARG2 (&side, 1),
464 F77_CONST_CHAR_ARG2 (&howmany, 1),
472 F77_CHAR_ARG_LEN (1)));
476#if defined (OCTAVE_QZ_DEBUG)
477 octave_stdout <<
"qz: computing generalized eigenvectors" << std::endl;
485 (F77_CONST_CHAR_ARG2 (&side, 1),
486 F77_CONST_CHAR_ARG2 (&howmany, 1),
488 nn,
VL.rwdata (), nn,
VR.rwdata (), nn, nn,
489 m, work.rwdata (), info
491 F77_CHAR_ARG_LEN (1)));
524 retval(2) =
CQ.hermitian ();
526 retval(2) = QQ.transpose ();
535#if defined (OCTAVE_QZ_DEBUG)
547#if defined (OCTAVE_QZ_DEBUG)
562#if defined (OCTAVE_QZ_DEBUG)