PSEvt/src/ProxyDict.cpp

Go to the documentation of this file.
00001 //--------------------------------------------------------------------------
00002 // File and Version Information:
00003 //      $Id: ProxyDict.cpp 7525 2014-01-13 19:52:29Z salnikov@SLAC.STANFORD.EDU $
00004 //
00005 // Description:
00006 //      Class ProxyDict...
00007 //
00008 // Author List:
00009 //      Andrei Salnikov
00010 //
00011 //------------------------------------------------------------------------
00012 
00013 //-----------------------
00014 // This Class's Header --
00015 //-----------------------
00016 #include "PSEvt/ProxyDict.h"
00017 
00018 //-----------------
00019 // C/C++ Headers --
00020 //-----------------
00021 
00022 //-------------------------------
00023 // Collaborating Class Headers --
00024 //-------------------------------
00025 #include "PSEvt/Exceptions.h"
00026 
00027 //-----------------------------------------------------------------------
00028 // Local Macros, Typedefs, Structures, Unions and Forward Declarations --
00029 //-----------------------------------------------------------------------
00030 
00031 //              ----------------------------------------
00032 //              -- Public Function Member Definitions --
00033 //              ----------------------------------------
00034 
00035 namespace PSEvt {
00036 
00037 //----------------
00038 // Constructors --
00039 //----------------
00040 ProxyDict::ProxyDict (const boost::shared_ptr<AliasMap>& amap)
00041   : m_dict()
00042   , m_amap(amap)
00043 {
00044 }
00045 
00046 //--------------
00047 // Destructor --
00048 //--------------
00049 ProxyDict::~ProxyDict ()
00050 {
00051 }
00052 
00053 
00054 void 
00055 ProxyDict::putImpl( const boost::shared_ptr<ProxyI>& proxy, 
00056                     const EventKey& key )
00057 {
00058   // key may define one of alias or Src
00059   EventKey ekey = key;
00060   if (not ekey.alias().empty()) {
00061     if (m_amap) {
00062       // get src from alias
00063       Pds::Src src = m_amap->src(ekey.alias());
00064       ekey = EventKey(ekey.typeinfo(), src, ekey.key(), ekey.alias());
00065     } else {
00066       throw ExceptionNoAliasMap(ERR_LOC);
00067     }
00068   } else {
00069     if (m_amap) {
00070       // try to find alias for src
00071       const std::string& alias = m_amap->alias(ekey.src());
00072       ekey = EventKey(ekey.typeinfo(), ekey.src(), ekey.key(), alias);
00073     }
00074   }
00075 
00076   // there should not be existing key
00077   Dict::iterator it = m_dict.find(ekey);
00078   if ( it != m_dict.end() ) {
00079     throw ExceptionDuplicateKey(ERR_LOC, ekey);
00080   }
00081 
00082   m_dict.insert(Dict::value_type(ekey, proxy));
00083 }
00084 
00085 
00086 boost::shared_ptr<void> 
00087 ProxyDict::getImpl( const std::type_info* typeinfo, 
00088                     const Source& source, 
00089                     const std::string& key,
00090                     Pds::Src* foundSrc )
00091 {
00092   Source::SrcMatch srcm = source.srcMatch(m_amap ? *m_amap : AliasMap());
00093 
00094   if (srcm.isExact()) {
00095     
00096     EventKey proxyKey(typeinfo, srcm.src(), key);
00097     Dict::const_iterator it = m_dict.find(proxyKey);
00098     if ( it != m_dict.end() ) {
00099       // call proxy to get the value
00100       if (foundSrc) *foundSrc = it->first.src();
00101       return it->second->get(this, it->first.src(), key);
00102     }
00103 
00104     // try special any-source proxy
00105     EventKey proxyKeyAny(typeinfo, EventKey::anySource(), key);
00106     it = m_dict.find(proxyKeyAny);
00107     if ( it != m_dict.end() ) {
00108       // call proxy to get the value
00109       if (foundSrc) *foundSrc = srcm.src();
00110       return it->second->get(this, srcm.src(), key);
00111     }
00112 
00113   } else {
00114 
00115     // When source is a match then no-source objects have priority. Try to
00116     // find no-source object first and see if it matches
00117     if (srcm.match(Pds::Src())) {
00118       EventKey proxyKey(typeinfo, Pds::Src(), key);
00119       Dict::const_iterator it = m_dict.find(proxyKey);
00120       if ( it != m_dict.end() ) {
00121         // call proxy to get the value
00122         if (foundSrc) *foundSrc = it->first.src();
00123         return it->second->get(this, it->first.src(), key);
00124       }
00125     }
00126 
00127     // Do linear search, find first match
00128     for (Dict::const_iterator it = m_dict.begin(); it != m_dict.end(); ++ it) {
00129       if (*typeinfo == *it->first.typeinfo() and
00130           key == it->first.key() and 
00131           srcm.match(it->first.src()) ) {
00132         // call proxy to get the value
00133         if (foundSrc) *foundSrc = it->first.src();
00134         return it->second->get(this, it->first.src(), key);
00135       }
00136     }
00137     
00138   }
00139 
00140   return proxy_ptr();
00141 
00142 }
00143 
00144 bool 
00145 ProxyDict::existsImpl(const EventKey& key)
00146 {
00147   return m_dict.find(key) != m_dict.end();
00148 }
00149 
00150 bool 
00151 ProxyDict::removeImpl(const EventKey& key)
00152 {
00153   return m_dict.erase(key) > 0;
00154 }
00155 
00156 void 
00157 ProxyDict::keysImpl(std::list<EventKey>& keys, const Source& source) const
00158 {
00159   Source::SrcMatch srcm = source.srcMatch(m_amap ? *m_amap : AliasMap());
00160 
00161   keys.clear();
00162   for (Dict::const_iterator it = m_dict.begin(); it != m_dict.end(); ++ it) {
00163     if (srcm.match(it->first.src())) keys.push_back(it->first);
00164   }
00165 }
00166 
00167 } // namespace PSEvt

Generated on 19 Dec 2016 for PSANAclasses by  doxygen 1.4.7