// suggested by Sederberg. double Bernsteins::horner(Bezier bz, double t) { double u, tn, tmp; u = 1.0 - t; tn = 1.0; tmp = bz.at0() * u; for(size_t i = 1; i < bz.degree(); ++i) { tn *= t; tmp = (tmp + tn*choose<double>(bz.order(), (unsigned)i)*bz[i]) * u; } return (tmp + tn*t*bz.at1()); }
void Bezier::find_bezier_roots(std::vector<double> &solutions, double left_t, double right_t) const { Bezier bz = *this; //convex_hull_marching(bz, bz, solutions, left_t, right_t); //return; // a constant bezier, even if identically zero, has no roots if (bz.isConstant()) { return; } while(bz[0] == 0) { debug(std::cout << "deflate\n"); bz = bz.deflate(); solutions.push_back(0); } if (bz.degree() == 1) { debug(std::cout << "linear\n"); if (SGN(bz[0]) != SGN(bz[1])) { double d = bz[0] - bz[1]; if(d != 0) { double r = bz[0] / d; if(0 <= r && r <= 1) solutions.push_back(r); } } return; } //std::cout << "initial = " << bz << std::endl; Bernsteins B(solutions); B.find_bernstein_roots(bz, 0, left_t, right_t); //std::cout << solutions << std::endl; }