synaps/mpol/Dual.h

00001 /*********************************************************************
00002 *      This file is part of the source code of the SYNAPS library.
00003 *      Author(s): B. Mourrain, GALAAD, INRIA                 
00004 **********************************************************************/
00005 
00006 #ifndef synaps_mpol_Dual_h
00007 #define synaps_mpol_Dual_h 
00008 
00009 #include <synaps/mpol/MPol.h>
00010 #include <synaps/mpol/AllVariables.h>
00011 
00012 //--------------------------------------------------------------------
00013 __BEGIN_NAMESPACE_SYNAPS
00014 //----------------------------------------------------------------------
00016 
00021 template <class C,
00022           class O=DegLex,
00023           class R=std::list<Monom<C,dynamicexp<int> > > >
00024 struct Dual: public MPol<C,O,R> {
00025 
00026   shared_object<R>  data;
00027   R &       rep()       {return (*data);}
00028   const R & rep() const {return (*data);}
00029 
00030   // Types
00031   typedef typename R::value_type             monom_t;
00032   typedef C                                  coeff_t;
00033   typedef O                                  order_t;
00034   typedef typename R::iterator               iterator;
00035   typedef typename R::const_iterator         const_iterator;
00036   typedef typename R::reverse_iterator       reverse_iterator;
00037   typedef typename R::const_reverse_iterator const_reverse_iterator;
00038   typedef MPol<C,O,R>                        poly_t;
00039   typedef Dual<C,O,R>                        self_t;
00040 
00041   // Constructors
00042   Dual(): poly_t() {}
00043   Dual(const monom_t & m):  poly_t(m) {neg_exponent(*this);}
00044   Dual(const coeff_t & c): poly_t(c) {}
00045   Dual(const int & i): poly_t(i) {}
00046 
00047   Dual(int n, const monom_t * t): poly_t(n,t) {neg_exponent(*this);}
00048 
00049   Dual(const self_t & P): poly_t(P){}
00050   Dual(const char * s, Variables& vars = Variables::default_): 
00051     poly_t(s,vars) {neg_exponent(*this);}
00052   Dual(const char * s, const Variables& vars):
00053     poly_t(s,vars) {neg_exponent(*this);}
00054 
00055   template<class S>
00056   Dual(const VAL<S>& M) {using let::assign; assign(*this,M.rep());}
00057 
00058 
00059   template<class Q>
00060   Dual(const Dual<C,Q,R>& p) : poly_t(p) {}
00061   
00062   // Destructor
00063   // no dynamic allocation at this level.
00064 
00065   //  static Variable var;
00066 
00067   // Assignment operators
00068   self_t & operator =(const self_t & x)  
00069   { 
00070     this->MPol<C,O,R>::operator=(x); return *this;
00071   }
00072   self_t & operator =(const coeff_t & c) {*this=self_t(c); return *this;}
00073   self_t & operator =(int n)             {*this=self_t(n); return *this;}
00074   self_t & operator =(const monom_t & m) {*this=self_t(m); return *this;}
00075   template<class S>
00076   self_t & operator =(const VAL<S> & M)  {assign(*this,M.rep());return *this;}
00077 
00078   C operator()(const poly_t& p);
00079 
00080 };
00081 
00082 template<class C, class O, class R>
00083 void neg_exponent(Dual<C,O,R>& p)
00084 {
00085   typedef typename Dual<C,O,R>::iterator iterator;
00086   for(iterator it=p.begin();it != p.end();it++)
00087     {
00088       for(unsigned j=0;j<(it->nvars()+1);j++)
00089         {
00090           it->setexpt(j,-(*it)[j]);
00091         }
00092     }
00093 }
00094 //--------------------------------------------------------------------
00099 template<class C, class O, class R>
00100 C Dual<C,O,R>::operator()(const MPol<C,O,R>& p)
00101 {
00102   MPol<C,O,R> t= ((MPol<C,O,R>)(*this))*p;
00103   typedef typename MPol<C,O,R>::reverse_iterator iterator;
00104   iterator it;
00105   for(it=t.rbegin(); it != t.rend();it++)
00106     {
00107       bool nul=true;
00108       for(unsigned j=0;j<(it->nvars()+1) && nul;j++)  
00109         {
00110           if((*it)[j]!=0) nul=false;
00111         }
00112       if(nul) return it->coeff();
00113     }
00114   return C(0);
00115 }
00116 //--------------------------------------------------------------------
00122 template<class C, class O, class R>
00123 Dual<C,O,R> operator*(const MPol<C,O,R>& p, const Dual<C,O,R>& l)
00124 {
00125   MPol<C,O,R> t= p* (MPol<C,O,R>)l;
00126   Dual<C,O,R> res;
00127   typedef typename Dual<C,O,R>::const_iterator iterator;
00128   for(iterator it=t.begin();it != t.end();it++)
00129     {
00130       bool neg=true;
00131       for(unsigned j=0;j<(it->nvars()+1) && neg;j++)  
00132         {
00133           if((*it)[j]>0) neg=false;
00134         }
00135       if(neg) res+=(*it);
00136     }
00137   return res;
00138 }
00139 //--------------------------------------------------------------------
00144 template<class C, class O, class R>
00145 MPol<C,O,R> operator*(const Dual<C,O,R>& l, const MPol<C,O,R>& p)
00146 {
00147   MPol<C,O,R> t= ((MPol<C,O,R>)l)*p;
00148   MPol<C,O,R> res;
00149   typedef typename Dual<C,O,R>::const_iterator iterator;
00150   for(iterator it=t.begin();it != t.end();it++)
00151     {
00152       bool pos=true;
00153       for(unsigned j=0;j<(it->nvars()+1) && pos;j++)  
00154         {
00155           if((*it)[j]<0) pos=false;
00156         }
00157       if(pos) res+=(*it);
00158     }
00159   return res;
00160 }
00161 //--------------------------------------------------------------------
00162 namespace MONOMIAL
00163 {
00164   template <class R> inline
00165   std::ostream & print_pp (std::ostream & os, const R & m, const AllVariables<'d'>& V)
00166   { 
00167     bool first=true;
00168     for (typename R::size_type i = 0; i < m.rep().size(); ++i)
00169       {
00170         if (m[i] !=0)
00171           {
00172             if(first)
00173               first =false;
00174             else
00175               os<<'*';
00176             os << V[i];
00177             if (m[i] != -1)
00178               os << '^' <<(-m[i]);
00179           }
00180       }
00181     return os;
00182   }
00183 }
00184 //--------------------------------------------------------------------
00186 
00189 template <class C, class O, class R>
00190 std::ostream & operator<< (std::ostream & os, const Dual<C,O,R> & P)
00191 {
00192   MPOLDST::print(os,P, AllVariables<'d'>()); return os;
00193 }
00194 
00195 __END_NAMESPACE_SYNAPS
00196 //======================================================================
00197 
00198 #endif // synaps_mpol_Dual_h
00199 

SYNAPS DOCUMENTATION
logo