CMS 3D CMS Logo

VarProcessor.h

Go to the documentation of this file.
00001 #ifndef PhysicsTools_MVAComputer_VarProcessor_h
00002 #define PhysicsTools_MVAComputer_VarProcessor_h
00003 // -*- C++ -*-
00004 //
00005 // Package:     MVAComputer
00006 // Class  :     VarProcessor
00007 //
00008 
00009 //
00010 // Author:      Christophe Saout <christophe.saout@cern.ch>
00011 // Created:     Sat Apr 24 15:18 CEST 2007
00012 // $Id: VarProcessor.h,v 1.7 2009/03/27 14:33:38 saout Exp $
00013 //
00014 
00015 #include <algorithm>
00016 #include <vector>
00017 
00018 #include "PhysicsTools/MVAComputer/interface/ProcessRegistry.h"
00019 #include "PhysicsTools/MVAComputer/interface/CalibrationFwd.h"
00020 #include "PhysicsTools/MVAComputer/interface/Variable.h"
00021 #include "PhysicsTools/MVAComputer/interface/BitSet.h"
00022 
00023 namespace PhysicsTools {
00024 
00025 // forward declaration
00026 class MVAComputer;
00027 
00037 class VarProcessor :
00038         public ProcessRegistry<VarProcessor,
00039                                Calibration::VarProcessor,
00040                                const MVAComputer>::Factory {
00041     public:
00051         struct Config {
00052                 inline Config() : mask(Variable::FLAG_NONE), origin(0) {}
00053                 inline Config(Variable::Flags mask, unsigned int origin) :
00054                         mask(mask), origin(origin) {}
00055 
00056                 Variable::Flags mask;
00057                 unsigned int    origin;
00058         };
00059 
00060         class ConfigCtx {
00061             public:
00062                 typedef std::vector<Config>             Config_t;
00063 
00064                 typedef Config_t::value_type            value_type;
00065                 typedef Config_t::size_type             size_type;
00066                 typedef Config_t::iterator              iterator;
00067                 typedef Config_t::const_iterator        const_iterator;
00068 
00069                 struct Context { virtual ~Context() {} };
00070 
00071                 ConfigCtx(std::vector<Variable::Flags> flags);
00072                 ~ConfigCtx() { delete ctx; }
00073 
00074                 inline size_type size() const { return configs.size(); }
00075                 inline const_iterator begin() const { return configs.begin(); }
00076                 inline iterator begin() { return configs.begin(); }
00077                 inline const_iterator end() const { return configs.end(); }
00078                 inline iterator end() { return configs.end(); }
00079                 inline void push_back(const Config &config) { configs.push_back(config); }
00080                 inline Config &operator [] (size_type i) { return configs[i]; }
00081 
00082             private:            
00083                 friend class VarProcessor;
00084 
00085                 Config_t        configs;
00086                 VarProcessor    *loop;
00087                 Context         *ctx;
00088         };
00089 
00090         virtual ~VarProcessor();
00091 
00093         void configure(ConfigCtx &config);
00094 
00096         inline void
00097         eval(double *input, int *conf, double *output, int *outConf,
00098              int *loop, unsigned int offset) const
00099         {
00100                 ValueIterator iter(inputVars.iter(), input, conf,
00101                                    output, outConf, loop, offset);
00102                 eval(iter, nInputVars);
00103         }
00104 
00105         enum LoopStatus { kStop, kNext, kReset, kSkip };
00106 
00107         virtual LoopStatus loop(double *output, int *outConf,
00108                                 unsigned int nOutput,
00109                                 unsigned int &nOffset) const
00110         { return kStop; }
00111 
00112     protected:
00118         struct ConfIterator {
00119             public:
00121                 ConfIterator &operator () (Variable::Flags mask)
00122                 {
00123                         config[cur()].mask =
00124                                 (Variable::Flags)(config[cur()].mask & mask);
00125                         return *this;
00126                 }
00127 
00129                 ConfIterator &operator << (Config config_)
00130                 { config.push_back(config_); return *this; }
00131 
00133                 ConfIterator &operator << (Variable::Flags mask)
00134                 { return *this << Config(mask, 0); }
00135 
00137                 ConfIterator &operator << (const ConfIterator &origin)
00138                 { return *this << Config(config[origin.cur()].mask, origin.cur()); }
00139 
00141                 Variable::Flags operator * () const
00142                 { return config[cur()].mask; }
00143 
00145                 inline operator bool() const { return cur; }
00146 
00148                 ConfIterator &operator ++ () { ++cur; return *this; }
00149 
00151                 inline ConfIterator operator ++ (int dummy)
00152                 { ConfIterator orig = *this; operator ++ (); return orig; }
00153 
00154             protected:
00155                 friend class VarProcessor;
00156 
00157                 ConfIterator(BitSet::Iterator cur, ConfigCtx &config) :
00158                         cur(cur), config(config) {}
00159 
00160             private:
00161                 BitSet::Iterator        cur;
00162                 ConfigCtx               &config;
00163         };
00164 
00170         struct ValueIterator {
00171             public:
00173                 inline unsigned int size() const
00174                 { return loop ? (conf[1] - conf[0]) : 1; }
00175 
00177                 inline double *begin() const { return values; }
00178 
00180                 inline double *end() const { return values + size(); }
00181 
00183                 inline bool empty() const { return begin() == end(); }
00184 
00186                 inline double operator * ()
00187                 { return *values; }
00188 
00190                 inline double operator [] (unsigned int idx)
00191                 { return values[idx]; }
00192 
00194                 inline ValueIterator &operator << (double value)
00195                 { *output++ = value; return *this; }
00196 
00198                 inline void operator () ()
00199                 {
00200                         int pos = output - start;
00201                         if (*++outConf > pos)
00202                                 output = start + *outConf;
00203                         else
00204                                 *outConf = pos;
00205                 }
00206 
00208                 inline void operator () (double value)
00209                 { *this << value; (*this)(); }
00210 
00212                 inline operator bool() const { return cur; }
00213 
00215                 ValueIterator &operator ++ ()
00216                 {
00217                         BitSet::size_t orig = cur();
00218                         if (++cur) {
00219                                 unsigned int prev = *conf;
00220                                 conf += cur() - orig; 
00221                                 values += *conf - prev;
00222                                 if (loop && conf >= loop) {
00223                                         values += offset;
00224                                         loop = 0;
00225                                 }
00226                         }
00227                         return *this;
00228                 }
00229 
00231                 inline ValueIterator operator ++ (int dummy)
00232                 { ValueIterator orig = *this; operator ++ (); return orig; }
00233 
00234             protected:
00235                 friend class VarProcessor;
00236 
00237                 ValueIterator(BitSet::Iterator cur, double *values,
00238                               int *conf, double *output, int *outConf,
00239                               int *loop, unsigned int offset) :
00240                         cur(cur), offset(offset), start(values + offset),
00241                         values(values), conf(conf), loop(loop),
00242                         output(output + offset), outConf(outConf)
00243                 {
00244                         this->conf += cur();
00245                         this->values += *this->conf;
00246                         if (loop && this->conf >= loop) {
00247                                 this->values += offset;
00248                                 this->loop = 0;
00249                         }
00250                 }
00251 
00252             private:
00253                 BitSet::Iterator        cur;
00254                 const unsigned int      offset;
00255                 double                  *const start;
00256                 double                  *values;
00257                 const int               *conf;
00258                 const int               *loop;
00259                 double                  *output;
00260                 int                     *outConf;
00261         };
00262 
00263         typedef ProcessRegistry<VarProcessor,
00264                                 Calibration::VarProcessor,
00265                                 const MVAComputer> Registry;
00266 
00267         VarProcessor(const char *name, const Calibration::VarProcessor *calib,
00268                      const MVAComputer *computer);
00269 
00271         virtual void configure(ConfIterator iter, unsigned int n) = 0;
00272 
00274         virtual ConfigCtx::Context *
00275         configureLoop(ConfigCtx::Context *ctx, ConfigCtx::iterator begin,
00276                       ConfigCtx::iterator cur, ConfigCtx::iterator end);
00277 
00279         virtual void eval(ValueIterator iter, unsigned int n) const = 0;
00280 
00281     protected:
00282         const MVAComputer       *computer;
00283 
00284     private:
00286         BitSet                  inputVars;
00287         unsigned int            nInputVars;
00288 };
00289 
00290 } // namespace PhysicsTools
00291 
00292 #endif // PhysicsTools_MVAComputer_VarProcessor_h

Generated on Tue Jun 9 17:41:27 2009 for CMSSW by  doxygen 1.5.4