ATLAS Offline Software
Loading...
Searching...
No Matches
Navigable.icc
Go to the documentation of this file.
1/*
2 Copyright (C) 2002-2019 CERN for the benefit of the ATLAS collaboration
3*/
4
5//////////////////////////////////////////////////////////////////////////////
6// //
7// Navigable implementations //
8// //
9//////////////////////////////////////////////////////////////////////////////
10
11#include <typeinfo>
12
13// constructor
14template <typename CONT, typename RPAR, typename COLL>
15Navigable<CONT,RPAR,COLL>::Navigable() { }
16
17 //////////////////////////////////////////////
18 // Navigation query handling w/o parameters //
19 //////////////////////////////////////////////
20
21//debug #include <iostream>
22
23template <typename CONT, typename RPAR, typename COLL>
24void
25Navigable<CONT, RPAR, COLL>::fillToken(INavigationToken& navToken) const
26{
27 //////////////////////////////////
28 // Check Object Type Query Only //
29 //////////////////////////////////
30
31 // token type comparison
32 NavigationToken<constituent_type>* noParToken =
33 dynamic_cast< NavigationToken<constituent_type>* >(&navToken);
34
35 // token type accepted
36 if ( noParToken != 0 )
37 {
38 this->apply(*noParToken);
39 this->toKidsAfterAccept(*noParToken);
40//debug std::cout << "[Navigable::fillToken(token)] - honored "
41//debug << "NavigationToken<CONSTITUENT_TYPE>"
42//debug << std::endl;
43 return;
44 }
45
46 /////////////////////////////////////////////////////////
47 // Check Object Type & Relational Parameter Type Query //
48 /////////////////////////////////////////////////////////
49
50 // token type comparison
51 NavigationToken<constituent_type, RPAR>* parToken =
52 dynamic_cast< NavigationToken<constituent_type, RPAR>* >(&navToken);
53
54 // token type accepted
55 if ( parToken != 0 )
56 {
57 this->apply(*parToken, RPAR());
58 this->toKidsAfterAccept(*parToken,RPAR());
59//debug std::cout << "[Navigable::fillToken(token)] - honored "
60//debug << "NavigableToken<CONSTITUENT_TYPE,REL_PARM>"
61//debug << std::endl;
62 return;
63 }
64
65 ///////////////////////////////
66 // Forward Query If No Match //
67 ///////////////////////////////
68
69 this->toKidsAfterReject(navToken);
70}
71
72 /////////////////////////////////////////////
73 // Navigation query handling w/ parameters //
74 /////////////////////////////////////////////
75
76template <typename CONT, typename RPAR, typename COLL>
77void
78Navigable<CONT, RPAR, COLL>::fillToken(INavigationToken& navToken,
79 const std::any& aParameter) const
80{
81 //////////////////////////////////
82 // Check Object Type Query Only //
83 //////////////////////////////////
84
85 // token type comparison
86 NavigationToken<constituent_type>* noParToken =
87 dynamic_cast< NavigationToken<constituent_type>* >(&navToken);
88
89 // token type accepted
90 if ( noParToken != 0 )
91 {
92 this->apply(*noParToken);
93 this->toKidsAfterAccept(*noParToken);
94//debug std::cout << "[Navigable::fillToken(token,weight)] - honored "
95//debug << "NavigationToken<CONSTITUENT_TYPE>"
96//debug << std::endl;
97 return;
98 }
99
100 /////////////////////////////////////////////////////////
101 // Check Object Type & Relational Parameter Type Query //
102 /////////////////////////////////////////////////////////
103
104 // token type comparison
105 NavigationToken<constituent_type, RPAR>* parToken =
106 dynamic_cast< NavigationToken<constituent_type, RPAR>* >(&navToken);
107
108 // token type accepted
109 if ( parToken != 0 )
110 {
111 this->apply(*parToken, std::any_cast<RPAR>(aParameter));
112 this->toKidsAfterAccept(*parToken,aParameter);
113//debug std::cout << "[Navigable::fillToken(token,weight)] - honored "
114//debug << "NavigableToken<CONSTITUENT_TYPE,REL_PARM>"
115//debug << std::endl;
116 return;
117 }
118
119 ///////////////////////////////
120 // Forward Query If No Match //
121 ///////////////////////////////
122
123 this->toKidsAfterReject(navToken, aParameter);
124
125}
126
127 /////////////////////////
128 // Insert Constituents //
129 /////////////////////////
130
131// insert by object pointer
132template <typename CONT, typename RPAR, typename COLL>
133void
134Navigable<CONT, RPAR, COLL>::putElement(const CONT*
135 ptrObjectContainer,
136 const constituent_type*
137 ptrObject,
138 const RPAR&
139 refParameter,
140 size_t sizeHint)
141{
142 // replacement insertion policy in
143 if ( this->contains(ptrObject) ) this->remove(ptrObject);
144 this->insertElement(ptrObjectContainer,ptrObject,refParameter,sizeHint);
145}
146
147// insert by object index
148template <typename CONT, typename RPAR, typename COLL>
149void
150Navigable<CONT, RPAR, COLL>::putElement(const CONT*
151 ptrObjectContainer,
152 const external_index_type&
153 refIndex,
154 const RPAR&
155 refParameter,
156 size_t sizeHint)
157
158{
159 if ( this->contains(ptrObjectContainer,refIndex) )
160 this->remove(ptrObjectContainer,refIndex);
161 this->insertElement(ptrObjectContainer,refIndex,refParameter,sizeHint);
162}
163
164// insert by pointer without check on multiple insertions
165template<typename CONT, typename RPAR, typename COLL>
166void
167Navigable<CONT, RPAR, COLL>::insertElement(const CONT*
168 ptrObjectContainer,
169 const constituent_type*
170 ptrObject,
171 const RPAR&
172 refParameter,
173 size_t sizeHint)
174{
175 NavigationDefaults::DefaultChildColl<CONT, RPAR>::insert(
176 this->getConstituents(),
177 ptrObjectContainer,
178 ptrObject,
179 refParameter,
180 sizeHint
181 );
182}
183
184// insert by index without check on multiple insertions
185template<typename CONT, typename RPAR, typename COLL>
186void
187Navigable<CONT, RPAR, COLL>::insertElement(const CONT*
188 ptrObjectContainer,
189 const external_index_type&
190 refIndex,
191 const RPAR&
192 refParameter,
193 size_t sizeHint)
194{
195 NavigationDefaults::DefaultChildColl<CONT, RPAR>::insert(
196 this->getConstituents(),
197 ptrObjectContainer,
198 refIndex,
199 refParameter,
200 sizeHint
201 );
202}
203
204// insert by index without check on multiple insertions
205// store is supplied explicitly.
206template<typename CONT, typename RPAR, typename COLL>
207void
208Navigable<CONT, RPAR, COLL>::insertElement(const CONT*
209 ptrObjectContainer,
210 const external_index_type&
211 refIndex,
212 IProxyDict* sg,
213 const RPAR&
214 refParameter,
215 size_t sizeHint)
216{
217 NavigationDefaults::DefaultChildColl<CONT, RPAR>::insert(
218 this->getConstituents(),
219 ptrObjectContainer,
220 refIndex,
221 sg,
222 refParameter,
223 sizeHint
224 );
225}
226
227// insert by ElementLink without check on multiple insertions
228template<typename CONT, typename RPAR, typename COLL>
229void
230Navigable<CONT, RPAR, COLL>::insertElement(const ElementLink<CONT>& el,
231 const RPAR&
232 refParameter,
233 size_t sizeHint)
234{
235 NavigationDefaults::DefaultChildColl<CONT, RPAR>::insert(
236 this->getConstituents(),
237 &el,
238 refParameter,
239 sizeHint
240 );
241}
242 ////////////////////////////////
243 // Object Removal and Finding //
244 ////////////////////////////////
245
246// reweight object
247template<typename CONT, typename RPAR, typename COLL>
248void
249Navigable<CONT,RPAR,COLL>::reweight(const constituent_type* ptrObject,
250 const RPAR& refParm)
251{
252 NavigationDefaults::DefaultChildColl<CONT,RPAR>::
253 changeParm(this->getConstituents(),ptrObject,refParm);
254}
255template<typename CONT, typename RPAR, typename COLL>
256void
257Navigable<CONT,RPAR,COLL>::reweight(const CONT* ptrContainer,
258 const external_index_type& refIndex,
259 const RPAR& refParm)
260{
261 NavigationDefaults::DefaultChildColl<CONT,RPAR>::
262 changeParm(this->getConstituents(),ptrContainer,refIndex,refParm);
263}
264template<typename CONT, typename RPAR, typename COLL>
265void
266Navigable<CONT,RPAR,COLL>::reweight(object_iter& objectIter,
267 const RPAR& refParm)
268{
269 NavigationDefaults::DefaultChildColl<CONT,RPAR>::
270 changeParm(this->getConstituents(),(*objectIter),refParm);
271}
272
273
274// remove object by pointer
275template<typename CONT, typename RPAR, typename COLL>
276bool
277Navigable<CONT, RPAR, COLL>::remove(const constituent_type* ptrObject)
278{
279 // needs to be the non-const ref!
280 constituent_coll& refConstituents = this->getConstituents();
281 return
282 NavigationDefaults::DefaultChildColl<CONT, RPAR>::remove(refConstituents,
283 ptrObject);
284}
285
286// remove object by collection index
287template<typename CONT, typename RPAR, typename COLL>
288bool
289Navigable<CONT, RPAR, COLL>::remove( const CONT* ptrObjectContainer,
290 const external_index_type& refIndex)
291{
292 return this->remove((*ptrObjectContainer)[refIndex]);
293}
294
295// replace old object container with a new container
296template<typename CONT, typename RPAR, typename COLL>
297bool
298Navigable<CONT, RPAR, COLL>::replace(const CONT* newObjectContainer)
299{
300 // needs to be the non-const ref!
301 constituent_coll& refConstituents = this->getConstituents();
302 return
303 NavigationDefaults::DefaultChildColl<CONT, RPAR>::replace(refConstituents,
304 *newObjectContainer);
305
306}
307
308
309
310// test if object is in internal container
311template<typename CONT, typename RPAR, typename COLL>
312bool
313Navigable<CONT, RPAR, COLL>::contains(const constituent_type* ptrObject) const
314{
315 return
316 NavigationDefaults::DefaultChildColl<CONT, RPAR>::contains(
317 this->getConstituents(),
318 ptrObject
319 );
320}
321
322// test if object is in internal container using index in external collection
323template<typename CONT, typename RPAR, typename COLL>
324bool
325Navigable<CONT, RPAR, COLL>::contains( const CONT* ptrObjectContainer,
326 const external_index_type&
327 refIndex) const
328{
329 const constituent_type* ptrObject =
330 (ptrObjectContainer->operator[])(refIndex);
331 return this->contains(ptrObject);
332}
333
334 //////////////////////////
335 // Container Operations //
336 //////////////////////////
337
338// begin() iterator
339template<typename CONT, typename RPAR, typename COLL>
340typename Navigable<CONT, RPAR, COLL>::object_iter
341Navigable<CONT, RPAR, COLL>::begin() const
342{
343 return
344 NavigableIterator<CONT, RPAR, COLL>(this->getConstituents()).begin();
345}
346
347// end() iterator
348template<typename CONT, typename RPAR, typename COLL>
349typename Navigable<CONT, RPAR, COLL>::object_iter
350Navigable<CONT, RPAR, COLL>::end() const
351{
352 return
353 NavigableIterator<CONT, RPAR, COLL>(this->getConstituents()).end();
354}
355
356// size
357template<typename CONT, typename RPAR, typename COLL>
358unsigned int
359Navigable<CONT, RPAR, COLL>::size() const
360{
361 return this->getConstituents().size();
362}
363
364// return pointer to original data object container by object pointer
365template<typename CONT, typename RPAR, typename COLL>
366const CONT*
367Navigable<CONT, RPAR, COLL>::getContainer(const constituent_type*
368 aConstituent) const
369{
370 return
371 NavigationDefaults::DefaultChildColl<CONT,RPAR>::getContPtr(
372 this->getConstituents(),
373 aConstituent
374 );
375}
376
377// return pointer to original data object container by internal iterator
378template<typename CONT, typename RPAR, typename COLL>
379const CONT*
380Navigable<CONT, RPAR, COLL>::getContainer(constituent_const_iter anIter) const
381{
382 return
383 NavigationDefaults::DefaultChildColl<CONT,RPAR>::getContPtr(anIter);
384}
385
386// return pointer to original data object container by object iterator
387template<typename CONT, typename RPAR, typename COLL>
388const CONT*
389Navigable<CONT, RPAR, COLL>::getContainer(object_iter objectIter) const
390{
391 return this->getContainer(objectIter.getInternalIterator());
392}
393
394// get index of data object in original container by object pointer
395template<typename CONT, typename RPAR, typename COLL>
396bool
397Navigable<CONT, RPAR, COLL>::getIndex(const constituent_type* aConstituent,
398 external_index_type& theIndex) const
399{
400 return
401 NavigationDefaults::
402 DefaultChildColl<CONT,RPAR>::getContIndex(this->getConstituents(),
403 aConstituent,
404 theIndex);
405}
406
407// get index of data object in original container by internal iterator
408template<typename CONT, typename RPAR, typename COLL>
409bool
410Navigable<CONT, RPAR, COLL>::getIndex(constituent_const_iter anIter,
411 external_index_type& theIndex) const
412{
413 return
414 NavigationDefaults::
415 DefaultChildColl<CONT,RPAR>::getContIndex(anIter,theIndex);
416}
417
418
419// get index of data object in original container by object iterator
420template<typename CONT, typename RPAR, typename COLL>
421bool
422Navigable<CONT, RPAR, COLL>::getIndex(object_iter objectIter,
423 external_index_type& theIndex) const
424{
425 return this->getIndex(objectIter.getInternalIterator(),theIndex);
426}
427
428 /////////////////////////
429 // Retrieve Parameters //
430 /////////////////////////
431
432// by object pointer
433template<typename CONT, typename RPAR, typename COLL>
434RPAR
435Navigable<CONT, RPAR, COLL>::getParameter(const constituent_type*
436 ptrObject) const
437{
438 return
439 getConstituentPar(
440 NavigationDefaults::DefaultChildColl<CONT, RPAR>::find(getConstituents(),
441 ptrObject)
442 );
443}
444
445// by collection index
446template<typename CONT, typename RPAR, typename COLL>
447RPAR
448Navigable<CONT, RPAR, COLL>::getParameter(const CONT* ptrObjectContainer,
449 const external_index_type&
450 refIndex) const
451{
452 const constituent_type* ptrObject = (*ptrObjectContainer)[refIndex];
453 return this->getParameter(ptrObject);
454}
455
456// by iterator
457template<typename CONT, typename RPAR, typename COLL>
458RPAR
459Navigable<CONT, RPAR, COLL>::getParameter(object_iter& refIter) const
460{
461 return refIter.getParameter();
462}
463
464///////////////////////////////////////////////////////////////////////////////
465// Internally Used Methods //
466///////////////////////////////////////////////////////////////////////////////
467
468 //////////////////////////
469 // Query can be honored //
470 //////////////////////////
471
472// fill token with object pointers (no parameters)
473template <typename CONT, typename RPAR, typename COLL>
474void
475Navigable<CONT, RPAR, COLL>::apply(NavigationToken<constituent_type>&
476 navToken) const
477{
478 // loop on children
479 const constituent_coll& coll = this->getConstituents();
480 constituent_const_iter iCtr(coll.begin());
481 constituent_const_iter iEnd(coll.end());
482 for (; iCtr != iEnd; ++iCtr)
483 {
484 const constituent_type* ptrObject = this->getConstituentPtr(iCtr);
485 if ( ptrObject)
486 navToken.setObject( ptrObject );
487// else
488// setBackNavigationWarning();
489 }
490}
491
492// fill with parameter
493template <typename CONT, typename RPAR, typename COLL>
494void
495Navigable<CONT, RPAR, COLL>::apply(NavigationToken<constituent_type, RPAR>&
496 navToken,
497 const RPAR& aParameter) const
498{
499//debug std::cout << "[Navigable::apply(token,weight)] - invoked with "
500//debug << "token @ " << &navToken
501//debug << " and parameter " << aParameter
502//debug << std::endl;
503
504 // loop children
505 const constituent_coll& coll = this->getConstituents();
506 constituent_const_iter iCtr(coll.begin());
507 constituent_const_iter iEnd(coll.end());
508 for (; iCtr != iEnd; ++iCtr)
509 {
510 const constituent_type* ptrObject = this->getConstituentPtr(iCtr);
511//debug std::cout << "[Navigable::apply(token,weight)] - set constituent @ "
512//debug << ptrObject << ", incoming parameter "
513//debug << aParameter
514//debug << ", new parameter "
515//debug << aParameter * this->getConstituentPar(iCtr)
516//debug << std::endl;
517
518 if ( ptrObject)
519 navToken.setObject(ptrObject,
520 aParameter * this->getConstituentPar(iCtr));
521// else
522// setBackNavigationWarning();
523 }
524}
525
526 //////////////////////
527 // Forwarding query //
528 //////////////////////
529
530// no parameter, query is honored
531template <typename CONT, typename RPAR, typename COLL>
532void
533Navigable<CONT, RPAR,COLL>::toKidsAfterAccept(INavigationToken& navToken) const
534{
535 // loop on children
536 const constituent_coll& coll = this->getConstituents();
537 constituent_const_iter iCtr(coll.begin());
538 constituent_const_iter iEnd(coll.end());
539 for (; iCtr != iEnd; ++iCtr)
540 {
541 const constituent_type* ptrObject = this->getConstituentPtr(iCtr);
542 if ( ptrObject)
543 ptrObject->fillToken( navToken ); // forward query
544// else
545// setBackNavigationWarning();
546 }
547}
548
549// no parameter, query is not honored
550template <typename CONT, typename RPAR, typename COLL>
551void
552Navigable<CONT, RPAR,COLL>::toKidsAfterReject(INavigationToken& navToken) const
553{
554 // loop on children
555 const constituent_coll& coll = this->getConstituents();
556 constituent_const_iter iCtr(coll.begin());
557 constituent_const_iter iEnd(coll.end());
558 for (; iCtr != iEnd; ++iCtr)
559 {
560 const constituent_type* ptrObject = this->getConstituentPtr(iCtr);
561 if ( ptrObject) {
562 navToken.trySetObject( ptrObject ); // navigating inheritance
563 ptrObject->fillToken( navToken ); // forward query
564 }
565// else
566// setBackNavigationWarning();
567 }
568}
569
570// with parameter, query is honored
571template <typename CONT, typename RPAR, typename COLL>
572void
573Navigable<CONT, RPAR, COLL>::toKidsAfterAccept(INavigationToken& navToken,
574 const std::any& aParameter) const
575{
576 // loop on children
577 const constituent_coll& coll = this->getConstituents();
578 constituent_const_iter iCtr(coll.begin());
579 constituent_const_iter iEnd(coll.end());
580 // catch exception thrown by std::any_cast
581 try {
582 // only identical parameter types can be forwarded!
583 RPAR parentPar(std::any_cast<RPAR>(aParameter));
584
585 // Do it like this to avoid creating and destroying a temp any object
586 // each time through the loop.
587 std::any arg (parentPar);
588 RPAR* argp = std::any_cast<RPAR> (&arg);
589
590 for (; iCtr != iEnd; ++iCtr)
591 {
592 const constituent_type* ptrObject = this->getConstituentPtr(iCtr);
593 if ( ptrObject) {
594 *argp = parentPar * this->getConstituentPar(iCtr);
595 ptrObject->fillToken(navToken, arg);
596 }
597// else
598// setBackNavigationWarning();
599 }
600 } catch(std::bad_any_cast&) {
601 // parameter type mismatch: terminate parameter forwarding only
602 for (; iCtr != iEnd; ++iCtr)
603 { //FIXME no weight?
604 const constituent_type* ptrObject = this->getConstituentPtr(iCtr);
605 if (ptrObject)
606 ptrObject->fillToken(navToken, aParameter);
607// else
608// setBackNavigationWarning();
609 }
610 }
611}
612
613// with parameter, query is not honored
614template <typename CONT, typename RPAR, typename COLL>
615void
616Navigable<CONT, RPAR, COLL>::toKidsAfterReject(INavigationToken& navToken,
617 const std::any& aParameter) const
618{
619 // loop on children
620 const constituent_coll& coll = this->getConstituents();
621 constituent_const_iter iCtr(coll.begin());
622 constituent_const_iter iEnd(coll.end());
623 // catch exception thrown by std::any_cast
624 try {
625 // only identical parameter types can be forwarded!
626 RPAR parentPar(std::any_cast<RPAR>(aParameter));
627
628 // Do it like this to avoid creating and destroying a temp any object
629 // each time through the loop.
630 std::any arg (parentPar);
631 RPAR* argp = std::any_cast<RPAR> (&arg);
632
633 for (; iCtr != iEnd; ++iCtr)
634 {
635 const constituent_type* ptrObject = this->getConstituentPtr(iCtr);
636 if (ptrObject) {
637 *argp = parentPar * this->getConstituentPar(iCtr);
638 navToken.trySetObject(ptrObject, arg);
639 ptrObject->fillToken(navToken, arg);
640 }
641// else
642// setBackNavigationWarning();
643
644 }
645 } catch(std::bad_any_cast&) {
646 // parameter type mismatch: terminate parameter forwarding only
647 for (; iCtr != iEnd; ++iCtr)
648 { //FIXME no weight?
649 const constituent_type* ptrObject = this->getConstituentPtr(iCtr);
650 if (ptrObject)
651 ptrObject->fillToken(navToken, aParameter);
652// else
653// setBackNavigationWarning();
654 }
655 }
656}
657
658 ///////////////////////////////////
659 // Internal data object handling //
660 ///////////////////////////////////
661
662// non-const access data objects by iterator
663template <typename CONT, typename RPAR, typename COLL>
664const typename Navigable<CONT, RPAR, COLL>::constituent_type*
665Navigable<CONT, RPAR, COLL>::getConstituentPtr(constituent_iter
666 iter) const
667{
668 return NavigationDefaults::DefaultChildColl<CONT, RPAR>::getChildPtr(iter);
669}
670
671// access data objects by iterator
672template <typename CONT, typename RPAR, typename COLL>
673const typename Navigable<CONT, RPAR, COLL>::constituent_type*
674Navigable<CONT, RPAR, COLL>::getConstituentPtr(constituent_const_iter
675 iter) const
676{
677 return
678 NavigationDefaults::DefaultChildColl<CONT, RPAR>::getChildPtr(iter);
679}
680
681// access relational parameter by iterator
682template <typename CONT, typename RPAR, typename COLL>
683RPAR
684Navigable<CONT, RPAR, COLL>::getConstituentPar(constituent_const_iter
685 iter) const
686{
687 return NavigationDefaults::DefaultChildColl<CONT, RPAR>::getChildPar(iter);
688}
689
690// access relational parameter by iterator
691template <typename CONT, typename RPAR, typename COLL>
692RPAR
693Navigable<CONT, RPAR, COLL>::getConstituentPar(constituent_iter
694 iter) const
695{
696 return NavigationDefaults::DefaultChildColl<CONT, RPAR>::getChildPar(iter);
697}
698
699////////////////
700// Dump Store //
701////////////////
702
703// dump store
704template <typename CONT, typename RPAR, typename COLL>
705void
706Navigable<CONT, RPAR, COLL>::dumpStore() const
707{
708 std::cout << " Navigable class <"
709 << (typeid(*this)).name()
710 << "> @" << this << " with "
711 << this->size()
712 << " referenced objects " << std::endl;
713 object_iter fObj = this->begin();
714 object_iter lObj = this->end();
715 for ( ; fObj != lObj; fObj++ )
716 {
717 external_index_type theIndex = size_t(-1);
718 if ( this->getIndex(fObj,theIndex) )
719 {
720 std::cout << " "
721 << "Object @"
722 << *fObj
723 << " in Storable @"
724 << this->getContainer(fObj)
725 << " at index ["
726 << theIndex
727 << " ] with search indicator \042"
728 << this->contains(*fObj)
729 << "\042 and parameter "
730 << this->getParameter(fObj)
731 << std::endl;
732 }
733 else
734 {
735 std::cout << " "
736 << "Cannot find object @"
737 << *fObj
738 << " in collection, search indicator \042"
739 << this->contains(*fObj)
740 << "\042"
741 << std::endl;
742 }
743
744 }
745
746}