public void Add(PrecursorSchedule schedule) { TransitionCount += schedule.TransitionCount; _precursorSchedules.Add(schedule); }
private void ExportScheduledBuckets(FileIterator fileIterator) { if (!MaxTransitions.HasValue) { throw new InvalidOperationException(Resources.AbstractMassListExporter_ExportScheduledBuckets_Maximum_transitions_per_file_required); } bool singleWindow = ExportInstrumentType.IsSingleWindowInstrumentType(InstrumentType); var predict = Document.Settings.PeptideSettings.Prediction; int?maxInstrumentTrans = null; if (!IsPrecursorLimited) { maxInstrumentTrans = Document.Settings.TransitionSettings.Instrument.MaxTransitions; } var listSchedules = new List <PeptideSchedule>(); var listRequired = new List <PeptideSchedule>(); var listUnscheduled = new List <PeptideSchedule>(); foreach (PeptideGroupDocNode nodePepGroup in Document.MoleculeGroups) { foreach (PeptideDocNode nodePep in nodePepGroup.Children) { var peptideSchedule = new PeptideSchedule(nodePep, maxInstrumentTrans); foreach (TransitionGroupDocNode nodeTranGroup in nodePep.Children) { double timeWindow; double retentionTime = predict.PredictRetentionTime(Document, nodePep, nodeTranGroup, SchedulingReplicateIndex, SchedulingAlgorithm, singleWindow, out timeWindow) ?? 0; var nodeTranGroupPrimary = PrimaryTransitionCount > 0 ? nodePep.GetPrimaryResultsGroup(nodeTranGroup) : null; var ps = new PrecursorSchedule(nodePepGroup, nodePep, nodeTranGroup, nodeTranGroupPrimary, retentionTime, timeWindow, IsPrecursorLimited, SchedulingReplicateIndex, PrimaryTransitionCount, OptimizeStepCount); peptideSchedule.Add(ps); } if (RequiredPeptides.IsRequired(nodePep)) { if (!peptideSchedule.CanSchedule) { throw new IOException(string.Format(Resources.AbstractMassListExporter_ExportScheduledBuckets_The_required_peptide__0__cannot_be_scheduled, Document.Settings.GetDisplayName(nodePep))); } listRequired.Add(peptideSchedule); } else if (peptideSchedule.CanSchedule) { listSchedules.Add(peptideSchedule); } else { listUnscheduled.Add(peptideSchedule); } } } int totalScheduled = 0; var listScheduleBuckets = new List <PeptideScheduleBucket>(); while (!PeptideSchedule.IsListScheduled(listSchedules)) { var listScheduleNext = new PeptideScheduleBucket(); // First add all required transitions foreach (var schedule in listRequired) { schedule.Schedule(listScheduleNext, MaxTransitions.Value); } // Then try to add from the scheduling list foreach (var schedule in listSchedules) { schedule.Schedule(listScheduleNext, MaxTransitions.Value); } // Throw an error if nothing beyond the required transitions could be added if (listScheduleNext.TransitionCount == RequiredPeptides.TransitionCount) { string itemName = IsPrecursorLimited ? Resources.AbstractMassListExporter_ExportScheduledBuckets_precursors : Resources.AbstractMassListExporter_ExportScheduledBuckets_transitions; var sb = new StringBuilder(); foreach (var peptideSchedule in listSchedules) { if (peptideSchedule.TransitionCount > MaxTransitions.Value) { sb.AppendLine(string.Format("{0} - {1} {2}", // Not L10N peptideSchedule.Peptide.Peptide, peptideSchedule.TransitionCount, itemName)); } } var message = new StringBuilder(Resources.AbstractMassListExporter_ExportScheduledBuckets_Failed_to_schedule_the_following_peptides_with_the_current_settings); message.AppendLine().AppendLine().AppendLine(sb.ToString()); if (OptimizeStepCount == 0) { message.AppendLine().AppendLine(string.Format(Resources.AbstractMassListExporter_ExportScheduledBuckets_Check_max_concurrent__0__count, itemName)); } else { message.Append(string.Format(Resources.AbstractMassListExporter_ExportScheduledBuckets_Check_max_concurrent__0__count_and_optimization_step_count, itemName)); } throw new IOException(message.ToString()); } listScheduleBuckets.Add(listScheduleNext); totalScheduled += listScheduleNext.TransitionCount; } int countScheduleGroups = listScheduleBuckets.Count; if (countScheduleGroups > 1) { // Balance the scheduling buckets to counteract the tendancy for each // successive bucket to have fewer transitions than the previous. // CONSIDER: O(n^2) but number of groups should never get that large int balanceCount = totalScheduled / countScheduleGroups; for (int i = 0; i < countScheduleGroups; i++) { var bucketUnder = listScheduleBuckets[i]; if (bucketUnder.TransitionCount >= balanceCount) { continue; } // It should not be possible to borrow from scheduling lists // after the current list, since the reason they are there is // that they had too much overlap to be included in any of the // preceding buckets. for (int j = 0; j < i; j++) { var bucketOver = listScheduleBuckets[j]; if (bucketOver.TransitionCount <= balanceCount) { continue; } BorrowTransitions(bucketUnder, bucketOver, balanceCount); // If the under bucket ever goes over balance, then quit. if (bucketUnder.Count > balanceCount) { break; } } } } foreach (var listScheduleNext in listScheduleBuckets) { WriteScheduledList(fileIterator, listScheduleNext); } WriteScheduledList(fileIterator, listUnscheduled); }