CMS 3D CMS Logo

 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Macros Pages
IndexIntoFile.cc
Go to the documentation of this file.
4 
5 #include <algorithm>
6 #include <ostream>
7 #include <iomanip>
8 
9 namespace edm {
10 
16 
17  IndexIntoFile::IndexIntoFile() : transients_(),
18  processHistoryIDs_(),
19  runOrLumiEntries_() {
20  }
21 
23  }
24 
26  return processHistoryIDs_.at(i);
27  }
28 
29  std::vector<ProcessHistoryID> const& IndexIntoFile::processHistoryIDs() const {
30  return processHistoryIDs_;
31  }
32 
33  void
34  IndexIntoFile::addEntry(ProcessHistoryID const& processHistoryID,
39  int index = 0;
40  // First see if the ProcessHistoryID is the same as the previous one.
41  // This is just a performance optimization. We expect to usually get
42  // many in a row that are the same.
44  processHistoryID == processHistoryIDs_[previousAddedIndex()]) {
45  index = previousAddedIndex();
46  }
47  // If it was not the same as the previous one then search through the
48  // entire vector. If it is not there, it needs to be added at the
49  // end.
50  else {
51  index = 0;
52  while (index < static_cast<int>(processHistoryIDs_.size()) &&
53  processHistoryIDs_[index] != processHistoryID) {
54  ++index;
55  }
56  if (index == static_cast<int>(processHistoryIDs_.size())) {
57  processHistoryIDs_.push_back(processHistoryID);
58  }
59  }
61 
62  assert((currentRun() == run && currentIndex() == index) || currentRun() == invalidRun);
63  if (lumi == invalidLumi) {
64  if (currentLumi() != invalidLumi) {
66  << "In IndexIntoFile::addEntry. Entries were added in illegal order.\n"
67  << "This means the IndexIntoFile product in the output file will be corrupted.\n"
68  << "The output file will be unusable for most purposes.\n"
69  << "If this occurs after an unrelated exception was thrown in\n"
70  << "endLuminosityBlock or endRun then ignore this exception and fix\n"
71  << "the primary exception. This is an expected side effect.\n"
72  << "Otherwise please report this to the core framework developers\n";
73  }
77  std::pair<IndexRunKey, EntryNumber_t> firstRunEntry(IndexRunKey(index, run), entry);
78  runToFirstEntry().insert(firstRunEntry);
79  RunOrLumiEntry runEntry(runToFirstEntry()[IndexRunKey(index, run)], invalidEntry, entry, index, run, lumi, invalidEntry, invalidEntry);
80  runOrLumiEntries_.push_back(runEntry);
81  }
82  else {
83  assert(currentLumi() == lumi || currentLumi() == invalidLumi);
84  if (currentRun() == invalidRun) {
85  currentRun() = run;
86  currentIndex() = index;
87  }
88  if (event == invalidEvent) {
90  std::pair<IndexRunLumiKey, EntryNumber_t> firstLumiEntry(IndexRunLumiKey(index, run, lumi), entry);
91  lumiToFirstEntry().insert(firstLumiEntry);
92  RunOrLumiEntry lumiEntry(invalidEntry, lumiToFirstEntry()[IndexRunLumiKey(index, run, lumi)],
93  entry, index, run, lumi, beginEvents(), endEvents());
94  runOrLumiEntries_.push_back(lumiEntry);
97  }
98  else {
100  if (beginEvents() == invalidEntry) {
101  currentLumi() = lumi;
102  beginEvents() = entry;
103  endEvents() = beginEvents() + 1;
104  }
105  else {
106  assert(currentLumi() == lumi);
107  assert(entry == endEvents());
108  ++endEvents();
109  }
110  }
111  }
112  }
113 
115  if (runOrLumiEntries_.empty() || !runOrLumiIndexes().empty()) {
116  return;
117  }
118  runOrLumiIndexes().reserve(runOrLumiEntries_.size());
119 
120  int index = 0;
121  for (std::vector<RunOrLumiEntry>::const_iterator iter = runOrLumiEntries_.begin(),
122  iEnd = runOrLumiEntries_.end();
123  iter != iEnd;
124  ++iter, ++index) {
125  runOrLumiIndexes().push_back(RunOrLumiIndexes(iter->processHistoryIDIndex(),
126  iter->run(),
127  iter->lumi(),
128  index));
129  }
131 
132  long long beginEventNumbers = 0;
133 
134  std::vector<RunOrLumiIndexes>::iterator beginOfLumi = runOrLumiIndexes().begin();
135  std::vector<RunOrLumiIndexes>::iterator endOfLumi = beginOfLumi;
136  std::vector<RunOrLumiIndexes>::iterator iEnd = runOrLumiIndexes().end();
137  while (true) {
138  while (beginOfLumi != iEnd && beginOfLumi->isRun()) {
139  ++beginOfLumi;
140  }
141  if (beginOfLumi == iEnd) break;
142 
143  endOfLumi = beginOfLumi + 1;
144  while (endOfLumi != iEnd &&
145  beginOfLumi->processHistoryIDIndex() == endOfLumi->processHistoryIDIndex() &&
146  beginOfLumi->run() == endOfLumi->run() &&
147  beginOfLumi->lumi() == endOfLumi->lumi()) {
148  ++endOfLumi;
149  }
150  int nEvents = 0;
151  for (std::vector<RunOrLumiIndexes>::iterator iter = beginOfLumi;
152  iter != endOfLumi;
153  ++iter) {
154  if (runOrLumiEntries_[iter->indexToGetEntry()].beginEvents() != invalidEntry) {
155  nEvents += runOrLumiEntries_[iter->indexToGetEntry()].endEvents() -
156  runOrLumiEntries_[iter->indexToGetEntry()].beginEvents();
157  }
158  }
159  for (std::vector<RunOrLumiIndexes>::iterator iter = beginOfLumi;
160  iter != endOfLumi;
161  ++iter) {
162  iter->setBeginEventNumbers(beginEventNumbers);
163  iter->setEndEventNumbers(beginEventNumbers + nEvents);
164  }
165  beginEventNumbers += nEvents;
166  beginOfLumi = endOfLumi;
167  }
168  assert(runOrLumiIndexes().size() == runOrLumiEntries_.size());
169  }
170 
171  void
173  fillEventNumbersOrEntries(true, false);
174  }
175 
176  void
178  fillEventNumbersOrEntries(false, true);
179  }
180 
181  void
182  IndexIntoFile::fillEventNumbersOrEntries(bool needEventNumbers, bool needEventEntries) const {
183  if (numberOfEvents() == 0) {
184  return;
185  }
186 
187  if (needEventNumbers && !eventNumbers().empty()) {
188  needEventNumbers = false;
189  }
190 
191  if (needEventEntries && !eventEntries().empty()) {
192  needEventEntries = false;
193  }
194 
195  if (needEventNumbers && !eventEntries().empty()) {
196  assert(numberOfEvents() == eventEntries().size());
197  eventNumbers().reserve(eventEntries().size());
199  eventNumbers().push_back(eventEntries()[entry].event());
200  }
201  return;
202  }
203 
204  if (!needEventNumbers && !needEventEntries) {
205  return;
206  }
207 
209 
210  if (needEventNumbers) {
212  }
213  if (needEventEntries) {
214  eventEntries().resize(numberOfEvents());
215  }
216 
217  long long offset = 0;
218  long long previousBeginEventNumbers = -1LL;
219 
220  for (SortedRunOrLumiItr runOrLumi = beginRunOrLumi(), runOrLumiEnd = endRunOrLumi();
221  runOrLumi != runOrLumiEnd; ++runOrLumi) {
222 
223  if (runOrLumi.isRun()) continue;
224 
225  long long beginEventNumbers = 0;
226  long long endEventNumbers = 0;
227  EntryNumber_t beginEventEntry = -1LL;
228  EntryNumber_t endEventEntry = -1LL;
229  runOrLumi.getRange(beginEventNumbers, endEventNumbers, beginEventEntry, endEventEntry);
230 
231  // This is true each time one hits a new lumi section (except if the previous lumi had
232  // no events, in which case the offset is still 0 anyway)
233  if (beginEventNumbers != previousBeginEventNumbers) offset = 0;
234 
235  for (EntryNumber_t entry = beginEventEntry; entry != endEventEntry; ++entry) {
236  if (needEventNumbers) {
237  eventNumbers().at((entry - beginEventEntry) + offset + beginEventNumbers) = unsortedEventNumbers().at(entry);
238  }
239  if (needEventEntries) {
240  eventEntries().at((entry - beginEventEntry) + offset + beginEventNumbers) =
242  }
243  }
244 
245  previousBeginEventNumbers = beginEventNumbers;
246  offset += endEventEntry - beginEventEntry;
247  }
248  if (needEventNumbers) {
249  sortEvents();
250  assert(numberOfEvents() == eventNumbers().size());
251  }
252  if (needEventEntries) {
254  assert(numberOfEvents() == eventEntries().size());
255  }
256  }
257 
258  void
260  if (numberOfEvents() == 0 || !unsortedEventNumbers().empty()) {
261  return;
262  }
264 
265  // The main purpose for the existence of the unsortedEventNumbers
266  // vector is that it can easily be filled by reading through
267  // the EventAuxiliary branch in the same order as the TTree
268  // entries. fillEventNumbersOrEntries can then use this information
269  // instead of using getEventNumberOfEntry directly and reading
270  // the branch in a different order.
273  }
274  }
275 
276  // We are closing the input file, but we need to keep event numbers.
277  // We can delete the other transient collections by using the swap trick.
278 
279  void
281  std::vector<EventEntry>().swap(eventEntries());
282  std::vector<RunOrLumiIndexes>().swap(runOrLumiIndexes());
283  std::vector<EventNumber_t>().swap(unsortedEventNumbers());
285  }
286 
287  void
289  std::vector<EventNumber_t>().swap(unsortedEventNumbers());
290  }
291 
292  void
293  IndexIntoFile::fixIndexes(std::vector<ProcessHistoryID> & processHistoryIDs) {
294 
295  std::map<int, int> oldToNewIndex;
296  for (std::vector<ProcessHistoryID>::const_iterator iter = processHistoryIDs_.begin(),
297  iEnd = processHistoryIDs_.end();
298  iter != iEnd;
299  ++iter) {
300  std::vector<ProcessHistoryID>::const_iterator iterExisting =
301  std::find(processHistoryIDs.begin(), processHistoryIDs.end(), *iter);
302  if (iterExisting == processHistoryIDs.end()) {
303  oldToNewIndex[iter - processHistoryIDs_.begin()] = processHistoryIDs.size();
304  processHistoryIDs.push_back(*iter);
305  }
306  else {
307  oldToNewIndex[iter - processHistoryIDs_.begin()] = iterExisting - processHistoryIDs.begin();
308  }
309  }
311 
312  for (std::vector<RunOrLumiEntry>::iterator iter = runOrLumiEntries_.begin(),
313  iEnd = runOrLumiEntries_.end();
314  iter != iEnd;
315  ++iter) {
316  iter->setProcessHistoryIDIndex(oldToNewIndex[iter->processHistoryIDIndex()]);
317  }
318  }
319 
321  for (std::vector<RunOrLumiEntry>::iterator iter = runOrLumiEntries_.begin(),
322  iEnd = runOrLumiEntries_.end();
323  iter != iEnd;
324  ++iter) {
325  std::map<IndexRunKey, EntryNumber_t>::const_iterator firstRunEntry =
326  runToFirstEntry().find(IndexRunKey(iter->processHistoryIDIndex(), iter->run()));
327  if (firstRunEntry == runToFirstEntry().end()) {
329  << "In IndexIntoFile::sortVector_Run_Or_Lumi_Entries. A run entry is missing.\n"
330  << "This means the IndexIntoFile product in the output file will be corrupted.\n"
331  << "The output file will be unusable for most purposes.\n"
332  << "If this occurs after an unrelated exception was thrown in\n"
333  << "endLuminosityBlock or endRun then ignore this exception and fix\n"
334  << "the primary exception. This is an expected side effect.\n"
335  << "Otherwise please report this to the core framework developers\n";
336  }
337  iter->setOrderPHIDRun(firstRunEntry->second);
338  }
340  }
341 
344  std::vector<RunOrLumiIndexes>::iterator beginOfLumi = runOrLumiIndexes().begin();
345  std::vector<RunOrLumiIndexes>::iterator endOfLumi = beginOfLumi;
346  std::vector<RunOrLumiIndexes>::iterator iEnd = runOrLumiIndexes().end();
347  while (true) {
348  while (beginOfLumi != iEnd && beginOfLumi->isRun()) {
349  ++beginOfLumi;
350  }
351  if (beginOfLumi == iEnd) break;
352 
353  endOfLumi = beginOfLumi + 1;
354  while (endOfLumi != iEnd &&
355  beginOfLumi->processHistoryIDIndex() == endOfLumi->processHistoryIDIndex() &&
356  beginOfLumi->run() == endOfLumi->run() &&
357  beginOfLumi->lumi() == endOfLumi->lumi()) {
358  ++endOfLumi;
359  }
360  assert(beginOfLumi->endEventNumbers() >= 0);
361  assert(beginOfLumi->endEventNumbers() <= static_cast<long long>(eventNumbers().size()));
362  std::sort(eventNumbers().begin() + beginOfLumi->beginEventNumbers(),
363  eventNumbers().begin() + beginOfLumi->endEventNumbers());
364  beginOfLumi = endOfLumi;
365  }
366  }
367 
370  std::vector<RunOrLumiIndexes>::iterator beginOfLumi = runOrLumiIndexes().begin();
371  std::vector<RunOrLumiIndexes>::iterator endOfLumi = beginOfLumi;
372  std::vector<RunOrLumiIndexes>::iterator iEnd = runOrLumiIndexes().end();
373  while (true) {
374  while (beginOfLumi != iEnd && beginOfLumi->isRun()) {
375  ++beginOfLumi;
376  }
377  if (beginOfLumi == iEnd) break;
378 
379  endOfLumi = beginOfLumi + 1;
380  while (endOfLumi != iEnd &&
381  beginOfLumi->processHistoryIDIndex() == endOfLumi->processHistoryIDIndex() &&
382  beginOfLumi->run() == endOfLumi->run() &&
383  beginOfLumi->lumi() == endOfLumi->lumi()) {
384  ++endOfLumi;
385  }
386  assert(beginOfLumi->endEventNumbers() >= 0);
387  assert(beginOfLumi->endEventNumbers() <= static_cast<long long>(eventEntries().size()));
388  std::sort(eventEntries().begin() + beginOfLumi->beginEventNumbers(),
389  eventEntries().begin() + beginOfLumi->endEventNumbers());
390  beginOfLumi = endOfLumi;
391  }
392  }
393 
395  if (empty()) {
396  return end(sortOrder);
397  }
398  IndexIntoFileItr iter(this,
399  sortOrder,
400  kRun,
401  0,
402  invalidIndex,
403  invalidIndex,
404  0,
405  0);
406  iter.initializeRun();
407  return iter;
408  }
409 
411  return IndexIntoFileItr(this,
412  sortOrder,
413  kEnd,
414  invalidIndex,
415  invalidIndex,
416  invalidIndex,
417  0,
418  0);
419  }
420 
422  EntryNumber_t maxEntry = invalidEntry;
423  for(IndexIntoFileItr it = begin(sortOrder), itEnd = end(sortOrder); it != itEnd; ++it) {
424  if(it.getEntryType() == kEvent) {
425  if(it.entry() < maxEntry) {
426  return false;
427  }
428  maxEntry = it.entry();
429  }
430  }
431  return true;
432  }
433 
434  bool IndexIntoFile::empty() const {
435  return runOrLumiEntries().empty();
436  }
437 
441 
442  bool lumiMissing = (lumi == 0 && event != 0);
443 
444  std::vector<RunOrLumiIndexes>::const_iterator it;
445  std::vector<RunOrLumiIndexes>::const_iterator iEnd = runOrLumiIndexes().end();
446  std::vector<RunOrLumiIndexes>::const_iterator phEnd;
447 
448  // Loop over ranges of entries with the same ProcessHistoryID
449  for (std::vector<RunOrLumiIndexes>::const_iterator phBegin = runOrLumiIndexes().begin();
450  phBegin != iEnd;
451  phBegin = phEnd) {
452 
453  RunOrLumiIndexes el(phBegin->processHistoryIDIndex(), run, lumi, 0);
454  phEnd = std::upper_bound(phBegin, iEnd, el, Compare_Index());
455 
456  std::vector<RunOrLumiIndexes>::const_iterator iRun = std::lower_bound(phBegin, phEnd, el, Compare_Index_Run());
457 
458  if (iRun == phEnd || iRun->run() != run) continue;
459 
460  if (lumi == invalidLumi && event == invalidEvent) {
461  IndexIntoFileItr indexItr(this,
463  kRun,
464  iRun - runOrLumiIndexes().begin(),
465  invalidIndex,
466  invalidIndex,
467  0,
468  0);
469  indexItr.initializeRun();
470  return indexItr;
471  }
472 
473  std::vector<RunOrLumiIndexes>::const_iterator iRunEnd = std::upper_bound(iRun, phEnd, el, Compare_Index_Run());
474  if (!lumiMissing) {
475 
476  std::vector<RunOrLumiIndexes>::const_iterator iLumi = std::lower_bound(iRun, iRunEnd, el);
477  if (iLumi == iRunEnd || iLumi->lumi() != lumi) continue;
478 
479  if (event == invalidEvent) {
480  IndexIntoFileItr indexItr(this,
482  kRun,
483  iRun - runOrLumiIndexes().begin(),
484  iLumi - runOrLumiIndexes().begin(),
485  invalidIndex,
486  0,
487  0);
488  indexItr.initializeLumi();
489  return indexItr;
490  }
491 
492  long long beginEventNumbers = iLumi->beginEventNumbers();
493  long long endEventNumbers = iLumi->endEventNumbers();
494  if (beginEventNumbers >= endEventNumbers) continue;
495 
496 
497  long long indexToEvent = 0;
498  if (!eventEntries().empty()) {
499  std::vector<EventEntry>::const_iterator eventIter = std::lower_bound(eventEntries().begin() + beginEventNumbers,
500  eventEntries().begin() + endEventNumbers,
501  EventEntry(event, invalidEntry));
502  if (eventIter == (eventEntries().begin() + endEventNumbers) ||
503  eventIter->event() != event) continue;
504 
505  indexToEvent = eventIter - eventEntries().begin() - beginEventNumbers;
506  } else {
508  std::vector<EventNumber_t>::const_iterator eventIter = std::lower_bound(eventNumbers().begin() + beginEventNumbers,
509  eventNumbers().begin() + endEventNumbers,
510  event);
511  if (eventIter == (eventNumbers().begin() + endEventNumbers) ||
512  *eventIter != event) continue;
513 
514  indexToEvent = eventIter - eventNumbers().begin() - beginEventNumbers;
515  }
516  return IndexIntoFileItr(this,
518  kRun,
519  iRun - runOrLumiIndexes().begin(),
520  iLumi - runOrLumiIndexes().begin(),
521  iLumi - runOrLumiIndexes().begin(),
522  indexToEvent,
523  endEventNumbers - beginEventNumbers);
524  }
525  if (lumiMissing) {
526 
527  std::vector<RunOrLumiIndexes>::const_iterator iLumi = iRun;
528  while (iLumi != iRunEnd && iLumi->lumi() == invalidLumi) {
529  ++iLumi;
530  }
531  if (iLumi == iRunEnd) continue;
532 
533  std::vector<RunOrLumiIndexes>::const_iterator lumiEnd;
534  for ( ;
535  iLumi != iRunEnd;
536  iLumi = lumiEnd) {
537 
538  RunOrLumiIndexes elWithLumi(phBegin->processHistoryIDIndex(), run, iLumi->lumi(), 0);
539  lumiEnd = std::upper_bound(iLumi, iRunEnd, elWithLumi);
540 
541  long long beginEventNumbers = iLumi->beginEventNumbers();
542  long long endEventNumbers = iLumi->endEventNumbers();
543  if (beginEventNumbers >= endEventNumbers) continue;
544 
545  long long indexToEvent = 0;
546  if (!eventEntries().empty()) {
547  std::vector<EventEntry>::const_iterator eventIter = std::lower_bound(eventEntries().begin() + beginEventNumbers,
548  eventEntries().begin() + endEventNumbers,
549  EventEntry(event, invalidEntry));
550  if (eventIter == (eventEntries().begin() + endEventNumbers) ||
551  eventIter->event() != event) continue;
552  indexToEvent = eventIter - eventEntries().begin() - beginEventNumbers;
553  } else {
555  std::vector<EventNumber_t>::const_iterator eventIter = std::lower_bound(eventNumbers().begin() + beginEventNumbers,
556  eventNumbers().begin() + endEventNumbers,
557  event);
558  if (eventIter == (eventNumbers().begin() + endEventNumbers) ||
559  *eventIter != event) continue;
560  indexToEvent = eventIter - eventNumbers().begin() - beginEventNumbers;
561  }
562  return IndexIntoFileItr(this,
564  kRun,
565  iRun - runOrLumiIndexes().begin(),
566  iLumi - runOrLumiIndexes().begin(),
567  iLumi - runOrLumiIndexes().begin(),
568  indexToEvent,
569  endEventNumbers - beginEventNumbers);
570  }
571  }
572  } // Loop over ProcessHistoryIDs
573 
574  return IndexIntoFileItr(this,
576  kEnd,
577  invalidIndex,
578  invalidIndex,
579  invalidIndex,
580  0,
581  0);
582 
583  }
584 
587  if (sortOrder == IndexIntoFile::numericalOrder) {
588  return findPosition(run, lumi, event); // a faster algorithm
589  }
590  IndexIntoFileItr itr = begin(sortOrder);
591  IndexIntoFileItr itrEnd = end(sortOrder);
592 
593  while (itr != itrEnd) {
594  if (itr.run() != run) {
595  itr.advanceToNextRun();
596  }
597  else {
598  if (lumi == invalidLumi && event == invalidEvent) {
599  return itr;
600  }
601  else if (lumi != invalidLumi && itr.peekAheadAtLumi() != lumi) {
602  if (!itr.skipLumiInRun()) {
603  itr.advanceToNextRun();
604  }
605  }
606  else {
607  if (event == invalidEvent) {
608  return itr;
609  }
610  else {
612  if (eventNumber == event) {
613  return itr;
614  }
615  else {
616  if (!itr.skipToNextEventInLumi()) {
617  if (!itr.skipLumiInRun()) {
618  itr.advanceToNextRun();
619  }
620  }
621  }
622  }
623  }
624  }
625  }
626  return itrEnd;
627  }
628 
631  assert(event != invalidEvent);
632  IndexIntoFileItr iter = findPosition(run, lumi, event);
633  iter.advanceToEvent();
634  return iter;
635  }
636 
639  assert(lumi != invalidLumi);
640  IndexIntoFileItr iter = findPosition(run, lumi, 0U);
641  iter.advanceToLumi();
642  return iter;
643  }
644 
647  return findPosition(run, 0U, 0U);
648  }
649 
650  bool
652  return event ? containsEvent(run, lumi, event) : (lumi ? containsLumi(run, lumi) : containsRun(run));
653  }
654 
655  bool
657  return findEventPosition(run, lumi, event).getEntryType() != kEnd;
658  }
659 
660  bool
662  return findLumiPosition(run, lumi).getEntryType() != kEnd;
663  }
664 
665  bool
667  return findRunPosition(run).getEntryType() != kEnd;
668  }
669 
671  return SortedRunOrLumiItr(this, 0);
672  }
673 
675  return SortedRunOrLumiItr(this, runOrLumiEntries().size());
676  }
677 
679  std::set<IndexRunLumiEventKey> & intersection) const {
680 
681  if (empty() || indexIntoFile.empty()) return;
683  indexIntoFile.fillRunOrLumiIndexes();
684  RunOrLumiIndexes const& back1 = runOrLumiIndexes().back();
685  RunOrLumiIndexes const& back2 = indexIntoFile.runOrLumiIndexes().back();
686 
687  // Very quick decision if the run ranges in the two files do not overlap
688  if (back2 < runOrLumiIndexes().front()) return;
689  if (back1 < indexIntoFile.runOrLumiIndexes().front()) return;
690 
693 
694  SortedRunOrLumiItr iter2 = indexIntoFile.beginRunOrLumi();
695  SortedRunOrLumiItr iEnd2 = indexIntoFile.endRunOrLumi();
696 
697  // Quick decision if the lumi ranges in the two files do not overlap
698  while (iter1 != iEnd1 && iter1.isRun()) ++iter1;
699  if (iter1 == iEnd1) return;
700  if (back2 < iter1.runOrLumiIndexes()) return;
701 
702  while (iter2 != iEnd2 && iter2.isRun()) ++iter2;
703  if (iter2 == iEnd2) return;
704  if (back1 < iter2.runOrLumiIndexes()) return;
705 
706  RunOrLumiIndexes const* previousIndexes = 0;
707 
708  // Loop through the both IndexIntoFile objects and look for matching lumis
709  while (iter1 != iEnd1 && iter2 != iEnd2) {
710 
711  RunOrLumiIndexes const& indexes1 = iter1.runOrLumiIndexes();
712  RunOrLumiIndexes const& indexes2 = iter2.runOrLumiIndexes();
713  if (indexes1 < indexes2) {
714  ++iter1;
715  }
716  else if (indexes2 < indexes1) {
717  ++iter2;
718  }
719  else { // they are equal
720 
721  // Skip them if it is a run or the same lumi
722  if (indexes1.isRun() ||
723  (previousIndexes && !(*previousIndexes < indexes1))) {
724  ++iter1;
725  ++iter2;
726  }
727  else {
728  previousIndexes = &indexes1;
729 
730  // Found a matching lumi, now look for matching events
731 
732  long long beginEventNumbers1 = indexes1.beginEventNumbers();
733  long long endEventNumbers1 = indexes1.endEventNumbers();
734 
735  long long beginEventNumbers2 = indexes2.beginEventNumbers();
736  long long endEventNumbers2 = indexes2.endEventNumbers();
737 
738  // there must be at least 1 event in each lumi for there to be any matches
739  if ((beginEventNumbers1 >= endEventNumbers1) ||
740  (beginEventNumbers2 >= endEventNumbers2)) {
741  ++iter1;
742  ++iter2;
743  continue;
744  }
745 
746  if (!eventEntries().empty() && !indexIntoFile.eventEntries().empty()) {
747  std::vector<EventEntry> matchingEvents;
748  std::insert_iterator<std::vector<EventEntry> > insertIter(matchingEvents, matchingEvents.begin());
749  std::set_intersection(eventEntries().begin() + beginEventNumbers1,
750  eventEntries().begin() + endEventNumbers1,
751  indexIntoFile.eventEntries().begin() + beginEventNumbers2,
752  indexIntoFile.eventEntries().begin() + endEventNumbers2,
753  insertIter);
754  for (std::vector<EventEntry>::const_iterator iEvent = matchingEvents.begin(),
755  iEnd = matchingEvents.end();
756  iEvent != iEnd; ++iEvent) {
757  intersection.insert(IndexRunLumiEventKey(indexes1.processHistoryIDIndex(),
758  indexes1.run(),
759  indexes1.lumi(),
760  iEvent->event()));
761  }
762  } else {
764  indexIntoFile.fillEventNumbers();
765  std::vector<EventNumber_t> matchingEvents;
766  std::insert_iterator<std::vector<EventNumber_t> > insertIter(matchingEvents, matchingEvents.begin());
767  std::set_intersection(eventNumbers().begin() + beginEventNumbers1,
768  eventNumbers().begin() + endEventNumbers1,
769  indexIntoFile.eventNumbers().begin() + beginEventNumbers2,
770  indexIntoFile.eventNumbers().begin() + endEventNumbers2,
771  insertIter);
772  for (std::vector<EventNumber_t>::const_iterator iEvent = matchingEvents.begin(),
773  iEnd = matchingEvents.end();
774  iEvent != iEnd; ++iEvent) {
775  intersection.insert(IndexRunLumiEventKey(indexes1.processHistoryIDIndex(),
776  indexes1.run(),
777  indexes1.lumi(),
778  *iEvent));
779  }
780  }
781  }
782  }
783  }
784  }
785 
787 
788  RunOrLumiIndexes const* previousIndexes = 0;
789 
790  for (SortedRunOrLumiItr iter = beginRunOrLumi(),
791  iEnd = endRunOrLumi();
792  iter != iEnd; ++iter) {
793 
794  RunOrLumiIndexes const& indexes = iter.runOrLumiIndexes();
795 
796  // Skip it if it is a run or the same lumi
797  if (indexes.isRun() ||
798  (previousIndexes && !(*previousIndexes < indexes))) {
799  continue;
800  }
801  previousIndexes = &indexes;
802 
803  long long beginEventNumbers = indexes.beginEventNumbers();
804  long long endEventNumbers = indexes.endEventNumbers();
805 
806  // there must be more than 1 event in the lumi for there to be any duplicates
807  if (beginEventNumbers + 1 >= endEventNumbers) continue;
808 
809  if (!eventEntries().empty()) {
810  std::vector<EventEntry>::iterator last = eventEntries().begin() + endEventNumbers;
811  if (std::adjacent_find(eventEntries().begin() + beginEventNumbers, last) != last) {
812  return true;
813  }
814  } else {
816  std::vector<EventNumber_t>::iterator last = eventNumbers().begin() + endEventNumbers;
817  if (std::adjacent_find(eventNumbers().begin() + beginEventNumbers, last) != last) {
818  return true;
819  }
820  }
821  }
822  return false;
823  }
824 
826  orderPHIDRun_(invalidEntry),
827  orderPHIDRunLumi_(invalidEntry),
828  entry_(invalidEntry),
829  processHistoryIDIndex_(invalidIndex),
830  run_(invalidRun),
831  lumi_(invalidLumi),
832  beginEvents_(invalidEntry),
833  endEvents_(invalidEntry) {
834  }
835 
837  EntryNumber_t orderPHIDRunLumi,
839  int processHistoryIDIndex,
844  orderPHIDRun_(orderPHIDRun),
845  orderPHIDRunLumi_(orderPHIDRunLumi),
846  entry_(entry),
847  processHistoryIDIndex_(processHistoryIDIndex),
848  run_(run),
849  lumi_(lumi),
850  beginEvents_(beginEvents),
851  endEvents_(endEvents) {
852  }
853 
857  int indexToGetEntry) :
858  processHistoryIDIndex_(processHistoryIDIndex),
859  run_(run),
860  lumi_(lumi),
861  indexToGetEntry_(indexToGetEntry),
862  beginEventNumbers_(-1),
863  endEventNumbers_(-1)
864  {
865  }
866 
867  IndexIntoFile::SortedRunOrLumiItr::SortedRunOrLumiItr(IndexIntoFile const* indexIntoFile, unsigned runOrLumi) :
868  indexIntoFile_(indexIntoFile), runOrLumi_(runOrLumi) {
869  assert(runOrLumi_ <= indexIntoFile_->runOrLumiEntries().size());
871  }
872 
874  return indexIntoFile_ == right.indexIntoFile() &&
875  runOrLumi_ == right.runOrLumi();
876  }
877 
879  return indexIntoFile_ != right.indexIntoFile() ||
880  runOrLumi_ != right.runOrLumi();
881  }
882 
884  if (runOrLumi_ != indexIntoFile_->runOrLumiEntries().size()) {
885  ++runOrLumi_;
886  }
887  return *this;
888  }
889 
891  return indexIntoFile_->runOrLumiIndexes().at(runOrLumi_).lumi() == invalidLumi;
892  }
893 
894  void IndexIntoFile::SortedRunOrLumiItr::getRange(long long & beginEventNumbers,
895  long long & endEventNumbers,
896  EntryNumber_t & beginEventEntry,
897  EntryNumber_t & endEventEntry) {
898  beginEventNumbers = indexIntoFile_->runOrLumiIndexes().at(runOrLumi_).beginEventNumbers();
899  endEventNumbers = indexIntoFile_->runOrLumiIndexes().at(runOrLumi_).endEventNumbers();
900 
901  int indexToGetEntry = indexIntoFile_->runOrLumiIndexes().at(runOrLumi_).indexToGetEntry();
902  beginEventEntry = indexIntoFile_->runOrLumiEntries_.at(indexToGetEntry).beginEvents();
903  endEventEntry = indexIntoFile_->runOrLumiEntries_.at(indexToGetEntry).endEvents();
904  }
905 
908  return indexIntoFile_->runOrLumiIndexes().at(runOrLumi_);
909  }
910 
912  EntryType entryType,
913  int indexToRun,
914  int indexToLumi,
915  int indexToEventRange,
916  long long indexToEvent,
917  long long nEvents) :
918  indexIntoFile_(indexIntoFile),
919  size_(static_cast<int>(indexIntoFile_->runOrLumiEntries_.size())),
920  type_(entryType),
921  indexToRun_(indexToRun),
922  indexToLumi_(indexToLumi),
923  indexToEventRange_(indexToEventRange),
924  indexToEvent_(indexToEvent),
925  nEvents_(nEvents) {
926  }
927 
929 
931 
932  if (type_ == kEvent) {
933  if ((indexToEvent_ + 1) < nEvents_) {
934  ++indexToEvent_;
935  }
936  else {
937  bool found = nextEventRange();
938 
939  if (!found) {
940  type_ = getRunOrLumiEntryType(indexToLumi_ + 1);
941 
942  if (type_ == kLumi) {
943  ++indexToLumi_;
944  initializeLumi();
945  }
946  else if (type_ == kRun) {
947  indexToRun_ = indexToLumi_ + 1;
948  initializeRun();
949  }
950  else {
951  setInvalid(); // type_ is kEnd
952  }
953  }
954  }
955  }
956  else if (type_ == kLumi) {
957 
958  if (indexToLumi_ + 1 == size_) {
959  if (indexToEvent_ < nEvents_) {
960  type_ = kEvent;
961  }
962  else {
963  setInvalid();
964  }
965  }
966  else {
967 
968  EntryType nextType = getRunOrLumiEntryType(indexToLumi_ + 1);
969 
970  if (nextType == kLumi && isSameLumi(indexToLumi_, indexToLumi_ + 1)) {
971  ++indexToLumi_;
972  }
973  else if (indexToEvent_ < nEvents_) {
974  type_ = kEvent;
975  }
976  else if (nextType == kRun) {
977  type_ = kRun;
978  indexToRun_ = indexToLumi_ + 1;
979  initializeRun();
980  }
981  else {
982  ++indexToLumi_;
983  initializeLumi();
984  }
985  }
986  }
987  else if (type_ == kRun) {
988  EntryType nextType = getRunOrLumiEntryType(indexToRun_ + 1);
989  bool sameRun = isSameRun(indexToRun_, indexToRun_ + 1);
990  if (nextType == kRun && sameRun) {
991  ++indexToRun_;
992  }
993  else if (nextType == kRun && !sameRun) {
994  ++indexToRun_;
995  initializeRun();
996  }
997  else if (nextType == kLumi) {
998  type_ = kLumi;
999  }
1000  else {
1001  setInvalid();
1002  }
1003  }
1004  }
1005 
1007  RunNumber_t & runOfSkippedEvent,
1008  LuminosityBlockNumber_t & lumiOfSkippedEvent,
1009  EntryNumber_t & skippedEventEntry) {
1010  if (indexToEvent_ < nEvents_) {
1011  phIndexOfSkippedEvent = processHistoryIDIndex();
1012  runOfSkippedEvent = run();
1013  lumiOfSkippedEvent = peekAheadAtLumi();
1014  skippedEventEntry = peekAheadAtEventEntry();
1015 
1016  if ((indexToEvent_ + 1) < nEvents_) {
1017  ++indexToEvent_;
1018  return;
1019  }
1020  else if (nextEventRange()) {
1021  return;
1022  }
1023  else if (type_ == kRun || type_ == kLumi) {
1024  if (skipLumiInRun()) {
1025  return;
1026  }
1027  }
1028  else if (type_ == kEvent) {
1029  next();
1030  return;
1031  }
1032  advanceToNextRun();
1033  return;
1034  }
1035 
1036  if (type_ == kRun) {
1037  while (skipLumiInRun()) {
1038  if (indexToEvent_ < nEvents_) {
1039  skipEventForward(phIndexOfSkippedEvent, runOfSkippedEvent, lumiOfSkippedEvent, skippedEventEntry);
1040  return;
1041  }
1042  }
1043  }
1044 
1045  while (indexToEvent_ >= nEvents_ && type_ != kEnd) {
1046  while (skipLumiInRun()) {
1047  if (indexToEvent_ < nEvents_) {
1048  skipEventForward(phIndexOfSkippedEvent, runOfSkippedEvent, lumiOfSkippedEvent, skippedEventEntry);
1049  return;
1050  }
1051  }
1052  advanceToNextRun();
1053  }
1054  if (type_ == kEnd) {
1055  phIndexOfSkippedEvent = invalidIndex;
1056  runOfSkippedEvent = invalidRun;
1057  lumiOfSkippedEvent = invalidLumi;
1058  skippedEventEntry = invalidEntry;
1059  return;
1060  }
1061  skipEventForward(phIndexOfSkippedEvent, runOfSkippedEvent, lumiOfSkippedEvent, skippedEventEntry);
1062  return;
1063  }
1064 
1066  RunNumber_t& runOfEvent,
1067  LuminosityBlockNumber_t& lumiOfEvent,
1068  EntryNumber_t& eventEntry) {
1069  // Look for previous events in the current lumi
1070  if (indexToEvent_ > 0) {
1071  --indexToEvent_;
1072  }
1073  else if (!previousEventRange()) {
1074 
1075  // Look for previous events in previous lumis
1076  if (!previousLumiWithEvents()) {
1077 
1078  // If we get here there are no previous events in the file
1079 
1080  if (!indexIntoFile_->empty()) {
1081  // Set the iterator to the beginning of the file
1082  type_ = kRun;
1083  indexToRun_ = 0;
1084  initializeRun();
1085  }
1086  phIndexOfEvent = invalidIndex;
1087  runOfEvent = invalidRun;
1088  lumiOfEvent = invalidLumi;
1089  eventEntry = invalidEntry;
1090  return;
1091  }
1092  }
1093  // Found a previous event and we have set the iterator so that this event
1094  // will be the next event process. (There may or may not be a run and/or
1095  // a lumi processed first).
1096  // Return information about this event
1097  phIndexOfEvent = processHistoryIDIndex();
1098  runOfEvent = run();
1099  lumiOfEvent = peekAheadAtLumi();
1100  eventEntry = peekAheadAtEventEntry();
1101  }
1102 
1104  // Find the correct place to start the search
1105  int newLumi = indexToLumi();
1106  if (newLumi == invalidIndex) {
1107  newLumi = indexToRun() == invalidIndex ? size() - 1 : indexToRun();
1108  }
1109  else {
1110  while (getRunOrLumiEntryType(newLumi - 1) == kLumi &&
1111  isSameLumi(newLumi, newLumi - 1)) {
1112  --newLumi;
1113  }
1114  --newLumi;
1115  }
1116  if (newLumi <= 0) return false;
1117 
1118  // Look backwards for a lumi with events
1119  for ( ; newLumi > 0; --newLumi) {
1120  if (getRunOrLumiEntryType(newLumi) == kRun) {
1121  continue;
1122  }
1123  if (setToLastEventInRange(newLumi)) {
1124  break; // found it
1125  }
1126  }
1127  if (newLumi == 0) return false;
1128 
1129  // Finish initializing the iterator
1130  while (getRunOrLumiEntryType(newLumi - 1) == kLumi &&
1131  isSameLumi(newLumi, newLumi - 1)) {
1132  --newLumi;
1133  }
1134  setIndexToLumi(newLumi);
1135 
1136  if (type() != kEnd &&
1137  isSameRun(newLumi, indexToRun())) {
1138  if (type() == kEvent) type_ = kLumi;
1139  return true;
1140  }
1141  int newRun = newLumi;
1142  while (newRun > 0 && getRunOrLumiEntryType(newRun - 1) == kLumi) {
1143  --newRun;
1144  }
1145  --newRun;
1146  assert(getRunOrLumiEntryType(newRun) == kRun);
1147  while (getRunOrLumiEntryType(newRun - 1) == kRun &&
1148  isSameRun(newRun - 1, newLumi)) {
1149  --newRun;
1150  }
1151  indexToRun_ = newRun;
1152  type_ = kRun;
1153  return true;
1154  }
1155 
1157  if (type_ == kEnd) return;
1158  for (int i = 1; indexToRun_ + i < size_; ++i) {
1159  if (getRunOrLumiEntryType(indexToRun_ + i) == kRun) {
1160  if (!isSameRun(indexToRun_, indexToRun_ + i)) {
1161  type_ = kRun;
1162  indexToRun_ += i;
1163  initializeRun();
1164  return;
1165  }
1166  }
1167  }
1168  setInvalid();
1169  }
1170 
1172  if (type_ == kEnd) return;
1173  assert(indexToRun_ != invalidIndex);
1174 
1175  // A preliminary step is to advance to the last run entry for
1176  // this run (actually this step is not needed in the
1177  // context I expect this to be called in, just being careful)
1178  int startSearch = indexToRun_;
1179  for (int i = 1; startSearch + i < size_; ++i) {
1180  if (getRunOrLumiEntryType(startSearch + i) == kRun &&
1181  isSameRun(indexToRun_, startSearch + i)) {
1182  indexToRun_ = startSearch + i;
1183  }
1184  else {
1185  break;
1186  }
1187  }
1188 
1189  if (type_ == kRun && indexToLumi_ != invalidIndex) {
1190  type_ = kLumi;
1191  return;
1192  }
1193 
1194  startSearch = indexToLumi_;
1195  if (startSearch == invalidIndex) startSearch = indexToRun_;
1196  for (int i = 1; startSearch + i < size_; ++i) {
1197  if (getRunOrLumiEntryType(startSearch + i) == kRun) {
1198  if (!isSameRun(indexToRun_, startSearch + i)) {
1199  type_ = kRun;
1200  indexToRun_ = startSearch + i;
1201  initializeRun();
1202  return;
1203  }
1204  }
1205  else if (indexToLumi_ != invalidIndex) {
1206  if (!isSameLumi(indexToLumi_, startSearch + i)) {
1207  type_ = kLumi;
1208  indexToLumi_ = startSearch + i;
1209  initializeLumi();
1210  return;
1211  }
1212  }
1213  }
1214  setInvalid();
1215  }
1216 
1218  if (indexToEvent_ >= nEvents_) return false;
1219  if ((indexToEvent_ + 1) < nEvents_) {
1220  ++indexToEvent_;
1221  return true;
1222  }
1223  return nextEventRange();
1224  }
1225 
1227 
1228  indexToLumi_ = invalidIndex;
1229  indexToEventRange_ = invalidIndex;
1230  indexToEvent_ = 0;
1231  nEvents_ = 0;
1232 
1233  for (int i = 1; (i + indexToRun_) < size_; ++i) {
1234  EntryType entryType = getRunOrLumiEntryType(indexToRun_ + i);
1235  bool sameRun = isSameRun(indexToRun_, indexToRun_ + i);
1236 
1237  if (entryType == kRun) {
1238  if (sameRun) {
1239  continue;
1240  }
1241  else {
1242  break;
1243  }
1244  }
1245  else {
1246  indexToLumi_ = indexToRun_ + i;
1247  initializeLumi();
1248  return;
1249  }
1250  }
1251  }
1252 
1254  return (indexIntoFile_ == right.indexIntoFile_ &&
1255  size_ == right.size_ &&
1256  type_ == right.type_ &&
1257  indexToRun_ == right.indexToRun_ &&
1258  indexToLumi_ == right.indexToLumi_ &&
1259  indexToEventRange_ == right.indexToEventRange_ &&
1260  indexToEvent_ == right.indexToEvent_ &&
1261  nEvents_ == right.nEvents_);
1262  }
1263 
1264  void
1266  type_ = position.type_;
1267  indexToRun_ = position.indexToRun_;
1268  indexToLumi_ = position.indexToLumi_;
1269  indexToEventRange_ = position.indexToEventRange_;
1270  indexToEvent_ = position.indexToEvent_;
1271  nEvents_ = position.nEvents_;
1272  }
1273 
1275  type_ = kEnd;
1276  indexToRun_ = invalidIndex;
1277  indexToLumi_ = invalidIndex;
1278  indexToEventRange_ = invalidIndex;
1279  indexToEvent_ = 0;
1280  nEvents_ = 0;
1281  }
1282 
1284  EntryType entryType,
1285  int indexToRun,
1286  int indexToLumi,
1287  int indexToEventRange,
1288  long long indexToEvent,
1289  long long nEvents) :
1290  IndexIntoFileItrImpl(indexIntoFile,
1291  entryType,
1292  indexToRun,
1293  indexToLumi,
1294  indexToEventRange,
1295  indexToEvent,
1296  nEvents)
1297  {
1298  }
1299 
1302  return new IndexIntoFileItrNoSort(*this);
1303  }
1304 
1305  int
1307  if (type() == kEnd) return invalidIndex;
1308  return indexIntoFile()->runOrLumiEntries()[indexToRun()].processHistoryIDIndex();
1309  }
1310 
1312  if (type() == kEnd) return invalidRun;
1313  return indexIntoFile()->runOrLumiEntries()[indexToRun()].run();
1314  }
1315 
1317  if (type() == kEnd || type() == kRun) return invalidLumi;
1318  return indexIntoFile()->runOrLumiEntries()[indexToLumi()].lumi();
1319  }
1320 
1322  if (type() == kEnd) return invalidEntry;
1323  if (type() == kRun) return indexIntoFile()->runOrLumiEntries()[indexToRun()].entry();
1324  if (type() == kLumi) return indexIntoFile()->runOrLumiEntries()[indexToLumi()].entry();
1325  return
1326  indexIntoFile()->runOrLumiEntries()[indexToEventRange()].beginEvents() +
1327  indexToEvent();
1328  }
1329 
1331  if (indexToLumi() == invalidIndex) return invalidLumi;
1332  return indexIntoFile()->runOrLumiEntries()[indexToLumi()].lumi();
1333  }
1334 
1336  if (indexToLumi() == invalidIndex) return invalidEntry;
1337  if (indexToEvent() >= nEvents()) return invalidEntry;
1338  return
1339  indexIntoFile()->runOrLumiEntries()[indexToEventRange()].beginEvents() +
1340  indexToEvent();
1341  }
1342 
1344  assert(indexToLumi() != invalidIndex);
1345 
1346  setIndexToEventRange(invalidIndex);
1347  setIndexToEvent(0);
1348  setNEvents(0);
1349 
1350  for (int i = 0; indexToLumi() + i < size(); ++i) {
1351  if (indexIntoFile()->runOrLumiEntries()[indexToLumi() + i].isRun()) {
1352  break;
1353  }
1354  else if (indexIntoFile()->runOrLumiEntries()[indexToLumi() + i].lumi() ==
1355  indexIntoFile()->runOrLumiEntries()[indexToLumi()].lumi()) {
1356  if (indexIntoFile()->runOrLumiEntries()[indexToLumi() + i].beginEvents() == invalidEntry) {
1357  continue;
1358  }
1359  setIndexToEventRange(indexToLumi() + i);
1360  setIndexToEvent(0);
1361  setNEvents(indexIntoFile()->runOrLumiEntries()[indexToEventRange()].endEvents() -
1362  indexIntoFile()->runOrLumiEntries()[indexToEventRange()].beginEvents());
1363  break;
1364  }
1365  else {
1366  break;
1367  }
1368  }
1369  }
1370 
1372  if (indexToEventRange() == invalidIndex) return false;
1373 
1374  // Look for the next event range, same lumi but different entry
1375  for(int i = 1; indexToEventRange() + i < size(); ++i) {
1376  if (indexIntoFile()->runOrLumiEntries()[indexToEventRange() + i ].isRun()) {
1377  return false; // hit next run
1378  }
1379  else if (indexIntoFile()->runOrLumiEntries()[indexToEventRange() + i].lumi() ==
1380  indexIntoFile()->runOrLumiEntries()[indexToEventRange()].lumi()) {
1381  if (indexIntoFile()->runOrLumiEntries()[indexToEventRange() + i].beginEvents() == invalidEntry) {
1382  continue; // same lumi but has no events, keep looking
1383  }
1384  setIndexToEventRange(indexToEventRange() + i);
1385  setIndexToEvent(0);
1386  setNEvents(indexIntoFile()->runOrLumiEntries()[indexToEventRange()].endEvents() -
1387  indexIntoFile()->runOrLumiEntries()[indexToEventRange()].beginEvents());
1388  return true; // found more events in this lumi
1389  }
1390  return false; // hit next lumi
1391  }
1392  return false; // hit the end of the IndexIntoFile
1393  }
1394 
1396  if (indexToEventRange() == invalidIndex) return false;
1397  assert(indexToEventRange() < size());
1398 
1399  // Look backward for a previous event range with events, same lumi but different entry
1400  for(int i = 1; indexToEventRange() - i > 0; ++i) {
1401  int newRange = indexToEventRange() - i;
1402  if (indexIntoFile()->runOrLumiEntries()[newRange].isRun()) {
1403  return false; // hit run
1404  }
1405  else if (isSameLumi(newRange, indexToEventRange())) {
1406  if (indexIntoFile()->runOrLumiEntries()[newRange].beginEvents() == invalidEntry) {
1407  continue; // same lumi but has no events, keep looking
1408  }
1409  setIndexToEventRange(newRange);
1410  setNEvents(indexIntoFile()->runOrLumiEntries()[indexToEventRange()].endEvents() -
1411  indexIntoFile()->runOrLumiEntries()[indexToEventRange()].beginEvents());
1412  setIndexToEvent(nEvents() - 1);
1413  return true; // found previous event in this lumi
1414  }
1415  return false; // hit previous lumi
1416  }
1417  return false; // hit the beginning of the IndexIntoFile, 0th entry has to be a run
1418  }
1419 
1421  if (indexIntoFile()->runOrLumiEntries()[index].beginEvents() == invalidEntry) {
1422  return false;
1423  }
1424  setIndexToEventRange(index);
1425  setNEvents(indexIntoFile()->runOrLumiEntries()[indexToEventRange()].endEvents() -
1426  indexIntoFile()->runOrLumiEntries()[indexToEventRange()].beginEvents());
1427  assert(nEvents() > 0);
1428  setIndexToEvent(nEvents() - 1);
1429  return true;
1430  }
1431 
1433  if (indexToLumi() == invalidIndex) return false;
1434  for(int i = 1; indexToLumi() + i < size(); ++i) {
1435  int newLumi = indexToLumi() + i;
1436  if (indexIntoFile()->runOrLumiEntries()[newLumi].isRun()) {
1437  return false; // hit next run
1438  }
1439  else if (indexIntoFile()->runOrLumiEntries()[newLumi].lumi() ==
1440  indexIntoFile()->runOrLumiEntries()[indexToLumi()].lumi()) {
1441  continue;
1442  }
1443  setIndexToLumi(newLumi);
1444  initializeLumi();
1445  return true; // hit next lumi
1446  }
1447  return false; // hit the end of the IndexIntoFile
1448  }
1449 
1451  if (index < 0 || index >= size()) {
1452  return kEnd;
1453  }
1454  else if (indexIntoFile()->runOrLumiEntries()[index].isRun()) {
1455  return kRun;
1456  }
1457  return kLumi;
1458  }
1459 
1460  bool IndexIntoFile::IndexIntoFileItrNoSort::isSameLumi(int index1, int index2) const {
1461  if (index1 < 0 || index1 >= size() || index2 < 0 || index2 >= size()) {
1462  return false;
1463  }
1464  return indexIntoFile()->runOrLumiEntries()[index1].lumi() ==
1465  indexIntoFile()->runOrLumiEntries()[index2].lumi();
1466  }
1467 
1468  bool IndexIntoFile::IndexIntoFileItrNoSort::isSameRun(int index1, int index2) const {
1469  if (index1 < 0 || index1 >= size() || index2 < 0 || index2 >= size()) {
1470  return false;
1471  }
1472  return indexIntoFile()->runOrLumiEntries()[index1].run() ==
1473  indexIntoFile()->runOrLumiEntries()[index2].run() &&
1474  indexIntoFile()->runOrLumiEntries()[index1].processHistoryIDIndex() ==
1475  indexIntoFile()->runOrLumiEntries()[index2].processHistoryIDIndex();
1476  }
1477 
1479  EntryType entryType,
1480  int indexToRun,
1481  int indexToLumi,
1482  int indexToEventRange,
1483  long long indexToEvent,
1484  long long nEvents) :
1485  IndexIntoFileItrImpl(indexIntoFile,
1486  entryType,
1487  indexToRun,
1488  indexToLumi,
1489  indexToEventRange,
1490  indexToEvent,
1491  nEvents) {
1492  indexIntoFile->fillRunOrLumiIndexes();
1493  }
1494 
1496  return new IndexIntoFileItrSorted(*this);
1497  }
1498 
1500  if (type() == kEnd) return invalidIndex;
1501  return indexIntoFile()->runOrLumiIndexes()[indexToRun()].processHistoryIDIndex();
1502  }
1503 
1505  if (type() == kEnd) return invalidRun;
1506  return indexIntoFile()->runOrLumiIndexes()[indexToRun()].run();
1507  }
1508 
1510  if (type() == kEnd || type() == kRun) return invalidLumi;
1511  return indexIntoFile()->runOrLumiIndexes()[indexToLumi()].lumi();
1512  }
1513 
1515  if (type() == kEnd) return invalidEntry;
1516  if (type() == kRun) {
1517  int i = indexIntoFile()->runOrLumiIndexes()[indexToRun()].indexToGetEntry();
1518  return indexIntoFile()->runOrLumiEntries()[i].entry();
1519  }
1520  if (type() == kLumi) {
1521  int i = indexIntoFile()->runOrLumiIndexes()[indexToLumi()].indexToGetEntry();
1522  return indexIntoFile()->runOrLumiEntries()[i].entry();
1523  }
1524  long long eventNumberIndex =
1525  indexIntoFile()->runOrLumiIndexes()[indexToEventRange()].beginEventNumbers() +
1526  indexToEvent();
1527  indexIntoFile()->fillEventEntries();
1528  return indexIntoFile()->eventEntries().at(eventNumberIndex).entry();
1529  }
1530 
1532  if (indexToLumi() == invalidIndex) return invalidLumi;
1533  return indexIntoFile()->runOrLumiIndexes()[indexToLumi()].lumi();
1534  }
1535 
1537  if (indexToLumi() == invalidIndex) return invalidEntry;
1538  if (indexToEvent() >= nEvents()) return invalidEntry;
1539  long long eventNumberIndex =
1540  indexIntoFile()->runOrLumiIndexes()[indexToEventRange()].beginEventNumbers() +
1541  indexToEvent();
1542  indexIntoFile()->fillEventEntries();
1543  return indexIntoFile()->eventEntries().at(eventNumberIndex).entry();
1544  }
1545 
1547  assert(indexToLumi() != invalidIndex);
1548  setIndexToEventRange(indexToLumi());
1549  setIndexToEvent(0);
1550  setNEvents(
1551  indexIntoFile()->runOrLumiIndexes()[indexToLumi()].endEventNumbers() -
1552  indexIntoFile()->runOrLumiIndexes()[indexToLumi()].beginEventNumbers());
1553  if (nEvents() == 0){
1554  setIndexToEventRange(invalidIndex);
1555  }
1556  }
1557 
1559  return false;
1560  }
1561 
1563  return false;
1564  }
1565 
1567  long long nEventsInRange =
1568  indexIntoFile()->runOrLumiIndexes()[index].endEventNumbers() -
1569  indexIntoFile()->runOrLumiIndexes()[index].beginEventNumbers();
1570  if (nEventsInRange == 0) {
1571  return false;
1572  }
1573  while (index > 0 &&
1574  !indexIntoFile()->runOrLumiIndexes()[index - 1].isRun() &&
1575  isSameLumi(index, index - 1)) {
1576  --index;
1577  }
1578  assert(nEventsInRange ==
1579  indexIntoFile()->runOrLumiIndexes()[index].endEventNumbers() -
1580  indexIntoFile()->runOrLumiIndexes()[index].beginEventNumbers());
1581 
1582  setIndexToEventRange(index);
1583  setNEvents(nEventsInRange);
1584  assert(nEvents() > 0);
1585  setIndexToEvent(nEventsInRange - 1);
1586  return true;
1587  }
1588 
1590  if (indexToLumi() == invalidIndex) return false;
1591  for(int i = 1; indexToLumi() + i < size(); ++i) {
1592  int newLumi = indexToLumi() + i;
1593  if (indexIntoFile()->runOrLumiIndexes()[newLumi].isRun()) {
1594  return false; // hit next run
1595  }
1596  else if (indexIntoFile()->runOrLumiIndexes()[newLumi].lumi() ==
1597  indexIntoFile()->runOrLumiIndexes()[indexToLumi()].lumi()) {
1598  continue;
1599  }
1600  setIndexToLumi(newLumi);
1601  initializeLumi();
1602  return true; // hit next lumi
1603  }
1604  return false; // hit the end of the IndexIntoFile
1605  }
1606 
1608  if (index < 0 || index >= size()) {
1609  return kEnd;
1610  }
1611  else if (indexIntoFile()->runOrLumiIndexes()[index].isRun()) {
1612  return kRun;
1613  }
1614  return kLumi;
1615  }
1616 
1617  bool IndexIntoFile::IndexIntoFileItrSorted::isSameLumi(int index1, int index2) const {
1618  if (index1 < 0 || index1 >= size() || index2 < 0 || index2 >= size()) {
1619  return false;
1620  }
1621  return indexIntoFile()->runOrLumiIndexes()[index1].lumi() ==
1622  indexIntoFile()->runOrLumiIndexes()[index2].lumi();
1623  }
1624 
1625  bool IndexIntoFile::IndexIntoFileItrSorted::isSameRun(int index1, int index2) const {
1626  if (index1 < 0 || index1 >= size() || index2 < 0 || index2 >= size()) {
1627  return false;
1628  }
1629  return indexIntoFile()->runOrLumiIndexes()[index1].run() ==
1630  indexIntoFile()->runOrLumiIndexes()[index2].run() &&
1631  indexIntoFile()->runOrLumiIndexes()[index1].processHistoryIDIndex() ==
1632  indexIntoFile()->runOrLumiIndexes()[index2].processHistoryIDIndex();
1633  }
1634 
1636  SortOrder sortOrder,
1637  EntryType entryType,
1638  int indexToRun,
1639  int indexToLumi,
1640  int indexToEventRange,
1641  long long indexToEvent,
1642  long long nEvents) :
1643  impl_() {
1644  if (sortOrder == numericalOrder) {
1646  entryType,
1647  indexToRun,
1648  indexToLumi,
1649  indexToEventRange,
1650  indexToEvent,
1651  nEvents
1652  ));
1653  swap(temp, impl_);
1654  }
1655  else {
1657  entryType,
1658  indexToRun,
1659  indexToLumi,
1660  indexToEventRange,
1661  indexToEvent,
1662  nEvents));
1663  swap(temp, impl_);
1664  }
1665  }
1666 
1668  for (EntryType entryType = getEntryType();
1669  entryType != kEnd && entryType != kEvent;
1670  entryType = getEntryType()) {
1671  impl_->next();
1672  }
1673  }
1674 
1676  for (EntryType entryType = getEntryType();
1677  entryType != kEnd && entryType != kLumi;
1678  entryType = getEntryType()) {
1679  impl_->next();
1680  }
1681  }
1682 
1683  void
1685  impl_->copyPosition(*position.impl_);
1686  }
1687 
1689  runToFirstEntry_(),
1690  lumiToFirstEntry_(),
1691  beginEvents_(invalidEntry),
1692  endEvents_(invalidEntry),
1693  currentIndex_(invalidIndex),
1694  currentRun_(invalidRun),
1695  currentLumi_(invalidLumi),
1696  numberOfEvents_(0),
1697  eventFinder_(),
1698  runOrLumiIndexes_(),
1699  eventNumbers_(),
1700  eventEntries_(),
1701  unsortedEventNumbers_() {
1702  }
1703 
1705  if (lh.processHistoryIDIndex() == rh.processHistoryIDIndex()) {
1706  return lh.run() < rh.run();
1707  }
1708  return lh.processHistoryIDIndex() < rh.processHistoryIDIndex();
1709  }
1710 
1712  return lh.processHistoryIDIndex() < rh.processHistoryIDIndex();
1713  }
1714 }
void initializeRun()
Should only be used internally and for tests.
void fillEventNumbersOrEntries(bool needEventNumbers, bool needEventEntries) const
RunNumber_t & currentRun() const
type
Definition: HCALResponse.h:22
virtual bool isSameLumi(int index1, int index2) const
virtual EntryNumber_t entry() const
int i
Definition: DBlmapReader.cc:9
EntryNumber_t peekAheadAtEventEntry() const
void doneFileInitialization() const
Clears the temporary vector of event numbers to reduce memory usage.
static int const invalidIndex
virtual LuminosityBlockNumber_t lumi() const
virtual EntryNumber_t peekAheadAtEventEntry() const
virtual EntryNumber_t entry() const
virtual bool isSameRun(int index1, int index2) const
unsigned int EventNumber_t
Definition: EventID.h:30
std::vector< EventEntry > & eventEntries() const
Definition: Hash.h:36
tuple lumi
Definition: fjr2json.py:41
virtual EntryType getRunOrLumiEntryType(int index) const
SortedRunOrLumiItr beginRunOrLumi() const
bool empty() const
True if no runs, lumis, or events are in the file.
LuminosityBlockNumber_t & currentLumi() const
virtual LuminosityBlockNumber_t peekAheadAtLumi() const
bool operator==(SortedRunOrLumiItr const &right) const
std::vector< RunOrLumiIndexes > & runOrLumiIndexes() const
void sortEvents() const
void fillUnsortedEventNumbers() const
IndexIntoFileItr begin(SortOrder sortOrder) const
LuminosityBlockNumber_t lumi() const
bool int lh
Definition: SSEVec.h:37
std::vector< RunOrLumiEntry > const & runOrLumiEntries() const
Used internally and for test purposes.
void stable_sort_all(RandomAccessSequence &s)
wrappers for std::stable_sort
Definition: Algorithms.h:135
void find(edm::Handle< EcalRecHitCollection > &hits, DetId thisDet, std::vector< EcalRecHitCollection::const_iterator > &hit, bool debug=false)
Definition: FindCaloHit.cc:7
virtual IndexIntoFileItrImpl * clone() const
uint16_t size_type
unsigned int LuminosityBlockNumber_t
Definition: EventID.h:31
IndexIntoFileItr findRunPosition(RunNumber_t run) const
Same as findPosition.
std::vector< ProcessHistoryID > const & processHistoryIDs() const
long long EntryNumber_t
static int position[TOTALCHAMBERS][3]
Definition: ReadPGInfo.cc:509
static EventNumber_t const invalidEvent
void swap(Association< C > &lhs, Association< C > &rhs)
Definition: Association.h:117
IndexIntoFileItr findPosition(RunNumber_t run, LuminosityBlockNumber_t lumi=0U, EventNumber_t event=0U) const
int & previousAddedIndex() const
void sortVector_Run_Or_Lumi_Entries()
size_t numberOfEvents() const
IndexIntoFile const * indexIntoFile() const
int & currentIndex() const
int iEvent
Definition: GenABIO.cc:243
RunOrLumiIndexes(int processHistoryIDIndex, RunNumber_t run, LuminosityBlockNumber_t lumi, int indexToGetEntry)
static RunNumber_t const invalidRun
void skipEventBackward(int &phIndexOfEvent, RunNumber_t &runOfEvent, LuminosityBlockNumber_t &lumiOfEvent, EntryNumber_t &eventEntry)
std::vector< RunOrLumiEntry > runOrLumiEntries_
void copyPosition(IndexIntoFileItr const &position)
Copy the position without modifying the pointer to the IndexIntoFile or size.
IndexIntoFileItr end(SortOrder sortOrder) const
Used to end an iteration over the Runs, Lumis, and Events in a file.
void skipEventForward(int &phIndexOfSkippedEvent, RunNumber_t &runOfSkippedEvent, LuminosityBlockNumber_t &lumiOfSkippedEvent, EntryNumber_t &skippedEventEntry)
std::vector< ProcessHistoryID > processHistoryIDs_
std::pair< std::string, MonitorElement * > entry
Definition: ME_MAP.h:8
void fillEventEntries() const
IndexIntoFileItrImpl(IndexIntoFile const *indexIntoFile, EntryType entryType, int indexToRun, int indexToLumi, int indexToEventRange, long long indexToEvent, long long nEvents)
virtual EntryNumber_t peekAheadAtEventEntry() const
void fillRunOrLumiIndexes() const
virtual bool isSameRun(int index1, int index2) const
bool operator==(IndexIntoFileItrImpl const &right) const
void set_intersection(IndexIntoFile const &indexIntoFile, std::set< IndexRunLumiEventKey > &intersection) const
bool iterationWillBeInEntryOrder(SortOrder sortOrder) const
Used to determine whether or not to disable fast cloning.
virtual IndexIntoFileItrImpl * clone() const
unsigned int offset(bool)
bool operator()(IndexIntoFile::RunOrLumiIndexes const &lh, IndexIntoFile::RunOrLumiIndexes const &rh)
How EventSelector::AcceptEvent() decides whether to accept an event for output otherwise it is excluding the probing of A single or multiple positive and the trigger will pass if any such matching triggers are PASS or EXCEPTION[A criterion thatmatches no triggers at all is detected and causes a throw.] A single negative with an expectation of appropriate bit checking in the decision and the trigger will pass if any such matching triggers are FAIL or EXCEPTION A wildcarded negative criterion that matches more than one trigger in the trigger but the state exists so we define the behavior If all triggers are the negative crieriion will lead to accepting the event(this again matches the behavior of"!*"before the partial wildcard feature was incorporated).The per-event"cost"of each negative criterion with multiple relevant triggers is about the same as!*was in the past
bool operator!=(SortedRunOrLumiItr const &right) const
void addEntry(ProcessHistoryID const &processHistoryID, RunNumber_t run, LuminosityBlockNumber_t lumi, EventNumber_t event, EntryNumber_t entry)
SortedRunOrLumiItr(IndexIntoFile const *indexIntoFile, unsigned runOrLumi)
void sortEventEntries() const
bool containsLumi(RunNumber_t run, LuminosityBlockNumber_t lumi) const
bool containsDuplicateEvents() const
Returns true if the IndexIntoFile contains 2 events with the same ProcessHistoryID index...
bool containsItem(RunNumber_t run, LuminosityBlockNumber_t lumi, EventNumber_t event) const
void inputFileClosed() const
void fixIndexes(std::vector< ProcessHistoryID > &processHistoryIDs)
void resetEventFinder() const
std::map< IndexRunKey, EntryNumber_t > & runToFirstEntry() const
std::vector< EventNumber_t > & unsortedEventNumbers() const
static EntryNumber_t const invalidEntry
virtual bool isSameLumi(int index1, int index2) const
virtual EntryType getRunOrLumiEntryType(int index) const
IndexIntoFileItrSorted(IndexIntoFile const *indexIntoFile, EntryType entryType, int indexToRun, int indexToLumi, int indexToEventRange, long long indexToEvent, long long nEvents)
virtual LuminosityBlockNumber_t peekAheadAtLumi() const
static LuminosityBlockNumber_t const invalidLumi
IndexIntoFileItr findLumiPosition(RunNumber_t run, LuminosityBlockNumber_t lumi) const
void initializeLumi()
Should only be used internally and for tests.
ProcessHistoryID const & processHistoryID(int i) const
void copyPosition(IndexIntoFileItrImpl const &position)
EventNumber_t getEventNumberOfEntry(EntryNumber_t entry) const
virtual LuminosityBlockNumber_t lumi() const
void fillEventNumbers() const
void setNumberOfEvents(EntryNumber_t nevents) const
bool containsEvent(RunNumber_t run, LuminosityBlockNumber_t lumi, EventNumber_t event) const
std::vector< EventNumber_t > & eventNumbers() const
IndexIntoFileItr(IndexIntoFile const *indexIntoFile, SortOrder sortOrder, EntryType entryType, int indexToRun, int indexToLumi, int indexToEventRange, long long indexToEvent, long long nEvents)
unsigned int RunNumber_t
Definition: EventRange.h:32
SortedRunOrLumiItr endRunOrLumi() const
bool operator()(IndexIntoFile::RunOrLumiIndexes const &lh, IndexIntoFile::RunOrLumiIndexes const &rh)
UInt_t nEvents
Definition: hcalCalib.cc:43
std::map< IndexRunLumiKey, EntryNumber_t > & lumiToFirstEntry() const
bool containsRun(RunNumber_t run) const
IndexIntoFileItr findEventPosition(RunNumber_t run, LuminosityBlockNumber_t lumi, EventNumber_t event) const
void getRange(long long &beginEventNumbers, long long &endEventNumbers, EntryNumber_t &beginEventEntry, EntryNumber_t &endEventEntry)
EntryNumber_t & endEvents() const
LuminosityBlockNumber_t peekAheadAtLumi() const
EntryNumber_t & beginEvents() const
value_ptr< IndexIntoFileItrImpl > impl_
tuple size
Write out results.
IndexIntoFileItrNoSort(IndexIntoFile const *indexIntoFile, EntryType entryType, int indexToRun, int indexToLumi, int indexToEventRange, long long indexToEvent, long long nEvents)
list at
Definition: asciidump.py:428
RunOrLumiIndexes const & runOrLumiIndexes() const