eoGenOp.h

00001 // -*- mode: c++; c-indent-level: 4; c++-member-init-indent: 8; comment-column: 35; -*-
00002 
00003 //-----------------------------------------------------------------------------
00004 // eoGenOp.h
00005 // (c) Maarten Keijzer and Marc Schoenauer, 2001
00006 /*
00007     This library is free software; you can redistribute it and/or
00008     modify it under the terms of the GNU Lesser General Public
00009     License as published by the Free Software Foundation; either
00010     version 2 of the License, or (at your option) any later version.
00011 
00012     This library is distributed in the hope that it will be useful,
00013     but WITHOUT ANY WARRANTY; without even the implied warranty of
00014     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00015     Lesser General Public License for more details.
00016 
00017     You should have received a copy of the GNU Lesser General Public
00018     License along with this library; if not, write to the Free Software
00019     Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
00020 
00021     Contact: mak@dhi.dk
00022              Marc.Schoenauer@polytechnique.fr
00023  */
00024 //-----------------------------------------------------------------------------
00025 
00026 #ifndef _eoGenOp_H
00027 #define _eoGenOp_H
00028 
00029 #include <eoOp.h>
00030 #include <eoPopulator.h>
00031 #include <eoFunctorStore.h>
00032 #include <assert.h>
00033 
00044 
00056 template <class EOT>
00057 class eoGenOp : public eoOp<EOT>, public eoUF<eoPopulator<EOT> &, void>
00058 {
00059   public :
00061   eoGenOp(): eoOp<EOT>( eoOp<EOT>::general ) {}
00062 
00066   virtual unsigned max_production(void) = 0;
00067 
00068   virtual std::string className() const = 0;
00069     void operator()(eoPopulator<EOT>& _pop)
00070     {
00071     _pop.reserve(max_production());
00072       apply(_pop);
00073     }
00074 
00075 
00076   protected :
00079     virtual void apply(eoPopulator<EOT>& _pop) = 0;
00080 };
00081 
00082 
00084 template <class EOT>
00085 class eoMonGenOp : public eoGenOp<EOT>
00086 {
00087    public:
00088     eoMonGenOp(eoMonOp<EOT>& _op) : op(_op) {}
00089 
00090     unsigned max_production(void) { return 1; }
00091 
00092     void apply(eoPopulator<EOT>& _it)
00093     {
00094       if (op(*_it))
00095         (*_it).invalidate();  // look how simple
00096 
00097     }
00098   virtual std::string className() const {return op.className();}
00099    private :
00100     eoMonOp<EOT>& op;
00101 };
00102 
00106 template <class EOT>
00107 class eoBinGenOp : public eoGenOp<EOT>
00108 {
00109    public:
00110     eoBinGenOp(eoBinOp<EOT>& _op) : op(_op) {}
00111 
00112     unsigned max_production(void) { return 1; } 
00113 
00117     void apply(eoPopulator<EOT>& _pop)
00118     {
00119       EOT& a = *_pop;
00120       const EOT& b = _pop.select();
00121 
00122       if (op(a, b))
00123         a.invalidate();
00124     }
00125   virtual std::string className() const {return op.className();}
00126 
00127    private :
00128     eoBinOp<EOT>& op;
00129 };
00130 
00132 template <class EOT>
00133 class eoSelBinGenOp : public eoGenOp<EOT>
00134 {
00135    public:
00136     eoSelBinGenOp(eoBinOp<EOT>& _op, eoSelectOne<EOT>& _sel) :
00137       op(_op), sel(_sel) {}
00138 
00139     unsigned max_production(void) { return 1; }
00140 
00141     void apply(eoPopulator<EOT>& _pop)
00142     { // _pop.source() gets the original population, an eoVecOp can make use of this as well
00143       if (op(*_pop, sel(_pop.source())))
00144         (*_pop).invalidate();
00145     }
00146   virtual std::string className() const {return op.className();}
00147 
00148    private :
00149     eoBinOp<EOT>& op;
00150     eoSelectOne<EOT>& sel;
00151 };
00152 
00153 
00156 template <class EOT>
00157 class eoQuadGenOp : public eoGenOp<EOT>
00158 {
00159    public:
00160     eoQuadGenOp(eoQuadOp<EOT>& _op) : op(_op) {}
00161 
00162     unsigned max_production(void) { return 2; }
00163 
00164     void apply(eoPopulator<EOT>& _pop)
00165     {
00166       EOT& a = *_pop;
00167       EOT& b = *++_pop; 
00168       
00169       
00170       if(op(a, b))
00171       {
00172         a.invalidate();
00173         b.invalidate();
00174       }
00175 
00176    }
00177   virtual std::string className() const {return op.className();}
00178 
00179    private :
00180     eoQuadOp<EOT>& op;
00181 };
00182 
00207     template <class EOT>
00208     eoGenOp<EOT>& wrap_op(eoOp<EOT>& _op, eoFunctorStore& _store)
00209     {
00210       switch(_op.getType())
00211       {
00212         case eoOp<EOT>::unary     : return _store.storeFunctor(new eoMonGenOp<EOT>(static_cast<eoMonOp<EOT>&>(_op)));
00213         case eoOp<EOT>::binary    : return _store.storeFunctor(new eoBinGenOp<EOT>(static_cast<eoBinOp<EOT>&>(_op)));
00214         case eoOp<EOT>::quadratic : return _store.storeFunctor(new eoQuadGenOp<EOT>(static_cast<eoQuadOp<EOT>&>(_op)));
00215         case eoOp<EOT>::general   : return static_cast<eoGenOp<EOT>&>(_op);
00216       }
00217 
00218       assert(false);
00219       return static_cast<eoGenOp<EOT>&>(_op);
00220     }
00221 
00222 #endif
00223 

Generated on Thu Oct 19 05:06:35 2006 for EO by  doxygen 1.3.9.1