File indexing completed on 2025-01-18 09:58:16
0001
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012
0013
0014
0015
0016
0017
0018
0019
0020
0021
0022
0023
0024
0025
0026
0027
0028
0029
0030
0031
0032
0033
0034
0035
0036
0037
0038
0039
0040 template<class OBJECT>
0041 OBJECT*
0042 G4FastList_iterator<OBJECT>::operator*()
0043 {
0044 if (fpNode == nullptr) return nullptr;
0045 return fpNode->GetObject();
0046 }
0047
0048 template<class OBJECT>
0049 OBJECT*
0050 G4FastList_iterator<OBJECT>::operator->()
0051 {
0052 if (fpNode == nullptr) return nullptr;
0053 return fpNode->GetObject();
0054 }
0055
0056 template<class OBJECT>
0057 const OBJECT*
0058 G4FastList_iterator<OBJECT>::operator*() const
0059 {
0060 if (fpNode == 0) return 0;
0061 return fpNode->GetObject();
0062 }
0063
0064 template<class OBJECT>
0065 const OBJECT*
0066 G4FastList_iterator<OBJECT>::operator->() const
0067 {
0068 if (fpNode == 0) return 0;
0069 return fpNode->GetObject();
0070 }
0071
0072
0073
0074
0075 template<class OBJECT>
0076 G4FastListNode<OBJECT>::G4FastListNode(OBJECT* track) :
0077 fpObject(track), fpPrevious(nullptr), fpNext(nullptr)
0078 {
0079 fAttachedToList = false;
0080 }
0081
0082 template<class OBJECT>
0083 G4FastListNode<OBJECT>::~G4FastListNode()
0084 {
0085 if (fListRef && fListRef->fpList)
0086 {
0087 fListRef->fpList->pop(this);
0088 }
0089 }
0090
0091 template<class OBJECT>
0092 void G4FastListNode<OBJECT>::DetachYourSelf()
0093 {
0094 if(fpObject)
0095 {
0096 fpObject->SetListNode(nullptr);
0097 }
0098 }
0099
0100
0101
0102 template<class OBJECT>
0103 G4FastList<OBJECT>::G4FastList() :
0104 fBoundary()
0105 {
0106 fListRef.reset(new _ListRef<G4FastList<OBJECT> >(this));
0107 fNbObjects = 0;
0108 fBoundary.SetPrevious(&fBoundary);
0109 fBoundary.SetNext(&fBoundary);
0110 fBoundary.fAttachedToList = true;
0111 fpNodeInManyLists = nullptr;
0112 }
0113
0114
0115 template<class OBJECT>
0116 G4FastList<OBJECT>::G4FastList(const G4FastList<OBJECT>& ) :
0117 fBoundary()
0118 {
0119
0120 fNbObjects = 0;
0121 fpNodeInManyLists = 0;
0122 }
0123
0124 template<class OBJECT>
0125 G4FastList<OBJECT>& G4FastList<OBJECT>::operator=(const G4FastList<OBJECT>& other)
0126 {
0127
0128 if (this == &other) return *this;
0129
0130 return *this;
0131 }
0132
0133 template<class OBJECT>
0134 G4FastList<OBJECT>::~G4FastList()
0135 {
0136 if (fNbObjects != 0)
0137 {
0138 G4FastListNode<OBJECT> * __stackedTrack = fBoundary.GetNext();
0139 G4FastListNode<OBJECT> * __nextStackedTrack;
0140
0141
0142 while (__stackedTrack && __stackedTrack != &(fBoundary))
0143 {
0144 __nextStackedTrack = __stackedTrack->GetNext();
0145 OBJECT* __obj = __stackedTrack->GetObject();
0146
0147 delete __stackedTrack;
0148 __stackedTrack = nullptr;
0149
0150 if (__obj)
0151 {
0152
0153 DeleteObject(__obj);
0154 __obj = nullptr;
0155
0156 }
0157 __stackedTrack = __nextStackedTrack;
0158 }
0159 }
0160 fNbObjects = 0;
0161
0162 auto it = fWatchers.begin();
0163 auto _end = fWatchers.end();
0164
0165 for (; it != _end; it++)
0166 {
0167 (*it)->NotifyDeletingList(this);
0168 (*it)->StopWatching(this, false);
0169 }
0170
0171 if (fpNodeInManyLists)
0172 {
0173 delete fpNodeInManyLists;
0174 fpNodeInManyLists = nullptr;
0175 }
0176 }
0177
0178 template<class OBJECT>
0179 bool G4FastList<OBJECT>::empty() const
0180 {
0181 return (fNbObjects == 0);
0182 }
0183
0184 template<class OBJECT>
0185 typename G4FastList<OBJECT>::iterator G4FastList<OBJECT>::begin()
0186 {
0187 return iterator(fBoundary.GetNext());
0188 }
0189
0190 template<class OBJECT>
0191 typename G4FastList<OBJECT>::const_iterator G4FastList<OBJECT>::begin() const
0192 {
0193 return const_iterator(fBoundary.GetNext());
0194 }
0195
0196 template<class OBJECT>
0197 typename G4FastList<OBJECT>::iterator G4FastList<OBJECT>::end()
0198 {
0199 return iterator(&(fBoundary));
0200 }
0201
0202 template<class OBJECT>
0203 typename G4FastList<OBJECT>::const_iterator G4FastList<OBJECT>::end() const
0204 {
0205 return const_iterator(&(fBoundary));
0206 }
0207
0208
0209
0210 template<class OBJECT>
0211 void G4FastList<OBJECT>::push_front(OBJECT* __obj)
0212 {
0213 insert(begin(), __obj);
0214 }
0215
0216 template<class OBJECT>
0217 void G4FastList<OBJECT>::push_back(OBJECT* __obj)
0218 {
0219 insert(end(), __obj);
0220 }
0221
0222 template<class OBJECT>
0223 bool G4FastList<OBJECT>::Holds(const OBJECT* __obj) const
0224 {
0225 node* __node = GetNode(__obj);
0226 if(__node == 0) return false;
0227 return (__node->fListRef->fpList == this);
0228 }
0229
0230
0231 template<class OBJECT>
0232 G4FastListNode<OBJECT>* G4FastList<OBJECT>::Flag(OBJECT* __obj)
0233 {
0234 G4FastListNode<OBJECT>* __node = GetNode(__obj);
0235
0236 if (__node != nullptr)
0237 {
0238
0239 if (__node->fAttachedToList)
0240 {
0241 G4ExceptionDescription exceptionDescription;
0242 exceptionDescription << "An object";
0243 exceptionDescription << " is already attached to a TrackList ";
0244 G4Exception("G4FastList<OBJECT>::Flag", "G4FastList001",
0245 FatalErrorInArgument, exceptionDescription);
0246 }
0247 }
0248 else
0249 {
0250 __node = new G4FastListNode<OBJECT>(__obj);
0251 SetNode(__obj,__node);
0252 }
0253
0254 __node->fAttachedToList = true;
0255 __node->fListRef = fListRef;
0256 return __node;
0257 }
0258
0259 template<class OBJECT>
0260 G4FastListNode<OBJECT>* G4FastList<OBJECT>::CreateNode(OBJECT* __obj)
0261 {
0262 G4FastListNode<OBJECT>* __listNode = Flag(__obj);
0263 return __listNode;
0264 }
0265
0266 template<class OBJECT>
0267 void G4FastList<OBJECT>::Hook(G4FastListNode<OBJECT>* __position,
0268 G4FastListNode<OBJECT>* __toHook)
0269 {
0270
0271
0272
0273
0274
0275
0276 G4FastListNode<OBJECT>* __previous = __position->GetPrevious();
0277 __toHook->SetPrevious(__previous);
0278 __toHook->SetNext(__position);
0279 __position->SetPrevious(__toHook);
0280 __previous->SetNext(__toHook);
0281
0282
0283
0284
0285
0286
0287
0288
0289
0290
0291
0292
0293
0294
0295
0296
0297
0298
0299
0300
0301
0302
0303
0304
0305
0306
0307
0308
0309
0310
0311
0312
0313
0314
0315
0316
0317
0318
0319
0320
0321
0322
0323
0324 fNbObjects++;
0325
0326 if(fWatchers.empty() == false)
0327 {
0328 auto it = fWatchers.begin();
0329 auto _end = fWatchers.end();
0330
0331 for (; it != _end; it++)
0332 {
0333 (*it)->NotifyAddObject(__toHook->GetObject(), this);
0334 }
0335 }
0336 }
0337
0338 template<class OBJECT>
0339 void G4FastListNode<OBJECT>::UnHook()
0340 {
0341 G4FastListNode<OBJECT>* __next_node = this->fpNext;
0342 G4FastListNode<OBJECT>* __prev_node = this->fpPrevious;
0343
0344 if (__prev_node)
0345 {
0346 __prev_node->fpNext = __next_node;
0347 }
0348
0349 if (__next_node)
0350 {
0351 __next_node->fpPrevious = __prev_node;
0352 }
0353 fpNext = nullptr;
0354 fpPrevious = nullptr;
0355 }
0356
0357 template<class OBJECT>
0358 void G4FastList<OBJECT>::Unhook(G4FastListNode<OBJECT>* __toUnHook)
0359 {
0360 __toUnHook->UnHook();
0361
0362 fNbObjects--;
0363
0364 auto it = fWatchers.begin();
0365 auto _end = fWatchers.end();
0366
0367 for (; it != _end; it++)
0368 {
0369 (*it)->NotifyRemoveObject(__toUnHook->GetObject(), this);
0370 }
0371 }
0372
0373 template<class OBJECT>
0374 typename G4FastList<OBJECT>::iterator
0375 G4FastList<OBJECT>::insert(typename G4FastList<OBJECT>::iterator __position,
0376 OBJECT* __obj)
0377 {
0378 G4FastListNode<OBJECT>* __node = CreateNode(__obj);
0379 Hook(__position.fpNode, __node);
0380 return iterator(__node);
0381 }
0382
0383
0384
0385
0386
0387
0388 template<class OBJECT>
0389 void G4FastList<OBJECT>::CheckFlag(G4FastListNode<OBJECT>* __node)
0390 {
0391 if (__node->fListRef->fpList != this)
0392 {
0393 G4ExceptionDescription exceptionDescription;
0394 exceptionDescription << "The object "
0395 << " is not correctly linked to a G4FastList." << G4endl
0396 << "You are probably trying to withdraw this object "
0397 << "from the list but it probably does not belong to "
0398 << "this fast list." << G4endl;
0399 G4Exception("G4FastList<OBJECT>::CheckFlag", "G4FastList002",
0400 FatalErrorInArgument, exceptionDescription);
0401 }
0402 }
0403
0404 template<class OBJECT>
0405 G4FastListNode<OBJECT>* G4FastList<OBJECT>::Unflag(OBJECT* __obj)
0406 {
0407 G4FastListNode<OBJECT>* __node = __GetNode(__obj);
0408 CheckFlag(__node);
0409 __node->fAttachedToList = false;
0410 __node->fListRef.reset();
0411 return __node;
0412 }
0413
0414 template<class OBJECT>
0415 void G4FastList<OBJECT>::Unflag(G4FastListNode<OBJECT>* __node)
0416 {
0417 CheckFlag(__node);
0418 __node->fAttachedToList = false;
0419 __node->fListRef.reset();
0420 return;
0421 }
0422
0423 template<class OBJECT>
0424 OBJECT* G4FastList<OBJECT>::pop_back()
0425 {
0426 if (fNbObjects == 0) return 0;
0427 G4FastListNode<OBJECT> * __aNode = fBoundary.GetPrevious();
0428 Unhook(__aNode);
0429 Unflag(__aNode);
0430 return __aNode->GetObject();
0431 }
0432
0433 template<class OBJECT>
0434 typename G4FastList<OBJECT>::iterator G4FastList<OBJECT>::pop(OBJECT* __obj)
0435 {
0436 G4FastListNode<OBJECT>* __node = Unflag(__obj);
0437 iterator __next(__node->GetNext());
0438 Unhook(__node);
0439 return __next;
0440 }
0441
0442 template<class OBJECT>
0443 typename G4FastList<OBJECT>::iterator
0444 G4FastList<OBJECT>::pop(G4FastListNode<OBJECT>* __node)
0445 {
0446 Unflag(__node);
0447 iterator __next(__node->GetNext());
0448 Unhook(__node);
0449 return __next;
0450 }
0451
0452 template<class OBJECT>
0453 typename G4FastList<OBJECT>::iterator G4FastList<OBJECT>::erase(OBJECT* __obj)
0454 {
0455 G4FastListNode<OBJECT>* __next_node = EraseListNode(__obj);
0456
0457 DeleteObject(__obj);
0458 __obj = nullptr;
0459
0460 iterator __next(__next_node);
0461 return __next;
0462 }
0463
0464 template<class OBJECT>
0465 G4FastListNode<OBJECT>* G4FastList<OBJECT>::EraseListNode(OBJECT* __obj)
0466 {
0467 G4FastListNode<OBJECT>* __node = Unflag(__obj);
0468 __node->DetachYourSelf();
0469 G4FastListNode<OBJECT>* __next = __node->GetNext();
0470 Unhook(__node);
0471 delete __node;
0472 return __next;
0473 }
0474
0475 template<class OBJECT>
0476 void G4FastList<OBJECT>::DeleteObject(OBJECT*)
0477 {
0478
0479 }
0480
0481 template<class OBJECT>
0482 void G4FastList<OBJECT>::remove(OBJECT* __obj)
0483 {
0484 this->erase(__obj);
0485 }
0486
0487 template<class OBJECT>
0488 typename G4FastList<OBJECT>::iterator G4FastList<OBJECT>::pop(iterator __first,
0489 iterator __last)
0490 {
0491 if (fNbObjects == 0) return iterator(&fBoundary);
0492
0493 while (__first != __last)
0494 {
0495 if (__first.fpNode) __first = pop(*__first);
0496 }
0497 return __last;
0498 }
0499
0500 template<class OBJECT>
0501 typename G4FastList<OBJECT>::iterator G4FastList<OBJECT>::erase(iterator __first,
0502 iterator __last)
0503 {
0504 if (fNbObjects == 0) return iterator(&fBoundary);
0505
0506 while (__first != __last)
0507 {
0508 if (__first.fpNode) __first = erase(*__first);
0509 }
0510 return __last;
0511 }
0512
0513 template<class OBJECT>
0514 void G4FastList<OBJECT>::clear()
0515 {
0516 erase(begin(), end());
0517 }
0518
0519 template<class OBJECT>
0520 void G4FastList<OBJECT>::transferTo(G4FastList<OBJECT>* __destination)
0521 {
0522 if (fNbObjects == 0) return;
0523
0524 if (__destination->fNbObjects == 0)
0525 {
0526
0527 if(__destination->fWatchers.empty()==false)
0528 {
0529 auto it = __destination->fWatchers.begin();
0530 auto _end = __destination->fWatchers.end();
0531
0532
0533
0534
0535
0536 for (; it != _end; it++)
0537 {
0538 for(iterator it2 = this->begin() ;
0539 it2 != this->end(); ++it2
0540 )
0541 {
0542 (*it)->NotifyAddObject(*it2, this);
0543 }
0544 }
0545 }
0546
0547 __destination->fNbObjects = this->fNbObjects;
0548
0549 __destination->fBoundary.SetNext(fBoundary.GetNext());
0550 __destination->fBoundary.SetPrevious(fBoundary.GetPrevious());
0551 fBoundary.GetNext()->SetPrevious(&__destination->fBoundary);
0552 fBoundary.GetPrevious()->SetNext(&__destination->fBoundary);
0553 }
0554 else
0555 {
0556 if(__destination->fWatchers.empty()==false)
0557 {
0558 auto it = __destination->fWatchers.begin();
0559 auto _end = __destination->fWatchers.end();
0560
0561 for (; it != _end; it++)
0562 {
0563 for(iterator it2 = this->begin() ;
0564 it2 != this->end(); ++it2)
0565 {
0566 (*it)->NotifyAddObject(*it2, this);
0567 }
0568 }
0569 }
0570
0571 node* lastNode = __destination->fBoundary.GetPrevious();
0572 lastNode->SetNext(fBoundary.GetNext());
0573 fBoundary.GetNext()->SetPrevious(lastNode);
0574 __destination->fBoundary.SetPrevious(fBoundary.GetPrevious());
0575 fBoundary.GetPrevious()->SetNext(&__destination->fBoundary);
0576
0577 __destination->fNbObjects += this->fNbObjects;
0578 }
0579
0580 fNbObjects = 0;
0581 this->fBoundary.SetPrevious(&this->fBoundary);
0582 this->fBoundary.SetNext(&this->fBoundary);
0583
0584 fListRef->fpList = __destination;
0585 }
0586
0587
0588
0589
0590
0591
0592 template<class OBJECT>
0593 G4FastListNode<OBJECT>* G4FastList<OBJECT>::__GetNode(OBJECT* __obj)
0594 {
0595 G4FastListNode<OBJECT>* __node = GetNode(__obj);
0596
0597 if (__node == nullptr)
0598 {
0599 G4ExceptionDescription exceptionDescription;
0600 exceptionDescription << "The object ";
0601 exceptionDescription << " was not connected to any trackList ";
0602 G4Exception("G4FastList<OBJECT>::Unflag", "G4FastList003",
0603 FatalErrorInArgument, exceptionDescription);
0604 return nullptr;
0605 }
0606 return __node;
0607 }
0608
0609 template<class OBJECT>
0610 G4FastListNode<OBJECT>* G4FastList<OBJECT>::GetNode(OBJECT* __obj)
0611 {
0612 G4FastListNode<OBJECT>* __node = __obj->GetListNode();
0613 return __node;
0614 }
0615
0616 template<class OBJECT>
0617 void G4FastList<OBJECT>::SetNode(OBJECT* __obj,
0618 G4FastListNode<OBJECT>* __node)
0619 {
0620 __obj->SetListNode(__node);
0621 }
0622
0623 template<class OBJECT>
0624 G4FastList<OBJECT>* G4FastList<OBJECT>::GetList(OBJECT* __obj)
0625 {
0626 G4FastListNode<OBJECT>* __node = GetNode(__obj);
0627
0628 if (__node == 0) return 0;
0629 if (__node->fListRef == nullptr) return 0;
0630
0631 return __node->fListRef->fpTrackList;
0632 }
0633
0634 template<class OBJECT>
0635 G4FastList<OBJECT>*
0636 G4FastList<OBJECT>::GetList(G4FastListNode<OBJECT>* __node)
0637 {
0638 if (__node == nullptr) return nullptr;
0639 if (__node->fListRef == nullptr) return nullptr;
0640
0641 return __node->fListRef->fpList;
0642 }
0643
0644 template<class OBJECT>
0645 void G4FastList<OBJECT>::Pop(OBJECT* __obj)
0646 {
0647 G4FastListNode<OBJECT>* __node = G4FastList<OBJECT>::GetNode(__obj);
0648 G4FastList<OBJECT>* __list = G4FastList<OBJECT>::GetList(__node);
0649 if (__list) __list->pop(__node);
0650 }
0651
0652