Back to home page

Project CMSSW displayed by LXR

 
 

    


File indexing completed on 2024-04-06 12:03:51

0001 #ifndef DataFormats_Common_FwdPtr_h
0002 #define DataFormats_Common_FwdPtr_h
0003 // -*- C++ -*-
0004 //
0005 // Package:     Common
0006 // Class  :     FwdPtr
0007 //
0008 /**\class edm::FwdPtr FwdPtr.h DataFormats/Common/interface/FwdPtr.h
0009 
0010  Description: Persistent 'pointer' to an item in a collection where the collection is in the edm::Event
0011 
0012  Usage:
0013     <usage>
0014 
0015 */
0016 //
0017 // Original Author:  Salvatore Rappoccio
0018 //         Created:  Fri Feb  5 14:58:49 CST 2010
0019 //
0020 
0021 // user include files
0022 #include "DataFormats/Common/interface/CMS_CLASS_VERSION.h"
0023 #include "DataFormats/Common/interface/EDProductGetter.h"
0024 #include "DataFormats/Common/interface/GetProduct.h"
0025 #include "DataFormats/Common/interface/Handle.h"
0026 #include "DataFormats/Common/interface/OrphanHandle.h"
0027 #include "DataFormats/Common/interface/Ptr.h"
0028 #include "DataFormats/Common/interface/RefCore.h"
0029 #include "DataFormats/Common/interface/TestHandle.h"
0030 #include "DataFormats/Common/interface/traits.h"
0031 
0032 #include "FWCore/Utilities/interface/EDMException.h"
0033 
0034 // system include files
0035 #include <cassert>
0036 
0037 // forward declarations
0038 namespace edm {
0039   template <typename T>
0040   class FwdPtr {
0041     friend class FwdPtrVectorBase;
0042 
0043   public:
0044     typedef unsigned long key_type;
0045     typedef T value_type;
0046 
0047     // General purpose constructor from two Ptrs.
0048     template <typename C>
0049     FwdPtr(const Ptr<C>& f, const Ptr<C>& b) : ptr_(f), backPtr_(b) {
0050       assert(f.isNull() == b.isNull());
0051     }
0052 
0053     FwdPtr() : ptr_(), backPtr_() {}
0054 
0055     /*     template<typename U> */
0056     /*     FwdPtr(FwdPtr<U> const& iOther, typename boost::enable_if_c<boost::is_base_of<T, U>::value>::type * t = 0): */
0057     /*     ptr_(iOther.ptr_, t), backPtr_(iOther.backPtr_,t) */
0058     /*     { */
0059     /*     } */
0060 
0061     /*     template<typename U> */
0062     /*     explicit */
0063     /*     FwdPtr(FwdPtr<U> const& iOther, typename boost::enable_if_c<boost::is_base_of<U, T>::value>::type * t = 0): */
0064     /*     ptr_(iOther.ptr_,t), backPtr_(iOther.backPtr_,t){} */
0065 
0066     /// Destructor
0067     ~FwdPtr() {}
0068 
0069     /// Dereference operator
0070     T const& operator*() const { return ptr_.isAvailable() ? ptr_.operator*() : backPtr_.operator*(); }
0071 
0072     /// Member dereference operator
0073     T const* operator->() const { return ptr_.isAvailable() ? ptr_.operator->() : backPtr_.operator->(); }
0074 
0075     /// Returns C++ pointer to the item
0076     T const* get() const { return ptr_.isAvailable() ? ptr_.get() : backPtr_.get(); }
0077 
0078     /// Checks for null
0079     bool isNull() const { return !isNonnull(); }
0080 
0081     /// Checks for non-null
0082     //bool isNonnull() const {return id().isValid(); }
0083     bool isNonnull() const { return ptr_.isNonnull() || backPtr_.isNonnull(); }
0084     /// Checks for null
0085     bool operator!() const { return isNull(); }
0086 
0087     /// Checks if collection is in memory or available
0088     /// in the event. No type checking is done.
0089     bool isAvailable() const { return ptr_.isAvailable() || backPtr_.isAvailable(); }
0090 
0091     /// Checks if this FwdPtr is transient (i.e. not persistable).
0092     bool isTransient() const { return ptr_.isTransient(); }
0093 
0094     /// Accessor for product ID.
0095     ProductID id() const { return ptr_.isNonnull() ? ptr_.id() : backPtr_.id(); }
0096 
0097     /// Accessor for product getter.
0098     EDProductGetter const* productGetter() const {
0099       //another thread might cause productGetter() to change its value
0100       EDProductGetter const* getter = ptr_.productGetter();
0101       if (getter)
0102         return getter;
0103       else
0104         return backPtr_.productGetter();
0105     }
0106 
0107     key_type key() const { return ptr_.isNonnull() ? ptr_.key() : backPtr_.key(); }
0108 
0109     bool hasProductCache() const { return ptr_.hasProductCache() || backPtr_.hasProductCache(); }
0110 
0111     RefCore const& refCore() const { return ptr_.isNonnull() ? ptr_.refCore() : backPtr_.refCore(); }
0112     // ---------- member functions ---------------------------
0113 
0114     void const* product() const { return nullptr; }
0115 
0116     Ptr<value_type> const& ptr() const { return ptr_; }
0117     Ptr<value_type> const& backPtr() const { return backPtr_; }
0118 
0119     //Used by ROOT storage
0120     CMS_CLASS_VERSION(10)
0121 
0122   private:
0123     Ptr<value_type> ptr_;
0124     Ptr<value_type> backPtr_;
0125   };
0126 
0127   template <typename T>
0128   inline bool operator==(FwdPtr<T> const& lhs, FwdPtr<T> const& rhs) {
0129     return (lhs.ptr() == rhs.ptr() || lhs.backPtr() == rhs.ptr() || lhs.ptr() == rhs.backPtr() ||
0130             lhs.backPtr() == rhs.backPtr());
0131   }
0132 
0133   template <typename T>
0134   inline bool operator!=(FwdPtr<T> const& lhs, FwdPtr<T> const& rhs) {
0135     return !(lhs == rhs);
0136   }
0137 
0138   template <typename T>
0139   inline bool operator<(FwdPtr<T> const& lhs, FwdPtr<T> const& rhs) {
0140     /// The ordering of integer keys guarantees that the ordering of FwdPtrs within
0141     /// a collection will be identical to the ordering of the referenced objects in the collection.
0142     return (lhs.ptr() < rhs.ptr());
0143   }
0144 
0145 }  // namespace edm
0146 #endif