Region

RegionalOutput

iterator

Macros

Line Code
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149
#ifndef DataFormats_L1Trigger_RegionalOutput_h
#define DataFormats_L1Trigger_RegionalOutput_h

#include "DataFormats/Common/interface/CMS_CLASS_VERSION.h"
#include "DataFormats/Common/interface/RefProd.h"
#include "DataFormats/Common/interface/Ref.h"
#include <vector>

namespace l1t {
  template <typename T>
  class RegionalOutput {
  public:
    typedef typename T::value_type value_type;
    typedef edm::Ref<T> ref;
    typedef edm::RefProd<T> refprod;

    class iterator {
    public:
      typedef typename T::value_type value_type;
      typedef ptrdiff_t difference_type;
      iterator(const RegionalOutput<T>& src, unsigned int idx) : src_(&src), idx_(idx) {}
      iterator(iterator const& it) : src_(it.src_), idx_(it.idx_) {}
      iterator() : src_(nullptr), idx_(0) {}
      iterator& operator++() {
        ++idx_;
        return *this;
      }
      iterator operator++(int) {
        iterator ci = *this;
        ++idx_;
        return ci;
      }
      iterator& operator--() {
        --idx_;
        return *this;
      }
      iterator operator--(int) {
        iterator ci = *this;
        --idx_;
        return ci;
      }
      difference_type operator-(iterator const& o) const { return idx_ - o.idx_; }
      iterator operator+(difference_type n) const { return iterator(src_, idx_ + n); }
      iterator operator-(difference_type n) const { return iterator(src_, idx_ - n); }
      bool operator<(iterator const& o) const { return idx_ < o.idx_; }
      bool operator==(iterator const& ci) const { return idx_ == ci.idx_; }
      bool operator!=(iterator const& ci) const { return idx_ != ci.idx_; }
      value_type const& operator*() const { return src_->objAt(idx_); }
      value_type const* operator->() const { return &src_->objAt(idx_); }
      iterator& operator+=(difference_type d) {
        idx_ += d;
        return *this;
      }
      iterator& operator-=(difference_type d) {
        idx_ -= d;
        return *this;
      }
      value_type const& operator[](difference_type d) const { return src_->objAt(idx_ + d); }
      // interface to get EDM refs & related stuff
      edm::Ref<T> ref() const { return src_->refAt(idx_); }
      edm::ProductID id() const { return src_->id(); }
      unsigned int idx() const { return idx_; }
      unsigned int key() const { return idx_; }

    private:
      const RegionalOutput<T>* src_;
      unsigned int idx_;
    };
    typedef iterator const_iterator;

    class Region {
    public:
      typedef typename T::value_type value_type;
      typedef typename RegionalOutput<T>::iterator iterator;
      typedef typename RegionalOutput<T>::const_iterator const_iterator;

      const value_type& operator[](unsigned int idx) const { return src_->objAt(ibegin_ + idx); }
      const value_type& front() const { return src_->objAt(ibegin_); }
      const value_type& back() const { return src_->objAt(iend_ - 1); }
      iterator begin() const { return iterator(*src_, ibegin_); }
      iterator end() const { return iterator(*src_, iend_); }
      unsigned int size() const { return iend_ - ibegin_; }
      bool empty() const { return (iend_ == ibegin_); }
      // interface to get EDM refs & related stuff
      ref refAt(unsigned int idx) const { return src_->refAt(ibegin_ + idx); }
      edm::ProductID id() const { return src_->id(); }

    private:
      const RegionalOutput<T>* src_;
      unsigned int ibegin_, iend_;
      friend class RegionalOutput<T>;
      Region(const RegionalOutput<T>* src, unsigned int ibegin, unsigned int iend)
          : src_(src), ibegin_(ibegin), iend_(iend) {}
    };

    RegionalOutput() : refprod_(), values_(), regions_(), etas_(), phis_() {}
    RegionalOutput(const edm::RefProd<T>& prod) : refprod_(prod), values_(), regions_(), etas_(), phis_() {}

    void addRegion(const std::vector<int>& indices, const float eta, const float phi) {
      regions_.emplace_back((regions_.empty() ? 0 : regions_.back()) + indices.size());
      values_.insert(values_.end(), indices.begin(), indices.end());
      etas_.push_back(eta);
      phis_.push_back(phi);
    }

    edm::ProductID id() const { return refprod_.id(); }
    unsigned int size() const { return values_.size(); }
    unsigned int nRegions() const { return regions_.size(); }
    bool empty() const { return values_.empty(); }
    void clear() {
      values_.clear();
      regions_.clear();
      etas_.clear();
      phis_.clear();
    }
    void shrink_to_fit() {
      values_.shrink_to_fit();
      regions_.shrink_to_fit();
      etas_.shrink_to_fit();
      phis_.shrink_to_fit();
    }

    const_iterator begin() const { return const_iterator(this, 0); }
    const_iterator end() const { return const_iterator(this, values_.size()); }

    Region region(unsigned int ireg) const {
      if (ireg >= regions_.size())
        throw cms::Exception("Region index out of bounds");
      return Region(this, ireg == 0 ? 0 : regions_[ireg - 1], regions_[ireg]);
    }

    const float eta(unsigned int ireg) const { return etas_[ireg]; }
    const float phi(unsigned int ireg) const { return phis_[ireg]; }

    ref refAt(unsigned int idx) const { return ref(refprod_, values_[idx]); }
    const value_type& objAt(unsigned int idx) const { return (*refprod_)[values_[idx]]; }

    //Used by ROOT storage
    CMS_CLASS_VERSION(3)

  protected:
    refprod refprod_;
    std::vector<unsigned int> values_;   // list of indices to objects in each region, flattened.
    std::vector<unsigned int> regions_;  // for each region, store the index of one-past the last object in values
    std::vector<float> etas_;            // floatEtaCenter of each PFregion
    std::vector<float> phis_;            // floatPhiCenter of each PFregion
  };
}  // namespace l1t
#endif