CMS 3D CMS Logo

/data/refman/pasoursint/CMSSW_5_3_3/src/DataFormats/Common/interface/fillPtrVector.h

Go to the documentation of this file.
00001 #ifndef DataFormats_Common_fillPtrVector_h
00002 #define DataFormats_Common_fillPtrVector_h
00003 // -*- C++ -*-
00004 //
00005 // Package:     Common
00006 // Class  :     fillPtrVector
00007 //
00016 //
00017 // Original Author:  Chris Jones
00018 //         Created:  Sat Oct 20 11:45:38 CEST 2007
00019 //
00020 
00021 // system include files
00022 
00023 // user include files
00024 #include "DataFormats/Common/interface/FillView.h"
00025 #include "FWCore/Utilities/interface/EDMException.h"
00026 #include "Reflex/Object.h"
00027 #include "Reflex/Type.h"
00028 
00029 #include "DataFormats/Common/interface/fwd_fillPtrVector.h"
00030 
00031 #include <typeinfo>
00032 #include <vector>
00033 
00034 // forward declarations
00035 namespace edm {
00036   namespace detail {
00037     template <typename COLLECTION>
00038     void
00039     reallyfillPtrVector(COLLECTION const& coll,
00040                         std::type_info const& iToType,
00041                         std::vector<unsigned long> const& iIndicies,
00042                         std::vector<void const*>& oPtr)
00043     {
00044       typedef COLLECTION                            product_type;
00045       typedef typename GetProduct<product_type>::element_type     element_type;
00046       typedef typename product_type::const_iterator iter;
00047       typedef typename product_type::size_type      size_type;
00048 
00049       oPtr.reserve(iIndicies.size());
00050       if(iToType == typeid(element_type)) {
00051         for(std::vector<unsigned long>::const_iterator itIndex = iIndicies.begin(),
00052             itEnd = iIndicies.end();
00053             itIndex != itEnd;
00054             ++itIndex) {
00055           iter it = coll.begin();
00056           std::advance(it, *itIndex);
00057           element_type const* address = GetProduct<product_type>::address(it);
00058           oPtr.push_back(address);
00059         }
00060       } else {
00061         using Reflex::Type;
00062         using Reflex::Object;
00063         static Type const s_type(Type::ByTypeInfo(typeid(element_type)));
00064         Type toType = Type::ByTypeInfo(iToType);
00065 
00066         for(std::vector<unsigned long>::const_iterator itIndex = iIndicies.begin(),
00067             itEnd = iIndicies.end();
00068             itIndex != itEnd;
00069             ++itIndex) {
00070           iter it = coll.begin();
00071           std::advance(it, *itIndex);
00072           element_type const* address = GetProduct<product_type>::address(it);
00073           // The const_cast below is needed because
00074           // Object's constructor requires a pointer to
00075           // non-const void, although the implementation does not, of
00076           // course, modify the object to which the pointer points.
00077           Object obj(s_type, const_cast<void*>(static_cast<void const*>(address)));
00078           Object cast = obj.CastObject(toType);
00079           if(0 != cast.Address()) {
00080             oPtr.push_back(cast.Address());// returns void*, after pointer adjustment
00081           } else {
00082             Exception::throwThis(errors::LogicError,
00083             "TypeConversionError "
00084             "edm::PtrVector<> : unable to convert type ",
00085             typeid(element_type).name(),
00086             " to ",
00087             iToType.name(),
00088             "\n");
00089           }
00090         }
00091       }
00092     }
00093   }
00094 
00095   template <typename T, typename A>
00096   void
00097   fillPtrVector(std::vector<T, A> const& obj,
00098                 std::type_info const& iToType,
00099                 std::vector<unsigned long> const& iIndicies,
00100                 std::vector<void const*>& oPtr) {
00101     detail::reallyfillPtrVector(obj, iToType, iIndicies, oPtr);
00102   }
00103 
00104   template <typename T, typename A>
00105   void
00106   fillPtrVector(std::list<T, A> const& obj,
00107                 std::type_info const& iToType,
00108                 std::vector<unsigned long> const& iIndicies,
00109                 std::vector<void const*>& oPtr) {
00110     detail::reallyfillPtrVector(obj, iToType, iIndicies, oPtr);
00111   }
00112 
00113   template <typename T, typename A>
00114   void
00115   fillPtrVector(std::deque<T, A> const& obj,
00116                 std::type_info const& iToType,
00117                 std::vector<unsigned long> const& iIndicies,
00118                 std::vector<void const*>& oPtr) {
00119     detail::reallyfillPtrVector(obj, iToType, iIndicies, oPtr);
00120   }
00121 
00122   template <typename T, typename A, typename Comp>
00123   void
00124   fillPtrVector(std::set<T, A, Comp> const& obj,
00125                 std::type_info const& iToType,
00126                 std::vector<unsigned long> const& iIndicies,
00127                 std::vector<void const*>& oPtr) {
00128     detail::reallyfillPtrVector(obj, iToType, iIndicies, oPtr);
00129   }
00130 }
00131 
00132 #endif