|
|
@@ -91,7 +91,7 @@ struct polynomial |
|
|
|
* as the value instead of a scalar. */ |
|
|
|
template<typename U> U eval(U x) const |
|
|
|
{ |
|
|
|
U ret((*this)[degree()]); |
|
|
|
U ret(leading()); |
|
|
|
for (int i = degree() - 1; i >= 0; --i) |
|
|
|
ret = ret * x + U(m_coefficients[i]); |
|
|
|
return ret; |
|
|
@@ -166,6 +166,12 @@ struct polynomial |
|
|
|
return m_coefficients[n]; |
|
|
|
} |
|
|
|
|
|
|
|
/* Return the leading coefficient */ |
|
|
|
inline T leading() const |
|
|
|
{ |
|
|
|
return (*this)[degree()]; |
|
|
|
} |
|
|
|
|
|
|
|
/* Unary plus */ |
|
|
|
polynomial<T> operator +() const |
|
|
|
{ |
|
|
@@ -264,6 +270,30 @@ struct polynomial |
|
|
|
return ret; |
|
|
|
} |
|
|
|
|
|
|
|
/* Divide a polynomial by another one. There is no /= variant because |
|
|
|
* the return value contains both the quotient and the remainder. */ |
|
|
|
tuple<polynomial<T>, polynomial<T>> operator /(polynomial<T> p) const |
|
|
|
{ |
|
|
|
ASSERT(p.degree() >= 0); |
|
|
|
|
|
|
|
tuple<polynomial<T>, polynomial<T>> ret; |
|
|
|
polynomial<T> "ient = ret.m1; |
|
|
|
polynomial<T> &remainder = ret.m2; |
|
|
|
|
|
|
|
remainder = *this / p.leading(); |
|
|
|
p /= p.leading(); |
|
|
|
|
|
|
|
for (int n = remainder.degree() - p.degree(); n >= 0; --n) |
|
|
|
{ |
|
|
|
quotient.set(n, remainder.leading()); |
|
|
|
remainder.m_coefficients.Pop(); |
|
|
|
for (int i = 0; i < p.degree(); ++i) |
|
|
|
remainder.m_coefficients[n + i] -= remainder.leading() * p[i]; |
|
|
|
} |
|
|
|
|
|
|
|
return ret; |
|
|
|
} |
|
|
|
|
|
|
|
private: |
|
|
|
/* Enforce the non-zero leading coefficient rule. */ |
|
|
|
void reduce_degree() |
|
|
|