Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2026-08-17 08:46:50

0001 // Copyright 2024 Ruggero Turra, Hans Dembinski
0002 //
0003 // Distributed under the Boost Software License, version 1.0.
0004 // (See accompanying file LICENSE_1_0.txt
0005 // or copy at http://www.boost.org/LICENSE_1_0.txt)
0006 
0007 #ifndef BOOST_HISTOGRAM_ACCUMULATORS_COLLECTOR_HPP
0008 #define BOOST_HISTOGRAM_ACCUMULATORS_COLLECTOR_HPP
0009 
0010 #include <algorithm> // for std::equal
0011 #include <boost/core/nvp.hpp>
0012 #include <boost/histogram/detail/detect.hpp>
0013 #include <boost/histogram/fwd.hpp> // for collector<>
0014 #include <initializer_list>
0015 #include <type_traits>
0016 
0017 namespace boost {
0018 namespace histogram {
0019 namespace accumulators {
0020 
0021 /** Collects samples.
0022 
0023   Input samples are stored in an internal container for later retrival, which stores the
0024   values consecutively in memory. The interface is designed to work with std::vector and
0025   other containers which implement the same API.
0026 
0027   Warning: The memory of the accumulator is unbounded.
0028 */
0029 template <class ContainerType>
0030 class collector {
0031 public:
0032   using container_type = ContainerType;
0033   using value_type = typename container_type::value_type;
0034   using allocator_type = typename container_type::allocator_type;
0035   using const_reference = typename container_type::const_reference;
0036   using iterator = typename container_type::iterator;
0037   using const_iterator = typename container_type::const_iterator;
0038   using size_type = typename container_type::size_type;
0039   using const_pointer = typename container_type::const_pointer;
0040 
0041   // make template only match if forwarding args to container is valid
0042   template <typename... Args, class = decltype(container_type(std::declval<Args>()...))>
0043   explicit collector(Args&&... args) : container_(std::forward<Args>(args)...) {}
0044 
0045   // make template only match if forwarding args to container is valid
0046   template <class T, typename... Args, class = decltype(container_type(std::initializer_list<T>(),std::declval<Args>()...))>
0047   explicit collector(std::initializer_list<T> list, Args&&... args)
0048       : container_(list, std::forward<Args>(args)...) {}
0049 
0050   /// Append sample x.
0051   void operator()(const_reference x) { container_.push_back(x); }
0052 
0053   /// Append samples from another collector.
0054   template <class C>
0055   collector& operator+=(const collector<C>& rhs) {
0056     container_.reserve(size() + rhs.size());
0057     container_.insert(end(), rhs.begin(), rhs.end());
0058     return *this;
0059   }
0060 
0061   /// Return true if collections are equal.
0062   ///
0063   /// Two collections are equal if they have the same number of elements
0064   /// which all compare equal.
0065   template <class Iterable, class = detail::is_iterable<Iterable>>
0066   bool operator==(const Iterable& rhs) const noexcept {
0067     return std::equal(begin(), end(), rhs.begin(), rhs.end());
0068   }
0069 
0070   /// Return true if collections are not equal.
0071   template <class Iterable, class = detail::is_iterable<Iterable>>
0072   bool operator!=(const Iterable& rhs) const noexcept {
0073     return !operator==(rhs);
0074   }
0075 
0076   /// Return number of samples.
0077   size_type size() const noexcept { return container_.size(); }
0078 
0079   /// Return number of samples (alias for size()).
0080   size_type count() const noexcept { return container_.size(); }
0081 
0082   /// Return readonly iterator to start of collection.
0083   const const_iterator begin() const noexcept { return container_.begin(); }
0084 
0085   /// Return readonly iterator to end of collection.
0086   const const_iterator end() const noexcept { return container_.end(); }
0087 
0088   /// Return const reference to value at index.
0089   const_reference operator[](size_type idx) const noexcept { return container_[idx]; }
0090 
0091   /// Return pointer to internal memory.
0092   const_pointer data() const noexcept { return container_.data(); }
0093 
0094   allocator_type get_allocator() const { return container_.get_allocator(); }
0095 
0096   template <class Archive>
0097   void serialize(Archive& ar, unsigned version) {
0098     (void)version;
0099     ar& make_nvp("container", container_);
0100   }
0101 
0102 private:
0103   container_type container_;
0104 };
0105 
0106 } // namespace accumulators
0107 } // namespace histogram
0108 } // namespace boost
0109 
0110 #endif