Polynomial Polynomial::embeddedInto(PolynomialRing const &r2, list<int> const *chosenVariables)const { Polynomial q(r2); if(chosenVariables) { assert(chosenVariables->size()==r2.getNumberOfVariables()); } for(TermMap::const_iterator i=terms.begin();i!=terms.end();i++) { IntegerVector v=i->first.exponent; if(chosenVariables) v=v.subvector(*chosenVariables); else v.resize(r2.getNumberOfVariables()); FieldElement e=i->second; q+=Term(e,Monomial(r2,v)); } if(isMarked()) { IntegerVector m=marked.m.exponent; //AsciiPrinter(Stderr)<<*this<<"\n"; if(chosenVariables) m=m.subvector(*chosenVariables); else m.resize(r2.getNumberOfVariables()); q.mark(Monomial(r2,m)); } // q.marked.m.exponent.resize(r2.getNumberOfVariables()); return q; }
void Polynomial::saturate(int variableNum)//does not compute sugar { if(!terms.empty()) { IntegerVector smallest=terms.begin()->first.exponent; for(TermMap::iterator i=terms.begin();i!=terms.end();i++) smallest=min(smallest,i->first.exponent); if(variableNum!=-1) { for(int j=0;j<smallest.size();j++)if(j!=variableNum)smallest[j]=0; } Polynomial p(theRing); for(TermMap::iterator i=terms.begin();i!=terms.end();i++) p.terms.insert(p.terms.end(),TermMap::value_type(Monomial(theRing,i->first.exponent-smallest),i->second)); terms=p.terms; if(isMarked()) { marked.m.exponent-=smallest; } } }
Polynomial Polynomial::homogenization(PolynomialRing const &newRing, IntegerVector const *w)const //does not compute sugar { int degree; Polynomial ret(newRing); if(w) degree=this->degree(*w); else degree=totalDegree(); IntegerVector m; for(TermMap::const_iterator i=terms.begin();i!=terms.end();i++) { IntegerVector v=i->first.exponent; int d; if(w) d=dot(v,*w); else d=v.sum(); IntegerVector a(v.size()); a.grow(a.size()+1); v.grow(v.size()+1); a[a.size()-1]=degree-d; v+=a; ret+=Term(i->second,Monomial(newRing,v)); if(isMarked())if(marked.m.exponent==i->first.exponent)m=v; } if(isMarked()) { IntegerVector v=m; if(m.size()==newRing.getNumberOfVariables()) { ret.mark(Monomial(newRing,v)); } // assert(m.size()==newRing.getNumberOfVariables()); // ret.mark(Monomial(newRing,m)); } return ret; }
void Polynomial::operator*=(const Monomial &m) { sugar+=m.exponent.sum(); Polynomial p(theRing); for(TermMap::iterator i=terms.begin();i!=terms.end();i++) { FieldElement prod=i->second; p.terms.insert(p.terms.end(),TermMap::value_type(Monomial(theRing,i->first.exponent+m.exponent),prod)); } terms=p.terms; }
void Polynomial::madd(const Term &m, const Polynomial &p) { if(p.terms.empty())return; //added May 7 2005 int sugar2=p.getSugar()+m.m.exponent.sum(); if(sugar2>sugar)sugar=sugar2; TermMap::iterator i=terms.lower_bound(Monomial(theRing,p.terms.begin()->first.exponent+m.m.exponent)); for(TermMap::const_iterator j=p.terms.begin();j!=p.terms.end();j++) { while(i!=terms.end() && TermMapCompare()(i->first,Monomial(theRing,j->first.exponent+m.m.exponent)))i++; if(i==terms.end()) { terms.insert(i,TermMap::value_type(Monomial(theRing,j->first.exponent+m.m.exponent),j->second*m.c)); } else { if(!TermMapCompare()(Monomial(theRing,j->first.exponent+m.m.exponent),i->first)) { // they must be equal FieldElement c=i->second+j->second*m.c; if(c.isZero()) { TermMap::iterator oldI=i; i++; terms.erase(oldI); } else { i->second=c; } } else { terms.insert(i,TermMap::value_type(Monomial(theRing,j->first.exponent+m.m.exponent),j->second*m.c)); } } } }
void Polynomial::changeNumberOfVariables(int n) { PolynomialRing newRing=theRing;//!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!111111111111!!!!!! Polynomial q(newRing); for(TermMap::iterator i=terms.begin();i!=terms.end();i++) { IntegerVector v=i->first.exponent; v.resize(n); FieldElement e=i->second; q+=Term(e,Monomial(theRing,v)); } if(isMarked())marked.m.exponent.resize(n); terms=q.terms; }
Monomial Monomial::operator * (const Monomial& p) const { Monomial ans = Monomial(); for (auto it = _multipliers.cbegin(); it != _multipliers.cend(); ++it) { ans._multipliers.insert(*it); } for (auto it = p._multipliers.cbegin(); it != p._multipliers.cend(); ++it) { if (!ans._multipliers.insert(*it).second) { ans._multipliers.at(it->first) += it->second; } if (ans._multipliers.at(it->first) == 0) { ans._multipliers.erase(it->first); } } return ans; }
Polynomial Polynomial::derivative()const { Polynomial ret(theRing); for(TermMap::const_iterator i=terms.begin();i!=terms.end();i++) { IntegerVector v=i->first.exponent; assert(v.size()==1); if(v[0]!=0) { v[0]--; ret+=Term(i->second*theRing.getField().zHomomorphism(v[0]+1),Monomial(theRing,v)); } } return ret; }
Polynomial Polynomial::deHomogenizationInSameRing()const { Polynomial ret(getRing()); int n=getRing().getNumberOfVariables(); assert(n>0); for(TermMap::const_iterator i=terms.begin();i!=terms.end();i++) { IntegerVector v=i->first.exponent; v[n-1]=0; FieldElement e=i->second; ret+=Term(e,Monomial(theRing,v)); } if(isMarked()) { ret.marked.m.exponent=marked.m.exponent.subvector(0,n-1); ret.isMarkedBool=true; } return ret; }
void Polynomial::operator*=(const Term &t) { sugar+=t.m.exponent.sum(); // faster multiplication Polynomial p(theRing); for(TermMap::iterator i=terms.begin();i!=terms.end();i++) { FieldElement prod=i->second; prod*=t.c; p.terms.insert(p.terms.end(),TermMap::value_type(Monomial(theRing,i->first.exponent+t.m.exponent),prod)); } terms=p.terms; // slow multiplication /* Polynomial p; for(TermMap::iterator i=terms.begin();i!=terms.end();i++) { Term T(i->second,i->first); T*=t; p+=T; } terms=p.terms; */ }
Polynomial::Polynomial(const LinearCombination& linearCombination) : monomials_(), constant_(linearCombination.constant_) { for (const LinearTerm& linearTerm : linearCombination.linearTerms_) { monomials_.push_back(Monomial(linearTerm)); } }
Monomial pow(const Variable& x, int degree) { return Monomial(x, degree); }
Monomial operator * (const Monomial& p, const Variable& x) { return Monomial(x) * p; }
Monomial operator * (const Variable& x, const Variable& y) { return Monomial(x) * Monomial(y); }