Geant4 Cross Reference

Cross-Referencing   Geant4
Geant4/digits_hits/hits/include/G4THitsMap.hh

Version: [ ReleaseNotes ] [ 1.0 ] [ 1.1 ] [ 2.0 ] [ 3.0 ] [ 3.1 ] [ 3.2 ] [ 4.0 ] [ 4.0.p1 ] [ 4.0.p2 ] [ 4.1 ] [ 4.1.p1 ] [ 5.0 ] [ 5.0.p1 ] [ 5.1 ] [ 5.1.p1 ] [ 5.2 ] [ 5.2.p1 ] [ 5.2.p2 ] [ 6.0 ] [ 6.0.p1 ] [ 6.1 ] [ 6.2 ] [ 6.2.p1 ] [ 6.2.p2 ] [ 7.0 ] [ 7.0.p1 ] [ 7.1 ] [ 7.1.p1 ] [ 8.0 ] [ 8.0.p1 ] [ 8.1 ] [ 8.1.p1 ] [ 8.1.p2 ] [ 8.2 ] [ 8.2.p1 ] [ 8.3 ] [ 8.3.p1 ] [ 8.3.p2 ] [ 9.0 ] [ 9.0.p1 ] [ 9.0.p2 ] [ 9.1 ] [ 9.1.p1 ] [ 9.1.p2 ] [ 9.1.p3 ] [ 9.2 ] [ 9.2.p1 ] [ 9.2.p2 ] [ 9.2.p3 ] [ 9.2.p4 ] [ 9.3 ] [ 9.3.p1 ] [ 9.3.p2 ] [ 9.4 ] [ 9.4.p1 ] [ 9.4.p2 ] [ 9.4.p3 ] [ 9.4.p4 ] [ 9.5 ] [ 9.5.p1 ] [ 9.5.p2 ] [ 9.6 ] [ 9.6.p1 ] [ 9.6.p2 ] [ 9.6.p3 ] [ 9.6.p4 ] [ 10.0 ] [ 10.0.p1 ] [ 10.0.p2 ] [ 10.0.p3 ] [ 10.0.p4 ] [ 10.1 ] [ 10.1.p1 ] [ 10.1.p2 ] [ 10.1.p3 ] [ 10.2 ] [ 10.2.p1 ] [ 10.2.p2 ] [ 10.2.p3 ] [ 10.3 ] [ 10.3.p1 ] [ 10.3.p2 ] [ 10.3.p3 ] [ 10.4 ] [ 10.4.p1 ] [ 10.4.p2 ] [ 10.4.p3 ] [ 10.5 ] [ 10.5.p1 ] [ 10.6 ] [ 10.6.p1 ] [ 10.6.p2 ] [ 10.6.p3 ] [ 10.7 ] [ 10.7.p1 ] [ 10.7.p2 ] [ 10.7.p3 ] [ 10.7.p4 ] [ 11.0 ] [ 11.0.p1 ] [ 11.0.p2 ] [ 11.0.p3, ] [ 11.0.p4 ] [ 11.1 ] [ 11.1.1 ] [ 11.1.2 ] [ 11.1.3 ] [ 11.2 ] [ 11.2.1 ] [ 11.2.2 ] [ 11.3.0 ]

  1 //
  2 // ********************************************************************
  3 // * License and Disclaimer                                           *
  4 // *                                                                  *
  5 // * The  Geant4 software  is  copyright of the Copyright Holders  of *
  6 // * the Geant4 Collaboration.  It is provided  under  the terms  and *
  7 // * conditions of the Geant4 Software License,  included in the file *
  8 // * LICENSE and available at  http://cern.ch/geant4/license .  These *
  9 // * include a list of copyright holders.                             *
 10 // *                                                                  *
 11 // * Neither the authors of this software system, nor their employing *
 12 // * institutes,nor the agencies providing financial support for this *
 13 // * work  make  any representation or  warranty, express or implied, *
 14 // * regarding  this  software system or assume any liability for its *
 15 // * use.  Please see the license in the file  LICENSE  and URL above *
 16 // * for the full disclaimer and the limitation of liability.         *
 17 // *                                                                  *
 18 // * This  code  implementation is the result of  the  scientific and *
 19 // * technical work of the GEANT4 collaboration.                      *
 20 // * By using,  copying,  modifying or  distributing the software (or *
 21 // * any work based  on the software)  you  agree  to acknowledge its *
 22 // * use  in  resulting  scientific  publications,  and indicate your *
 23 // * acceptance of all terms of the Geant4 Software license.          *
 24 // ********************************************************************
 25 //
 26 // G4VTHitsMap, G4THitsMultiMap, G4THitsUnorderedMap & G4THitsUnorderedMultiMap
 27 //
 28 // Class description:
 29 //
 30 // This is a template class of hits map and parametrised by
 31 // The concrete class of G4VHit. This is a uniform collection for
 32 // a particular concrete hit class objects.
 33 // An intermediate layer class G4HitsMap appeared in this
 34 // header file is used just for G4Allocator, because G4Allocator
 35 // cannot be instantiated with a template class. Thus G4HitsMap
 36 // class MUST NOT be directly used by the user.
 37 //
 38 // Authors: Makoto Asai, Jonathan Madsen
 39 // --------------------------------------------------------------------
 40 #ifndef G4THitsMap_h
 41 #define G4THitsMap_h 1
 42 
 43 #include "G4THitsCollection.hh"
 44 #include "globals.hh"
 45 
 46 #include <map>
 47 #include <unordered_map>
 48 #include <type_traits>
 49 
 50 template <typename T, typename Map_t = std::map<G4int, T*>>
 51 class G4VTHitsMap : public G4HitsCollection
 52 {
 53  private:
 54 
 55   using mmap_t = std::multimap<G4int, T *>;
 56   using pair_t = std::pair<G4int, T *>;
 57   using uommap_t = std::unordered_multimap<G4int, T *>;
 58 
 59 #define is_same_t(_Tp, _Up) std::is_same<_Tp, _Up>::value
 60 #define is_multimap_t(_Mp) std::is_same<_Mp, mmap_t>::value
 61 #define is_uommap_t(_Mp) std::is_same<_Mp, uommap_t>::value
 62 #define is_mmap_t(_Mp) (is_multimap_t(_Mp) || is_uommap_t(_Mp))
 63 #define is_fundamental_t(_Tp) std::is_fundamental<_Tp>::value
 64 
 65   template <bool _Bp, typename _Tp = void>
 66   using enable_if_t = typename std::enable_if<_Bp, _Tp>::type;
 67 
 68   // ensure fundamental types are initialized to zero
 69   template <typename U = T, enable_if_t<is_fundamental_t(U), G4int> = 0>
 70   T* allocate() const
 71   {
 72     return new T(0.);
 73   }
 74   // non-fundamental types should set values to appropriate values
 75   // and avoid issues such as:
 76   //   G4StatDouble stat(0.); stat += 1.0; gives n == 2;
 77   template <typename U = T, enable_if_t<! is_fundamental_t(U), G4int> = 0>
 78   T* allocate() const
 79   {
 80     return new T();
 81   }
 82 
 83  public:
 84   using this_type = G4VTHitsMap<T, Map_t>;
 85   using value_type = T;
 86   using map_type = Map_t;
 87   using iterator = typename map_type::iterator;
 88   using const_iterator = typename map_type::const_iterator;
 89 
 90   // generic constructor
 91   G4VTHitsMap();
 92   // det + collection description constructor
 93   G4VTHitsMap(const G4String& detName, const G4String& colNam);
 94   // destructor
 95   ~G4VTHitsMap() override;
 96   // equivalence operator
 97   G4bool operator==(const G4VTHitsMap<T, Map_t>& right) const;
 98 
 99   //------------------------------------------------------------------------//
100   // Generic operator += where add(...) overloads handle various
101   //  U and MapU_t types
102   //------------------------------------------------------------------------//
103   template <typename U, typename MapU_t>
104   this_type& operator+=(const G4VTHitsMap<U, MapU_t>& right) const
105   {
106     MapU_t* aHitsMap = right.GetMap();
107     for (auto itr = aHitsMap->begin(); itr != aHitsMap->end(); ++itr)
108       add<U, map_type>(itr->first, *(itr->second));
109     return (this_type&)(*this);
110   }
111   //------------------------------------------------------------------------//
112 
113   void DrawAllHits() override;
114   void PrintAllHits() override;
115   //  These two methods invokes Draw() and Print() methods of all of
116   //  hit objects stored in this map, respectively.
117 
118   // Generic iteration
119   inline Map_t* GetContainer() const { return (Map_t*)theCollection; }
120 
121   inline typename Map_t::size_type size() { return GetContainer()->size(); }
122 
123   inline typename Map_t::size_type GetIndex(iterator itr) { return itr->first; }
124 
125   inline typename Map_t::size_type GetIndex(const_iterator itr) const { return itr->first; }
126 
127   template <typename MapU_t = Map_t, enable_if_t<! is_mmap_t(MapU_t), G4int> = 0>
128   inline T* GetObject(G4int idx) const
129   {
130     return (GetContainer()->count(idx) != 0) ? (*GetContainer())[idx] : nullptr;
131   }
132 
133   template <typename MapU_t = Map_t, enable_if_t<is_mmap_t(MapU_t), G4int> = 0>
134   inline T* GetObject(G4int idx) const
135   {
136     return (GetContainer()->count(idx) != 0) ? GetContainer()->find(idx)->second : nullptr;
137   }
138 
139   inline T* GetObject(iterator itr) const { return itr->second; }
140 
141   inline const T* GetObject(const_iterator itr) const { return itr->second; }
142 
143   iterator begin() { return GetContainer()->begin(); }
144   iterator end() { return GetContainer()->end(); }
145   const_iterator begin() const { return GetContainer()->begin(); }
146   const_iterator end() const { return GetContainer()->end(); }
147   const_iterator cbegin() const { return GetContainer()->cbegin(); }
148   const_iterator cend() const { return GetContainer()->cend(); }
149 
150   //  Returns a pointer to a concrete hit object.
151   inline Map_t* GetMap() const { return (Map_t*)theCollection; }
152   //  Overwrite a hit object. Total number of hit objects stored in this
153   // map is returned.
154   inline std::size_t entries() const { return ((Map_t*)theCollection)->size(); }
155   //  Returns the number of hit objects stored in this map
156   inline void clear();
157 
158   G4VHit* GetHit(std::size_t) const override { return nullptr; }
159   std::size_t GetSize() const override { return ((Map_t*)theCollection)->size(); }
160 
161   //------------------------------------------------------------------------//
162   //  Add/Insert a hit object. Total number of hit objects stored in this
163   //  map is returned.
164   //------------------------------------------------------------------------//
165   //  Standard map overload for same type
166   //------------------------------------------------------------------------//
167   // here we don't use allocate() since instances like G4Colour() == white
168   // and += adds to white (not correct)
169   template <typename U = T, typename MapU_t = Map_t,
170     enable_if_t<is_same_t(U, T) && ! is_mmap_t(MapU_t), G4int> = 0>
171   std::size_t add(const G4int& key, U*& aHit) const
172   {
173     map_type* theHitsMap = GetMap();
174     if (theHitsMap->find(key) == theHitsMap->end())
175       theHitsMap->insert(pair_t(key, new T(*aHit)));
176     else
177       *theHitsMap->find(key)->second += *aHit;
178     return theHitsMap->size();
179   }
180   //------------------------------------------------------------------------//
181   //  Multimap overload for same type T
182   //------------------------------------------------------------------------//
183   template <typename U = T, typename MapU_t = Map_t,
184     enable_if_t<(is_same_t(U, T) && is_mmap_t(MapU_t)), G4int> = 0>
185   std::size_t add(const G4int& key, U*& aHit) const
186   {
187     map_type* theHitsMap = GetMap();
188     theHitsMap->insert(pair_t(key, aHit));
189     return theHitsMap->size();
190   }
191   //------------------------------------------------------------------------//
192   //  Multimap overload for different types
193   //      assumes type T has overload of += operator for U
194   //------------------------------------------------------------------------//
195   template <typename U = T, typename MapU_t = Map_t,
196     enable_if_t<(! is_same_t(U, T) && is_mmap_t(MapU_t)), G4int> = 0>
197   std::size_t add(const G4int& key, U*& aHit) const
198   {
199     map_type* theHitsMap = GetMap();
200     T* hit = allocate();
201     *hit += *aHit;
202     theHitsMap->insert(pair_t(key, hit));
203     return theHitsMap->size();
204   }
205 
206   //------------------------------------------------------------------------//
207   //  Standard map overload for same type
208   //      assumes type T has overload of += operator for U
209   //------------------------------------------------------------------------//
210   // here we don't use allocate() since instances like G4Colour() == white
211   // and += adds to white (not correct)
212   template <typename U = T, typename MapU_t = Map_t,
213     enable_if_t<(is_same_t(U, T) && ! is_mmap_t(MapU_t)), G4int> = 0>
214   std::size_t add(const G4int& key, U& aHit) const
215   {
216     map_type* theHitsMap = GetMap();
217     if (theHitsMap->find(key) == theHitsMap->end())
218       theHitsMap->insert(pair_t(key, new T(aHit)));
219     else
220       *theHitsMap->find(key)->second += aHit;
221     return theHitsMap->size();
222   }
223   //------------------------------------------------------------------------//
224   //  Standard map overload for different type
225   //      assumes type T has overload of += operator for U
226   //------------------------------------------------------------------------//
227   template <typename U = T, typename MapU_t = Map_t,
228     enable_if_t<(! is_same_t(U, T) && ! is_mmap_t(MapU_t)), G4int> = 0>
229   std::size_t add(const G4int& key, U& aHit) const
230   {
231     map_type* theHitsMap = GetMap();
232     if (theHitsMap->find(key) == theHitsMap->end()) theHitsMap->insert(pair_t(key, allocate()));
233     *theHitsMap->find(key)->second += aHit;
234     return theHitsMap->size();
235   }
236   //------------------------------------------------------------------------//
237   //  Multimap overload for same type T
238   //------------------------------------------------------------------------//
239   template <typename U = T, typename MapU_t = Map_t,
240     enable_if_t<(is_same_t(U, T) && is_mmap_t(MapU_t)), G4int> = 0>
241   std::size_t add(const G4int& key, U& aHit) const
242   {
243     map_type* theHitsMap = GetMap();
244     theHitsMap->insert(pair_t(key, new T(aHit)));
245     return theHitsMap->size();
246   }
247   //------------------------------------------------------------------------//
248   //  Multimap overload for different types
249   //      assumes type T has overload of += operator for U
250   //------------------------------------------------------------------------//
251   template <typename U = T, typename MapU_t = Map_t,
252     enable_if_t<(! is_same_t(U, T) && is_mmap_t(MapU_t)), G4int> = 0>
253   std::size_t add(const G4int& key, U& aHit) const
254   {
255     map_type* theHitsMap = GetMap();
256     T* hit = allocate();
257     *hit += aHit;
258     theHitsMap->insert(pair_t(key, hit));
259     return theHitsMap->size();
260   }
261 
262   //------------------------------------------------------------------------//
263   //  Set a hit object. Total number of hit objects stored in this
264   //  map is returned.
265   //------------------------------------------------------------------------//
266   //  Standard overload for same type T
267   //------------------------------------------------------------------------//
268   template <typename U = T, typename MapU_t = Map_t,
269     enable_if_t<(is_same_t(U, T) && ! is_mmap_t(MapU_t)), G4int> = 0>
270   inline std::size_t set(const G4int& key, U*& aHit) const
271   {
272     map_type* theHitsMap = GetMap();
273     if (theHitsMap->find(key) != theHitsMap->end()) delete theHitsMap->find(key)->second;
274     theHitsMap->find(key)->second = aHit;
275     return theHitsMap->size();
276   }
277   //------------------------------------------------------------------------//
278   //  Multimap overload for same type T
279   //------------------------------------------------------------------------//
280   template <typename U = T, typename MapU_t = Map_t,
281     enable_if_t<(is_same_t(U, T) && is_mmap_t(MapU_t)), G4int> = 0>
282   inline std::size_t set(const G4int& key, U*& aHit) const
283   {
284     map_type* theHitsMap = GetMap();
285     if (theHitsMap->find(key) != theHitsMap->end())
286       theHitsMap->insert(pair_t(key, aHit));
287     else {
288       delete theHitsMap->find(key)->second;
289       theHitsMap->find(key)->second = aHit;
290     }
291     return theHitsMap->size();
292   }
293   //------------------------------------------------------------------------//
294   //  Standard map overload for different types
295   //------------------------------------------------------------------------//
296   template <typename U = T, typename MapU_t = Map_t,
297     enable_if_t<(! is_same_t(U, T) && ! is_mmap_t(MapU_t)), G4int> = 0>
298   inline std::size_t set(const G4int& key, U*& aHit) const
299   {
300     map_type* theHitsMap = GetMap();
301     T* hit = nullptr;
302     if (theHitsMap->find(key) == theHitsMap->end())
303       theHitsMap->insert(std::make_pair(key, hit = allocate()));
304     else
305       hit = theHitsMap->find(key)->second;
306     *hit += *aHit;
307     return theHitsMap->size();
308   }
309   //------------------------------------------------------------------------//
310   //  Multimap overload for different types
311   //------------------------------------------------------------------------//
312   template <typename U = T, typename MapU_t = Map_t,
313     enable_if_t<(! is_same_t(U, T) && is_mmap_t(MapU_t)), G4int> = 0>
314   inline std::size_t set(const G4int& key, U*& aHit) const
315   {
316     map_type* theHitsMap = GetMap();
317     T* hit = allocate();
318     *hit += *aHit;
319     if (theHitsMap->find(key) != theHitsMap->end())
320       theHitsMap->insert(pair_t(key, hit));
321     else {
322       delete theHitsMap->find(key)->second;
323       theHitsMap->find(key)->second = hit;
324     }
325     return theHitsMap->size();
326   }
327 
328   //------------------------------------------------------------------------//
329   //  Set a hit object. Total number of hit objects stored in this
330   //  map is returned.
331   //------------------------------------------------------------------------//
332   //  Standard overload for same type T
333   //------------------------------------------------------------------------//
334   template <typename U = T, typename MapU_t = Map_t,
335     enable_if_t<(is_same_t(U, T) && ! is_mmap_t(MapU_t)), G4int> = 0>
336   inline std::size_t set(const G4int& key, U& aHit) const
337   {
338     map_type* theHitsMap = GetMap();
339     T* hit = nullptr;
340     if (theHitsMap->find(key) != theHitsMap->end())
341       hit = theHitsMap->find(key)->second;
342     else
343       theHitsMap->insert(pair_t(key, hit = allocate()));
344     *hit = aHit;
345     return theHitsMap->size();
346   }
347   //------------------------------------------------------------------------//
348   //  Multimap overload for same type T
349   //------------------------------------------------------------------------//
350   template <typename U = T, typename MapU_t = Map_t,
351     enable_if_t<(is_same_t(U, T) && is_mmap_t(MapU_t)), G4int> = 0>
352   inline std::size_t set(const G4int& key, U& aHit) const
353   {
354     map_type* theHitsMap = GetMap();
355     if (theHitsMap->find(key) != theHitsMap->end())
356       *theHitsMap->find(key)->second = aHit;
357     else
358       theHitsMap->insert(pair_t(key, new T(aHit)));
359     return theHitsMap->size();
360   }
361   //------------------------------------------------------------------------//
362   //  Standard map overload for different types
363   //------------------------------------------------------------------------//
364   template <typename U = T, typename MapU_t = Map_t,
365     enable_if_t<(! is_same_t(U, T) && ! is_mmap_t(MapU_t)), G4int> = 0>
366   inline std::size_t set(const G4int& key, U& aHit) const
367   {
368     map_type* theHitsMap = GetMap();
369     T* hit = nullptr;
370     if (theHitsMap->find(key) == theHitsMap->end())
371       theHitsMap->insert(std::make_pair(key, hit = allocate()));
372     else
373       hit = theHitsMap->find(key)->second;
374     *hit += aHit;
375     return theHitsMap->size();
376   }
377   //------------------------------------------------------------------------//
378   //  Multimap overload for different types
379   //------------------------------------------------------------------------//
380   template <typename U = T, typename MapU_t = Map_t,
381     enable_if_t<(! is_same_t(U, T) && is_mmap_t(MapU_t)), G4int> = 0>
382   inline std::size_t set(const G4int& key, U& aHit) const
383   {
384     map_type* theHitsMap = GetMap();
385     T* hit = allocate();
386     *hit += aHit;
387     if (theHitsMap->find(key) != theHitsMap->end())
388       *theHitsMap->find(key)->second = *hit;
389     else
390       theHitsMap->insert(pair_t(key, hit));
391     return theHitsMap->size();
392   }
393 
394   //------------------------------------------------------------------------//
395   //  Enable bracket operator. Return pointer to data indexed by key or
396   //      last occurring instance of pointer to data index by key in the
397   //      case of a multimap
398   //------------------------------------------------------------------------//
399   template <typename MapU_t = Map_t, enable_if_t<! is_mmap_t(MapU_t), G4int> = 0>
400   T* operator[](G4int key) const
401   {
402     map_type* theHitsMap = GetMap();
403     if (theHitsMap->find(key) != theHitsMap->end()) return theHitsMap->find(key)->second;
404     return nullptr;
405   }
406   //------------------------------------------------------------------------//
407   template <typename MapU_t = Map_t, enable_if_t<is_mmap_t(MapU_t), G4int> = 0>
408   T* operator[](G4int key) const
409   {
410 #ifdef G4VERBOSE
411     static G4bool _first = true;
412     if (_first) {
413       _first = false;
414       G4Exception("G4THitsMap operator[]", "calling [] on multimap", JustWarning,
415         "Returning the last matching entry");
416     }
417 #endif
418     map_type* theHitsMap = GetMap();
419     iterator itr = theHitsMap->find(key);
420     if (itr != theHitsMap->end()) {
421       std::advance(itr, theHitsMap->count(key) - 1);
422       return itr->second;
423     }
424     return nullptr;
425   }
426   //------------------------------------------------------------------------//
427 
428 #undef is_same_t
429 #undef is_multimap_t
430 #undef is_uommap_t
431 #undef is_mmap_t
432 #undef is_fundamental_t
433 };
434 
435 //============================================================================//
436 
437 template <typename T, typename Map_t>
438 G4VTHitsMap<T, Map_t>::G4VTHitsMap()
439 {
440   theCollection = (void*)new Map_t;
441 }
442 
443 //============================================================================//
444 
445 template <typename T, typename Map_t>
446 G4VTHitsMap<T, Map_t>::G4VTHitsMap(const G4String& detName, const G4String& colNam)
447   : G4HitsCollection(detName, colNam)
448 {
449   theCollection = (void*)new Map_t;
450 }
451 
452 //============================================================================//
453 
454 template <typename T, typename Map_t>
455 G4VTHitsMap<T, Map_t>::~G4VTHitsMap()
456 {
457   map_type* theHitsMap = GetMap();
458   for (auto itr = theHitsMap->begin(); itr != theHitsMap->end(); ++itr)
459     delete itr->second;
460   delete theHitsMap;
461 }
462 
463 //============================================================================//
464 
465 template <typename T, typename Map_t>
466 G4bool G4VTHitsMap<T, Map_t>::operator==(const G4VTHitsMap<T, Map_t>& right) const
467 {
468   return (collectionName == right.collectionName);
469 }
470 
471 //============================================================================//
472 
473 template <typename T, typename Map_t>
474 void G4VTHitsMap<T, Map_t>::DrawAllHits()
475 {
476   ;
477 }
478 
479 //============================================================================//
480 
481 template <typename T, typename Map_t>
482 void G4VTHitsMap<T, Map_t>::PrintAllHits()
483 {
484   G4cout << "G4THitsMap " << SDname << " / " << collectionName << " --- " << entries() << " entries"
485          << G4endl;
486   /*----- commented out for the use-case where <T> cannot be initialized
487           to be zero or does not support += operator.
488    Map_t * theHitsMap = GetMap();
489    typename Map_t::iterator itr = theHitsMap->begin();
490    T sum = 0.;
491    for(; itr != theHitsMap->end(); ++itr) {
492     G4cout << "  " << itr->first << " : "
493            << *(itr->second) << G4endl;
494     sum += *(itr->second);
495    }
496    G4cout << "             Total : " << sum << G4endl;
497   ----------------------------------------------------------------------*/
498 }
499 
500 //============================================================================//
501 
502 template <typename T, typename Map_t>
503 void G4VTHitsMap<T, Map_t>::clear()
504 {
505   Map_t* theHitsMap = GetMap();
506   for (iterator itr = theHitsMap->begin(); itr != theHitsMap->end(); ++itr)
507     delete itr->second;
508   theHitsMap->clear();
509 }
510 
511 //============================================================================//
512 //                                                                            //
513 //                                                                            //
514 //                      Helpers for different map types                       //
515 //                                                                            //
516 //                                                                            //
517 //============================================================================//
518 
519 template <typename _Tp>
520 class G4THitsMap : public G4VTHitsMap<_Tp, std::map<G4int, _Tp*>>
521 {
522  public:
523   using parent_type = G4VTHitsMap<_Tp, std::map<G4int, _Tp *>>;
524 
525  public:
526   G4THitsMap() : parent_type() {}
527   G4THitsMap(G4String detName, G4String colName) : parent_type(detName, colName) {}
528 
529   using parent_type::operator+=;
530   using parent_type::operator==;
531   using parent_type::operator[];
532   using parent_type::add;
533   using parent_type::begin;
534   using parent_type::cbegin;
535   using parent_type::cend;
536   using parent_type::clear;
537   using parent_type::DrawAllHits;
538   using parent_type::end;
539   using parent_type::entries;
540   using parent_type::GetHit;
541   using parent_type::GetMap;
542   using parent_type::GetSize;
543   using parent_type::PrintAllHits;
544   using parent_type::set;
545 };
546 
547 //============================================================================//
548 
549 template <typename _Tp>
550 class G4THitsMultiMap : public G4VTHitsMap<_Tp, std::multimap<G4int, _Tp*>>
551 {
552  public:
553   using parent_type = G4VTHitsMap<_Tp, std::multimap<G4int, _Tp *>>;
554 
555  public:
556   G4THitsMultiMap() : parent_type() {}
557   G4THitsMultiMap(const G4String& detName, const G4String& colName)
558     : parent_type(detName, colName) {}
559 
560   using parent_type::operator+=;
561   using parent_type::operator==;
562   using parent_type::operator[];
563   using parent_type::add;
564   using parent_type::begin;
565   using parent_type::cbegin;
566   using parent_type::cend;
567   using parent_type::clear;
568   using parent_type::DrawAllHits;
569   using parent_type::end;
570   using parent_type::entries;
571   using parent_type::GetHit;
572   using parent_type::GetMap;
573   using parent_type::GetSize;
574   using parent_type::PrintAllHits;
575   using parent_type::set;
576 };
577 
578 //============================================================================//
579 
580 template <typename _Tp>
581 class G4THitsUnorderedMap : public G4VTHitsMap<_Tp, std::unordered_map<G4int, _Tp*>>
582 {
583  public:
584   using parent_type = G4VTHitsMap<_Tp, std::unordered_map<G4int, _Tp *>>;
585 
586  public:
587   G4THitsUnorderedMap() : parent_type() {}
588   G4THitsUnorderedMap(const G4String& detName, const G4String& colName)
589     : parent_type(detName, colName) {}
590 
591   using parent_type::operator+=;
592   using parent_type::operator==;
593   using parent_type::operator[];
594   using parent_type::add;
595   using parent_type::begin;
596   using parent_type::cbegin;
597   using parent_type::cend;
598   using parent_type::clear;
599   using parent_type::DrawAllHits;
600   using parent_type::end;
601   using parent_type::entries;
602   using parent_type::GetHit;
603   using parent_type::GetMap;
604   using parent_type::GetSize;
605   using parent_type::PrintAllHits;
606   using parent_type::set;
607 };
608 
609 //============================================================================//
610 
611 template <typename _Tp>
612 class G4THitsUnorderedMultiMap : public G4VTHitsMap<_Tp, std::unordered_multimap<G4int, _Tp*>>
613 {
614  public:
615   using parent_type = G4VTHitsMap<_Tp, std::unordered_multimap<G4int, _Tp *>>;
616 
617  public:
618   G4THitsUnorderedMultiMap() : parent_type() {}
619   G4THitsUnorderedMultiMap(const G4String& detName, const G4String& colName)
620     : parent_type(detName, colName) {}
621 
622   using parent_type::operator+=;
623   using parent_type::operator==;
624   using parent_type::operator[];
625   using parent_type::add;
626   using parent_type::begin;
627   using parent_type::cbegin;
628   using parent_type::cend;
629   using parent_type::clear;
630   using parent_type::DrawAllHits;
631   using parent_type::end;
632   using parent_type::entries;
633   using parent_type::GetHit;
634   using parent_type::GetMap;
635   using parent_type::GetSize;
636   using parent_type::PrintAllHits;
637   using parent_type::set;
638 };
639 
640 //============================================================================//
641 
642 #endif
643