home *** CD-ROM | disk | FTP | other *** search
- cubic(a,rt1,rt2,rt3,tol,numrt)
-
- /*this function finds the roots (real or */
- /*real and complex) to any cubic equation. */
-
- int *numrt;
- float a[],rt1[],rt2[],rt3[],tol;
-
- {
-
- int it,n,nda,i;
- float ang,b[2],c[4],work[3],x,y,zz,zero;
- extern double fabs(),sqrt(),sin(),cos(),acos(),exp(),log(),pow();
-
- zero = tol/10.;
-
- if((fabs(a[0]) - zero) <= 0)
- {
- for(i = 0;i <= 2; i++)
- work[i] = a[i+1];
- quadrt(work, rt1,rt2,tol,&n);
- *numrt = n;
- return;
- }
- *numrt = 3;
- it = 0;
- for(i = 1; i <= 3; i++)
- a[i] = a[i]/a[0];
- a[0] = 1.0;
-
- if(fabs(a[1]) > zero)
- {
- nda = 3;
- b[0] = 1.0;
- b[1] = -(a[1]*.333333);
- lincng(a,nda,b,c);
- it = 1;
- }
- else
- {
- for(i = 0; i <= 3; i++)
- c[i] = a[i];
- }
- x = c[3] * c[3] * .25 + c[2]*c[2]*c[2] * .037037;
- if(x >= 0.0)
- {
- x = sqrt(x);
- y = -(c[3]*.5);
- i = 0;
- rt1[i] = y + x;
- l5: n = 0;
- if(rt1[0] < 0.0) n = 1;
- if(fabs(rt1[0]) > zero)
- {
- rt1[i] = exp((log(fabs(rt1[i])))*.333333);
- if(n == 1) rt1[i] = -rt1[i];
- }
- if(i == 1) goto l8;
- i = 1;
- rt1[i] = y - x;
- goto l5;
-
- l8: rt2[1] = ((rt1[0] - rt1[1])*.5)*1.732051;
- rt1[0] = rt1[0] + rt1[1];
- rt1[1] = 0.0;
- rt2[0] = - rt1[0] * .5;
- rt3[0] = rt2[0];
- rt3[1] = -rt2[1];
- }
- else
- {
- zz = fabs(c[2]);
- x = -(c[3]*.5)/sqrt(pow(zz,3.)*.037037);
- ang= acos(x);
- y = 2.0 * (sqrt(zz*.333333));
- ang = ang*.333333;
- rt1[0] = y * cos(ang);
- rt2[0] = y * cos(ang + 2.09440);
- rt3[0] = y * cos(ang + 4.18879);
- rt1[1] = 0.0;
- rt2[1] = 0.0;
- rt3[1] = 0.0;
- }
- if(it == 0) return;
- rt1[0] = rt1[0] + b[1];
- rt2[0] = rt2[0] + b[1];
- rt3[0] = rt3[0] + b[1];
- }