00001 #ifndef DataFormats_Common_fillPtrVector_h
00002 #define DataFormats_Common_fillPtrVector_h
00003
00004
00005
00006
00007
00016
00017
00018
00019
00020
00021
00022
00023
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
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
00074
00075
00076
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());
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