BWAPI
|
00001 /**************************************************************************** 00002 * Core Library Version 1.7, August 2004 00003 * Copyright (c) 1995-2004 Exact Computation Project 00004 * All rights reserved. 00005 * 00006 * This file is part of CORE (http://cs.nyu.edu/exact/core/); you may 00007 * redistribute it under the terms of the Q Public License version 1.0. 00008 * See the file LICENSE.QPL distributed with CORE. 00009 * 00010 * Licensees holding a valid commercial license may use this file in 00011 * accordance with the commercial license agreement provided with the 00012 * software. 00013 * 00014 * This file is provided AS IS with NO WARRANTY OF ANY KIND, INCLUDING THE 00015 * WARRANTY OF DESIGN, MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. 00016 * 00017 * 00018 * File: Poly.h 00019 * 00020 * Description: simple polynomial class 00021 * 00022 * REPRESENTATION: 00023 * --Each polynomial has a nominal "degree" (this 00024 * is an upper bound on the true degree, which 00025 * is determined by the first non-zero coefficient). 00026 * --coefficients are parametrized by some number type "NT". 00027 * --coefficients are stored in the "coeff" array of 00028 * length "degree + 1". 00029 * CONVENTION: coeff[i] is the coefficient of X^i. So, a 00030 * coefficient list begins with the constant term. 00031 * --IMPORTANT CONVENTION: 00032 * the zero polynomial has degree -1 00033 * while nonzero constant polynomials have degree 0. 00034 * 00035 * FUNCTIONALITY: 00036 * --Polynomial Ring Operations (+,-,*) 00037 * --Power 00038 * --Evaluation 00039 * --Differentiation 00040 * --Remainder, Quotient 00041 * --GCD 00042 * --Resultant, Discriminant (planned) 00043 * --Polynomial Composition (planned) 00044 * --file I/O (planned) 00045 * 00046 * Author: Chee Yap 00047 * Date: May 28, 2002 00048 * 00049 * WWW URL: http://cs.nyu.edu/exact/ 00050 * Email: exact@cs.nyu.edu 00051 * 00052 * $URL: svn+ssh://scm.gforge.inria.fr/svn/cgal/branches/CGAL-3.5-branch/Core/include/CGAL/CORE/poly/Poly.h $ 00053 * $Id: Poly.h 37060 2007-03-13 18:10:39Z reichel $ 00054 ***************************************************************************/ 00055 00056 #ifndef CORE_POLY_H 00057 #define CORE_POLY_H 00058 00059 #include <CGAL/CORE/BigFloat.h> 00060 #include <CGAL/CORE/Promote.h> 00061 #include <vector> 00062 00063 CORE_BEGIN_NAMESPACE 00064 using namespace std; 00065 class Expr; 00066 // ================================================== 00067 // Typedefs 00068 // ================================================== 00069 00070 //typedef std::vector<Expr> VecExpr; 00071 //typedef std::pair<Expr, Expr> Interval; 00072 //typedef std::vector<Interval> VecInterval; 00073 typedef std::pair<BigFloat, BigFloat> BFInterval; 00074 // NOTE: an error condition is indicated by 00075 // the special interval (1, 0) 00076 typedef std::vector<BFInterval> BFVecInterval; 00077 00078 00079 // ================================================== 00080 // Polynomial Class 00081 // ================================================== 00082 00083 template <class NT> 00084 class Polynomial { 00085 private: 00086 //The following are used in the constructor from strings. 00087 //For more details see the related constructor. 00088 00089 public: 00090 typedef std::vector<NT> VecNT; 00091 typedef NT coeffType; 00092 00093 int degree; // This is the nominal degree (an upper bound 00094 // on the true degree) 00095 NT * coeff; // coeff is an array of size degree+1; 00096 // This remark holds even when degree = -1. 00097 // Notes: 00098 // (1) coeff[i] is the coefficient of x^i 00099 // (2) The Zero Polynomial has degree -1 00100 // (3) Nonzero Constant Polynomials has degree 0 00101 00102 // STATIC MEMBERS 00103 // static NT ccc_; // THIS IS A TEMPORARY HACK 00104 static int COEFF_PER_LINE; // pretty print parameters 00105 static const char * INDENT_SPACE; // pretty print parameters 00106 00107 static const Polynomial<NT> & polyZero(); 00108 static const Polynomial<NT> & polyUnity(); 00109 static Polynomial polyWilkinson; // a sample polynomial 00110 static int NT_TYPE; // NT_TYPE = 1 if NT is integer type (int,long,BigInt) 00111 // NT_TYPE = 2 if NT is BigFloat 00112 // NT_TYPE = 3 if NT is BigRat 00113 // NT_TYPE = 4 if NT is Expr 00114 // Hack? NT_TYPE is needed for root bounds, etc. 00115 00116 // Constructors: 00117 Polynomial(void); // the Zero Polynomial 00118 Polynomial(int n); // construct the Unit Polynomial of nominal deg n>=0 00119 Polynomial(int n, const NT * coef); 00120 Polynomial(const Polynomial &); 00121 Polynomial(const VecNT &); 00122 Polynomial(int n, const char* s[]); 00123 Polynomial(const string & s, char myX='x'); 00124 Polynomial(const char* s, char myX='x'); 00125 ~Polynomial(); 00126 00127 private: 00128 void constructX(int n, Polynomial<NT>& P); 00129 void constructFromString(string & s, char myX='x'); 00130 int getnumber(const char* c, int i, unsigned int len, Polynomial<NT> & P); 00131 bool isint(char c); 00132 int getint(const char* c, int i, unsigned int len, int & n); 00133 int matchparen(const char* cstr, int start); 00134 int getbasicterm(string & s, Polynomial<NT> & P); 00135 int getterm(string & s, Polynomial<NT> & P); 00136 00137 00138 public: 00139 //Returns a Polynomial corresponding to s, which is supposed to 00140 //contain as place-holders the chars 'x' and 'y'. 00141 Polynomial<NT> getpoly(string & s); 00142 00143 // Assignment: 00144 Polynomial & operator=(const Polynomial&); 00145 00146 // Expand and Contract 00147 // -- they are semi-inverses: i.e., Contract(expand(p))=p 00148 int expand(int n); // Change the current degree to n 00149 // Helper function for polynomial arithmetic 00150 int contract(); // get rid of leading zeros 00151 00152 // Polynomial arithmetic (these are all self-modifying): 00153 Polynomial & operator+=(const Polynomial&); // += 00154 Polynomial & operator-=(const Polynomial&); // -= 00155 Polynomial & operator*=(const Polynomial&); // *= 00156 Polynomial & operator-(); // unary minus 00157 Polynomial & power (unsigned int n) ; // power (*this is changed!) 00158 00159 Polynomial & mulScalar (const NT & c); // return (*this) * (c) 00160 Polynomial & mulXpower(int i); // If i >= 0, then this is equivalent 00161 // to multiplying by X^i. 00162 // If i < 0 to dividing by X^i 00163 Polynomial pseudoRemainder (const Polynomial& B, NT& C); // C = return value 00164 Polynomial pseudoRemainder (const Polynomial& B); // no C version 00165 // The pseudo quotient of (*this) mod B 00166 // is returned, but (*this) is transformed 00167 // into the pseudo remainder. If the argument C is provided, 00168 // Then C*(*this) = B*pseudo-quotient + pseudo-remainder. 00169 Polynomial & negPseudoRemainder (const Polynomial& B); // negative remainder 00170 Polynomial reduceStep (const Polynomial& B ); //helper for pseudoRemainder 00171 // One step of pseudo remainder 00172 // What is returned is a special polynomial C + X*M (not "C+M") 00173 // telling us the initial constant C and 00174 // the quotient M of C*(THIS) divided by p. 00175 Polynomial testReduceStep(const Polynomial& A, const Polynomial& B); //helper 00176 00177 // Get functions 00178 int getDegree() const; // nominal degree 00179 int getTrueDegree() const; // true degree 00180 NT getCoeffi(int i) const; 00181 const NT & getLeadCoeff() const; // get TRUE leading coefficient 00182 const NT & getTailCoeff() const; // get last non-zero coefficient 00183 NT** getCoeffs() ; // get all coefficients 00184 const NT& getCoeff(int i) const; // Get single coefficient of X^i 00185 // NULL pointer if invalid i 00186 // Set functions 00187 bool setCoeff(int i, const NT & cc); // Make cc the coefficient of X^i 00188 // Return FALSE if invalid i 00189 // !! User's responsibility to 00190 // delete the old coefficient if 00191 // necessary !! 00192 // Helper Functions: 00194 void reverse(); 00197 Polynomial & negate(); 00201 int makeTailCoeffNonzero(); 00202 00203 // Evaluation Functions: 00206 BigFloat evalApprox(const BigFloat& f, 00207 const extLong& r=defRelPrec, const extLong& a=defAbsPrec) const; 00212 BigFloat evalExactSign(const BigFloat& val, const extLong& oldMSB=54) const; 00217 template <class T> 00218 MAX_TYPE(NT, T) eval(const T&) const; 00219 00220 // Bounds 00221 BigFloat CauchyUpperBound() const; // Cauchy Root Upper Bound 00222 BigFloat CauchyLowerBound() const; // Cauchy Root Lower Bound 00223 BigInt CauchyBound() const; // Cauchy Root Bound from Erich Kaltofen 00224 BigInt UpperBound() const; // Another Cauchy Root Bound; an improvement over 00225 //Erich Kaltofen 00226 BigFloat sepBound() const; // separation bound (multiple roots allowed) 00227 BigFloat height() const; // height return type BigFloat 00228 BigFloat length() const; // length return type BigFloat 00229 00230 // Differentiation 00231 Polynomial & differentiate() ; // self-differentiation 00232 Polynomial & differentiate(int n) ; // multi self-differentiation 00233 00234 // Reductions of polynomials (NT must have gcd function) 00235 Polynomial sqFreePart(); // Square free part of P is P/gcd(P,P'). Return gcd 00236 Polynomial & primPart(); // Primitive Part of *this (which is changed) 00237 00239 // Resultant and discriminant 00240 // NT & resultant() ; // resultant 00241 // NT & discriminant() ; // discriminant 00242 00243 // Composition of Polynomials: 00244 // NOT yet implemented 00245 00247 // Polynomial Dump 00248 void dump(std::ofstream & ofs, std::string msg="", 00249 std::string com="# ", std::string com2="# ") const; // dump to file 00250 void dump(std::string msg="", std::string com="# ", 00251 std::string com2="# ") const; // dump to cout 00252 void filedump(std::ostream & os, std::string msg="", std::string com="# ", 00253 std::string com2="# ") const; // dump workhorse (called by dump()) 00254 void mapleDump() const; // dump of maple code for Polynomial 00255 00256 }; //Polynomial Class 00257 00258 // template < class NT > 00259 // NT Polynomial<NT>::ccc_; 00260 00261 // ================================================== 00262 // Static Constants 00263 // Does this belong here? 00264 // ================================================== 00265 00266 template < class NT > 00267 CORE_INLINE 00268 const Polynomial<NT> & Polynomial<NT>::polyZero() { 00269 static Polynomial<NT> zeroP; 00270 return zeroP; 00271 } 00272 00273 template < class NT > 00274 CORE_INLINE 00275 const Polynomial<NT> & Polynomial<NT>::polyUnity() { 00276 static NT c[] = {1}; 00277 static Polynomial<NT> unityP(0, c); 00278 return unityP; 00279 } 00280 00281 // ================================================== 00282 // Useful functions for Polynomial class 00283 // ================================================== 00284 00285 // polynomial arithmetic: 00286 template < class NT > 00287 Polynomial<NT> operator+(const Polynomial<NT>&, const Polynomial<NT>&);// + 00288 template < class NT > 00289 Polynomial<NT> operator-(const Polynomial<NT>&, const Polynomial<NT>&);// - 00290 template < class NT > 00291 Polynomial<NT> operator*(const Polynomial<NT>&, const Polynomial<NT>&);// * 00292 template < class NT > 00293 Polynomial<NT> power(const Polynomial<NT>&, int n); // power 00294 template < class NT > 00295 Polynomial<NT> differentiate(const Polynomial<NT>&); // differentiate 00296 template < class NT > 00297 Polynomial<NT> differentiate(const Polynomial<NT>&, int n); // multi-differ. 00298 //Content of a Polynomial 00299 template < class NT > 00300 NT content(const Polynomial<NT>& p); 00301 00302 template <class NT> 00303 bool isDivisible(Polynomial<NT> p, Polynomial<NT> q); 00304 00305 // GCD of two polynomials 00306 template < class NT > 00307 Polynomial<NT> gcd(const Polynomial<NT>& p, const Polynomial<NT>& q); 00308 00309 //Resultant of two polynomials 00310 template < class NT > 00311 NT res( Polynomial<NT> p, Polynomial<NT> q); 00312 00313 //Principal Subresultant Coefficient (psc) of two polynomials 00314 template < class NT > 00315 NT psc(int i, Polynomial<NT> p, Polynomial<NT> q); 00316 00317 //Returns the polynomial which contains only the real roots 00318 //of P which have multiplicity d 00319 template < class NT > 00320 Polynomial<NT> factorI(Polynomial<NT> p, int d); 00321 00322 // comparisons 00323 template < class NT > 00324 bool operator==(const Polynomial<NT>&, const Polynomial<NT>&); // == 00325 template < class NT > 00326 bool operator!=(const Polynomial<NT>&, const Polynomial<NT>&); // != 00327 template < class NT > 00328 bool zeroP(const Polynomial <NT>&); // =Zero Poly? 00329 template < class NT > 00330 bool unitP(const Polynomial <NT>&); // =Unit Poly? 00331 00332 // stream i/o 00333 template < class NT > 00334 std::ostream& operator<<(std::ostream&, const Polynomial<NT>&); 00335 template < class NT > 00336 std::istream& operator>>(std::istream&, Polynomial<NT>&); 00337 00338 // ================================================== 00339 // Inline Functions 00340 // ================================================== 00341 00342 // friend polynomial arithmetic: 00343 template < class NT > 00344 CORE_INLINE 00345 Polynomial<NT> operator+(const Polynomial<NT>& p1, 00346 const Polynomial<NT>& p2) { // + 00347 return Polynomial<NT>(p1) += p2; 00348 } 00349 template < class NT > 00350 CORE_INLINE 00351 Polynomial<NT> operator-(const Polynomial<NT>& p1, 00352 const Polynomial<NT>& p2) { // - 00353 return Polynomial<NT>(p1) -= p2; 00354 } 00355 template < class NT > 00356 CORE_INLINE 00357 Polynomial<NT> operator*(const Polynomial<NT>& p1, 00358 const Polynomial<NT>& p2) { // * 00359 return Polynomial<NT> (p1) *= p2; 00360 } 00361 template < class NT > 00362 CORE_INLINE 00363 Polynomial<NT> power(const Polynomial<NT>& p, int n) { // power 00364 return Polynomial<NT>(p).power(n); 00365 } 00366 00367 // equal to zero poly? 00368 template < class NT > 00369 CORE_INLINE 00370 bool zeroP(const Polynomial <NT>& p) { // =Zero Poly? 00371 return (p.getTrueDegree()== -1); 00372 } 00373 template < class NT > 00374 CORE_INLINE 00375 bool unitP(const Polynomial <NT>& p) { // =Unit Poly? 00376 int d = p.getTrueDegree(); 00377 return ((d == 0) && p.coeff[0]==1 ); 00378 } 00379 00380 // get functions 00381 template < class NT > 00382 CORE_INLINE 00383 int Polynomial<NT>::getDegree() const { 00384 return degree; 00385 } 00386 // get TRUE leading coefficient 00387 template < class NT > 00388 CORE_INLINE 00389 const NT & Polynomial<NT>::getLeadCoeff() const { 00390 return getCoeff(getTrueDegree()); 00391 } 00392 00393 // get last non-zero coefficient 00394 template < class NT > 00395 CORE_INLINE 00396 const NT & Polynomial<NT>::getTailCoeff() const { 00397 for (int i = 0; i<= getTrueDegree(); i++) 00398 if (coeff[i] != 0) 00399 return coeff[i]; 00400 // This ought to be an error (user should check this) : 00401 NT * zero = new NT(0); 00402 return *zero; 00403 } 00404 00405 template < class NT > 00406 CORE_INLINE 00407 NT** Polynomial<NT>::getCoeffs() { 00408 return &coeff; 00409 } 00410 template < class NT > 00411 CORE_INLINE 00412 const NT& Polynomial<NT>::getCoeff(int i) const { 00413 //if (i > degree) return NULL; 00414 assert(i <= degree); 00415 return coeff[i]; 00416 } 00417 // set functions 00418 template < class NT > 00419 CORE_INLINE 00420 bool Polynomial<NT>::setCoeff(int i, const NT & cc) { 00421 if ((i<0) || (i > degree)) 00422 return false; 00423 coeff[i] = cc; 00424 return true; 00425 } 00426 00427 // IMPLEMENTATIONS ARE FOUND IN 00428 //#include <CGAL/CORE/poly/Poly.tcc> 00429 // 00430 // We include this file from CORE/Expr.h, AFTER the definition 00431 // of class Expr, because otherwise VC++.net2003 can'y compile Expr.cpp 00432 00433 CORE_END_NAMESPACE 00434 #endif