35 #if defined (HAVE_CONFIG_H)
42 #if defined (DEBUG_EIG)
55 #if defined (DEBUG) || defined (DEBUG_SORT)
63 DEFUN (qz, args, nargout,
171 int nargin = args.length ();
175 <<
", nargout = " << nargout << std::endl;
178 if (nargin < 2 || nargin > 3 || nargout > 7)
181 if (nargin == 3 && (nargout < 3 || nargout > 4))
182 error (
"qz: invalid number of output arguments for form 3 call");
185 octave_stdout <<
"qz: determine ordering option" << std::endl;
195 std::string opt = args(2).xstring_value (
"qz: OPT must be a string");
198 error (
"qz: OPT must be a non-empty string");
200 ord_job = std::toupper (opt[0]);
202 std::string valid_opts =
"NSB+-";
204 if (valid_opts.find_first_of (ord_job) == std::string::npos)
205 error (
"qz: invalid order option '%c'", ord_job);
210 F77_CHAR_ARG_LEN (1));
212 #if defined (DEBUG_EIG)
214 << setiosflags (std::ios::scientific)
215 << safmin << std::endl;
222 #if defined (DEBUG_EIG)
229 F77_CHAR_ARG_LEN (1));
231 #if defined (DEBUG_EIG)
233 << setiosflags (std::ios::scientific)
234 << safmin << std::endl;
244 F77_INT nn = octave::to_f77_int (args(0).rows ());
245 F77_INT nc = octave::to_f77_int (args(0).columns ());
252 if (args(0).isempty ())
264 if (args(0).iscomplex ())
265 caa = args(0).complex_matrix_value ();
267 aa = args(0).matrix_value ();
274 F77_INT b_nr = octave::to_f77_int (args(1).rows ());
275 F77_INT b_nc = octave::to_f77_int (args(1).columns ());
277 if (
nn != b_nc ||
nn != b_nr)
283 if (args(1).iscomplex ())
284 cbb = args(1).complex_matrix_value ();
286 bb = args(1).matrix_value ();
290 bool complex_case = (args(0).iscomplex () || args(1).iscomplex ());
292 if (nargin == 3 && complex_case)
293 error (
"qz: cannot re-order complex qz decomposition");
303 char comp_q = (nargout >= 3 ?
'V' :
'N');
304 char comp_z = ((nargout >= 4 || nargin == 3)?
'V' :
'N');
307 if (comp_q ==
'V' || comp_z ==
'V')
309 double *QQptr = QQ.fortran_vec ();
310 double *ZZptr = ZZ.fortran_vec ();
311 std::fill_n (QQptr, QQ.numel (), 0.0);
312 std::fill_n (ZZptr, ZZ.numel (), 0.0);
321 const char bal_job =
'P';
328 octave_stdout <<
"qz: performing balancing; CQ =\n" <<
CQ << std::endl;
330 if (args(0).isreal ())
333 if (args(1).isreal ())
343 (F77_CONST_CHAR_ARG2 (&bal_job, 1),
346 nn, ilo, ihi, lscale.fortran_vec (),
347 rscale.fortran_vec (), work.fortran_vec (), info
348 F77_CHAR_ARG_LEN (1)));
354 octave_stdout <<
"qz: performing balancing; QQ =\n" << QQ << std::endl;
358 (F77_CONST_CHAR_ARG2 (&bal_job, 1),
360 nn, ilo, ihi, lscale.fortran_vec (),
361 rscale.fortran_vec (), work.fortran_vec (), info
362 F77_CHAR_ARG_LEN (1)));
374 (F77_CONST_CHAR_ARG2 (&bal_job, 1),
375 F77_CONST_CHAR_ARG2 (
"L", 1),
376 nn, ilo, ihi, lscale.data (), rscale.data (),
377 nn, QQ.fortran_vec (),
nn, info
379 F77_CHAR_ARG_LEN (1)));
383 octave_stdout <<
"qz: balancing done; QQ =\n" << QQ << std::endl;
391 (F77_CONST_CHAR_ARG2 (&bal_job, 1),
392 F77_CONST_CHAR_ARG2 (
"R", 1),
393 nn, ilo, ihi, lscale.data (), rscale.data (),
394 nn, ZZ.fortran_vec (),
nn, info
396 F77_CHAR_ARG_LEN (1)));
400 octave_stdout <<
"qz: balancing done; ZZ=\n" << ZZ << std::endl;
405 char qz_job = (nargout < 2 ?
'E' :
'S');
416 caa = (cbqr.
Q ().hermitian ()) * caa;
420 (F77_CONST_CHAR_ARG2 (&comp_q, 1),
421 F77_CONST_CHAR_ARG2 (&comp_z, 1),
427 F77_CHAR_ARG_LEN (1)));
432 (F77_CONST_CHAR_ARG2 (&qz_job, 1),
433 F77_CONST_CHAR_ARG2 (&comp_q, 1),
434 F77_CONST_CHAR_ARG2 (&comp_z, 1),
446 F77_CHAR_ARG_LEN (1)));
452 (F77_CONST_CHAR_ARG2 (&bal_job, 1),
453 F77_CONST_CHAR_ARG2 (
"L", 1),
454 nn, ilo, ihi, lscale.data (), rscale.data (),
457 F77_CHAR_ARG_LEN (1)));
464 (F77_CONST_CHAR_ARG2 (&bal_job, 1),
465 F77_CONST_CHAR_ARG2 (
"R", 1),
466 nn, ilo, ihi, lscale.data (), rscale.data (),
469 F77_CHAR_ARG_LEN (1)));
476 octave_stdout <<
"qz: performing qr decomposition of bb" << std::endl;
483 octave_stdout <<
"qz: qr (bb) done; now performing qz decomposition"
511 octave_stdout <<
"qz: comp_q = " << comp_q <<
", comp_z = " << comp_z
517 (F77_CONST_CHAR_ARG2 (&comp_q, 1),
518 F77_CONST_CHAR_ARG2 (&comp_z, 1),
521 ZZ.fortran_vec (),
nn, info
523 F77_CHAR_ARG_LEN (1)));
530 (F77_CONST_CHAR_ARG2 (&qz_job, 1),
531 F77_CONST_CHAR_ARG2 (&comp_q, 1),
532 F77_CONST_CHAR_ARG2 (&comp_z, 1),
534 nn, alphar.fortran_vec (), alphai.fortran_vec (),
536 ZZ.fortran_vec (),
nn, work.fortran_vec (),
nn, info
539 F77_CHAR_ARG_LEN (1)));
544 (F77_CONST_CHAR_ARG2 (&bal_job, 1),
545 F77_CONST_CHAR_ARG2 (
"L", 1),
546 nn, ilo, ihi, lscale.data (), rscale.data (),
547 nn, QQ.fortran_vec (),
nn, info
549 F77_CHAR_ARG_LEN (1)));
553 octave_stdout <<
"qz: balancing done; QQ=\n" << QQ << std::endl;
561 (F77_CONST_CHAR_ARG2 (&bal_job, 1),
562 F77_CONST_CHAR_ARG2 (
"R", 1),
563 nn, ilo, ihi, lscale.data (), rscale.data (),
564 nn, ZZ.fortran_vec (),
nn, info
566 F77_CHAR_ARG_LEN (1)));
570 octave_stdout <<
"qz: balancing done; ZZ=\n" << ZZ << std::endl;
581 error (
"qz: cannot re-order complex QZ decomposition");
583 #if defined (DEBUG_SORT)
585 << ord_job << std::endl;
590 for (
int j = 0; j <
nn; j++)
595 select(j) = alphar(j)*alphar(j) + alphai(j)*alphai(j) < betar(j)*betar(j);
599 select(j) = alphar(j)*alphar(j) + alphai(j)*alphai(j) >= betar(j)*betar(j);
603 select(j) = alphar(j) * betar(j) >= 0;
607 select(j) = alphar(j) * betar(j) < 0;
619 F77_INT ijob = 0, mm, lrwork3 = 4*
nn+16, liwork =
nn;
629 alphar.fortran_vec (),
630 alphai.fortran_vec (),
633 ZZ.fortran_vec (),
nn,
641 #if defined (DEBUG_SORT)
665 if (nargout < 2 || nargout == 7 || (nargin == 3 && nargout == 4))
672 tmp(i) = xalpha(i) / xbeta(i);
679 octave_stdout <<
"qz: computing generalized eigenvalues" << std::endl;
688 tmp(cnt++) =
Complex (alphar(i), alphai(i)) / betar(i);
700 char side = (nargout == 5 ?
'R' :
'B');
715 (F77_CONST_CHAR_ARG2 (&side, 1),
716 F77_CONST_CHAR_ARG2 (&howmany, 1),
724 F77_CHAR_ARG_LEN (1)));
729 octave_stdout <<
"qz: computing generalized eigenvectors" << std::endl;
737 (F77_CONST_CHAR_ARG2 (&side, 1),
738 F77_CONST_CHAR_ARG2 (&howmany, 1),
741 m, work.fortran_vec (), info
743 F77_CHAR_ARG_LEN (1)));
760 else if (aa(j+1,j) == 0)
883 octave_stdout <<
"qz: retval(0) = gev = " << gev << std::endl;
889 error (
"qz: too many return arguments");
N Dimensional Array with copy-on-write semantics.
Array< T > transpose(void) const
Size of the specified dimension.
const T * fortran_vec(void) const
Size of the specified dimension.
void resize(octave_idx_type n, const Complex &rfv=Complex(0))
Vector representing the dimensions (size) of an Array.
OCTINTERP_API void print_usage(void)
#define DEFUN(name, args_name, nargout_name, doc)
Macro to define a builtin function.
void error(const char *fmt,...)
#define panic_impossible()
void err_square_matrix_required(const char *fcn, const char *name)
void warn_empty_arg(const char *name)
#define F77_DBLE_CMPLX_ARG(x)
#define F77_XFCN(f, F, args)
octave_f77_int_type F77_LOGICAL
octave_f77_int_type F77_INT
F77_RET_T F77_INT const F77_INT F77_DBLE const F77_INT F77_DBLE const F77_INT F77_DBLE const F77_INT F77_DBLE * VR
F77_RET_T const F77_INT const F77_INT const F77_INT F77_DBLE_CMPLX const F77_INT F77_DBLE_CMPLX const F77_INT F77_DBLE_CMPLX F77_DBLE_CMPLX F77_DBLE_CMPLX const F77_INT F77_DBLE_CMPLX * CZ
F77_RET_T const F77_INT const F77_INT const F77_INT F77_DBLE_CMPLX const F77_INT F77_DBLE_CMPLX const F77_INT F77_DBLE_CMPLX F77_DBLE_CMPLX F77_DBLE_CMPLX * CQ
F77_RET_T F77_INT const F77_INT F77_DBLE const F77_INT F77_DBLE const F77_INT F77_DBLE * VL
void err_nonconformant(const char *op, octave_idx_type op1_len, octave_idx_type op2_len)
std::complex< double > Complex
octave_value::octave_value(const Array< char > &chm, char type) return retval
void octave_print_internal(std::ostream &os, const float_display_format &fmt, bool d, bool pr_as_read_syntax)
static void transpose(octave_idx_type N, const octave_idx_type *ridx, const octave_idx_type *cidx, octave_idx_type *ridx2, octave_idx_type *cidx2)
subroutine xdlamch(cmach, retval)
F77_RET_T F77_FUNC(xerbla, XERBLA)(F77_CONST_CHAR_ARG_DEF(s_arg