private static int qzhes(int n, double[][] a, double[][] b, bool matz, double[][] z)
{
int i, j, k, l;
double r, s, t;
int l1;
double u1, u2, v1, v2;
int lb, nk1;
double rho;
if (matz)
{
// If we are interested in computing the
// eigenvectors, set Z to identity(n,n)
for (j = 0; j < n; ++j)
{
for (i = 0; i < n; ++i)
z[i][j] = 0.0;
z[j][j] = 1.0;
}
}
// Reduce b to upper triangular form
if (n <= 1) return 0;
for (l = 0; l < n - 1; ++l)
{
l1 = l + 1;
s = 0.0;
for (i = l1; i < n; ++i)
s += (System.Math.Abs(b[i][l]));
if (s == 0.0) continue;
s += (System.Math.Abs(b[l][l]));
r = 0.0;
for (i = l; i < n; ++i)
{
// Computing 2nd power
b[i][l] /= s;
r += b[i][l] * b[i][l];
}
r = Special.Sign(System.Math.Sqrt(r), b[l][l]);
b[l][l] += r;
rho = r * b[l][l];
for (j = l1; j < n; ++j)
{
t = 0.0;
for (i = l; i < n; ++i)
t += b[i][l] * b[i][j];
t = -t / rho;
for (i = l; i < n; ++i)
b[i][j] += t * b[i][l];
}
for (j = 0; j < n; ++j)
{
t = 0.0;
for (i = l; i < n; ++i)
t += b[i][l] * a[i][j];
t = -t / rho;
for (i = l; i < n; ++i)
a[i][j] += t * b[i][l];
}
b[l][l] = -s * r;
for (i = l1; i < n; ++i)
b[i][l] = 0.0;
}
// Reduce a to upper Hessenberg form, while keeping b triangular
if (n == 2)
return 0;
for (k = 0; k < n - 2; ++k)
{
nk1 = n - 2 - k;
// for l=n-1 step -1 until k+1 do
for (lb = 0; lb < nk1; ++lb)
{
l = n - lb - 2;
l1 = l + 1;
// Zero a(l+1,k)
s = (System.Math.Abs(a[l][k])) + (System.Math.Abs(a[l1][k]));
if (s == 0.0) continue;
u1 = a[l][k] / s;
u2 = a[l1][k] / s;
r = Special.Sign(Math.Sqrt(u1 * u1 + u2 * u2), u1);
v1 = -(u1 + r) / r;
v2 = -u2 / r;
u2 = v2 / v1;
for (j = k; j < n; ++j)
{
t = a[l][j] + u2 * a[l1][j];
a[l][j] += t * v1;
a[l1][j] += t * v2;
}
a[l1][k] = 0.0;
for (j = l; j < n; ++j)
{
t = b[l][j] + u2 * b[l1][j];
b[l][j] += t * v1;
b[l1][j] += t * v2;
}
// Zero b(l+1,l)
s = (System.Math.Abs(b[l1][l1])) + (System.Math.Abs(b[l1][l]));
if (s == 0.0) continue;
u1 = b[l1][l1] / s;
u2 = b[l1][l] / s;
r = Special.Sign(Math.Sqrt(u1 * u1 + u2 * u2), u1);
v1 = -(u1 + r) / r;
v2 = -u2 / r;
u2 = v2 / v1;
for (i = 0; i <= l1; ++i)
{
t = b[i][l1] + u2 * b[i][l];
b[i][l1] += t * v1;
b[i][l] += t * v2;
}
b[l1][l] = 0.0;
for (i = 0; i < n; ++i)
{
t = a[i][l1] + u2 * a[i][l];
a[i][l1] += t * v1;
a[i][l] += t * v2;
}
if (matz)
{
for (i = 0; i < n; ++i)
{
t = z[i][l1] + u2 * z[i][l];
z[i][l1] += t * v1;
z[i][l] += t * v2;
}
}
}
}
return 0;
}