Hi Jim.

> What about logic like this:
> 
> boolean checkRoots = false;
> if (D < 0) {
> // 3 solution form is possible, so use it
> checkRoots = (D > -TINY); // Check them if we were borderline
> // compute 3 roots as before
> } else {
> double u = ...;
> double v = ...;
> res[0] = u+v; // should be 2*u if D is near zero
> if (u close to v) { // Will be true for D near zero
> res[1] = -res[0]/2; // should be -u if D is near zero
> checkRoots = true; // Check them if we were borderline
> // Note that q=0 case ends up here as well...
> }
> }
> if (checkRoots) {
> if (num > 2 && (res[2] == res[1] || res[2] == res[0]) {
> num--;
> }
> if (num > 1 && res[1] == res[0]) {
> res[1] = res[--num]; // Copies res[2] to res[1] if needed
> }
> for (int i = num-1; i >= 0; i--) {
> res[i] = refine(res[i]);
> for (int j = i+1; j < num; j++) {
> if (res[i] == res[j]) {
> res[i] = res[--num];
> break;
> }
> }
> }
> }

I have two concerns about this.

1. How would refine() be implemented? Would we do something like in
findZero?
2. While I have no problem with your suggestion, it won't help us in
cases where there's a root with a multiplicity of 2 which is not found.
This was a large part of the motivation for this work. What should we
do in this case? The only solution I can see is to find the roots of
the derivative and evaluate the cubic at them, because when a root
has multiplicity > 1, the polynomial's derivative also has a root
there. This is what I'm currently doing.

Should we go ahead and push the pisces changes? The cubic solver
in pisces is good enough for what we're using it.

Regards,
Denis.

Reply via email to