OpenMS
MSExperiment.h
Go to the documentation of this file.
1 // Copyright (c) 2002-present, OpenMS Inc. -- EKU Tuebingen, ETH Zurich, and FU Berlin
2 // SPDX-License-Identifier: BSD-3-Clause
3 //
4 // --------------------------------------------------------------------------
5 // $Maintainer: Timo Sachsenberg $
6 // $Authors: Marc Sturm, Tom Waschischeck $
7 // --------------------------------------------------------------------------
8 
9 #pragma once
10 
19 
20 #include <vector>
21 
22 
23 namespace OpenMS
24 {
25  class Peak1D;
26  class ChromatogramPeak;
27 
29 
48  class OPENMS_DLLAPI MSExperiment final : public ExperimentalSettings
49  {
50 
51 public:
52  typedef Peak1D PeakT;
54 
56 
57  typedef PeakT PeakType;
67 
70 
78  typedef std::vector<SpectrumType> Base;
80 
82 
83  typedef std::vector<SpectrumType>::iterator Iterator;
86  typedef std::vector<SpectrumType>::const_iterator ConstIterator;
92 
94  // Attention: these refer to the spectra vector only!
96  typedef Base::value_type value_type;
97  typedef Base::iterator iterator;
98  typedef Base::const_iterator const_iterator;
99 
102 
104  MSExperiment(const MSExperiment & source);
105 
108 
111 
114 
117 
119  ~MSExperiment() override;
120 
122  bool operator==(const MSExperiment & rhs) const;
123 
125  bool operator!=(const MSExperiment & rhs) const;
126 
128  Size size() const noexcept;
129 
131  void resize(Size n);
132 
134  bool empty() const noexcept;
135 
137  void reserve(Size n);
138 
140  SpectrumType& operator[](Size n);
141 
143  const SpectrumType& operator[](Size n) const;
144 
145  Iterator begin() noexcept;
146 
147  ConstIterator begin() const noexcept;
148 
149  ConstIterator cbegin() const noexcept;
150 
151  Iterator end();
152 
153  ConstIterator end() const noexcept;
154 
155  ConstIterator cend() const noexcept;
157 
158  // Aliases / chromatograms
159  void reserveSpaceSpectra(Size s);
160  void reserveSpaceChromatograms(Size s);
161 
163 
164 
170  template <class Container>
171  void get2DData(Container& cont) const
172  {
173  for (typename Base::const_iterator spec = spectra_.begin(); spec != spectra_.end(); ++spec)
174  {
175  if (spec->getMSLevel() != 1)
176  {
177  continue;
178  }
179  typename Container::value_type s; // explicit object here, since instantiation within push_back() fails on VS<12
180  for (typename SpectrumType::const_iterator it = spec->begin(); it != spec->end(); ++it)
181  {
182  cont.push_back(s);
183  cont.back().setRT(spec->getRT());
184  cont.back().setMZ(it->getMZ());
185  cont.back().setIntensity(it->getIntensity());
186  }
187  }
188  }
189 
201  template <class Container>
202  void set2DData(const Container& container)
203  {
204  set2DData<false, Container>(container);
205  }
206 
221  template <class Container>
222  void set2DData(const Container& container, const StringList& store_metadata_names)
223  {
224  // clean up the container first
225  clear(true);
226  SpectrumType* spectrum = nullptr;
227  typename PeakType::CoordinateType current_rt = -std::numeric_limits<typename PeakType::CoordinateType>::max();
228  for (typename Container::const_iterator iter = container.begin(); iter != container.end(); ++iter)
229  {
230  // check if the retention time has changed
231  if (current_rt != iter->getRT() || spectrum == nullptr)
232  {
233  // append new spectrum
234  if (current_rt > iter->getRT())
235  {
236  throw Exception::Precondition(__FILE__, __LINE__, OPENMS_PRETTY_FUNCTION, "Input container is not sorted!");
237  }
238  current_rt = iter->getRT();
239  spectrum = createSpec_(current_rt, store_metadata_names);
240  }
241 
242  // add either data point or mass traces (depending on template argument value)
243  ContainerAdd_<typename Container::value_type, false>::addData_(spectrum, &(*iter), store_metadata_names);
244  }
245  }
246 
265  template <bool add_mass_traces, class Container>
266  void set2DData(const Container& container)
267  {
268  // clean up the container first
269  clear(true);
270  SpectrumType* spectrum = nullptr;
271  typename PeakType::CoordinateType current_rt = -std::numeric_limits<typename PeakType::CoordinateType>::max();
272  for (typename Container::const_iterator iter = container.begin(); iter != container.end(); ++iter)
273  {
274  // check if the retention time has changed
275  if (current_rt != iter->getRT() || spectrum == nullptr)
276  {
277  // append new spectrum
278  if (current_rt > iter->getRT())
279  {
280  throw Exception::Precondition(__FILE__, __LINE__, OPENMS_PRETTY_FUNCTION, "Input container is not sorted!");
281  }
282  current_rt = iter->getRT();
283  spectrum = createSpec_(current_rt);
284  }
285 
286  // add either data point or mass traces (depending on template argument value)
288  }
289  }
290 
292 
293 
295 
296  AreaIterator areaBegin(CoordinateType min_rt, CoordinateType max_rt,
298  CoordinateType min_mz, CoordinateType max_mz, UInt ms_level = 1);
299 
301  AreaIterator areaBegin(const RangeManagerType& range, UInt ms_level = 1);
302 
305 
308 
310  ConstAreaIterator areaBeginConst(const RangeManagerType& range, UInt ms_level = 1) const;
311 
314 
315  /* @brief Retrieves the peak data in the given mz-rt range and store data spectrum-wise in separate arrays.
316  *
317  * For fast pyOpenMS access to peak data in format: [rt, [mz, intensity]]
318  *
319  * @param min_rt The minimum retention time.
320  * @param max_rt The maximum retention time.
321  * @param min_mz The minimum m/z value.
322  * @param max_mz The maximum m/z value.
323  * @param ms_level The MS level of the spectra to consider.
324  * @param rt The vector to store the retention times in.
325  * @param mz The vector to store the m/z values in.
326  * @param intensity The vector to store the intensities in.
327  */
329  CoordinateType min_rt,
330  CoordinateType max_rt,
331  CoordinateType min_mz,
332  CoordinateType max_mz,
333  Size ms_level,
334  std::vector<float>& rt,
335  std::vector<std::vector<float>>& mz,
336  std::vector<std::vector<float>>& intensity) const;
337 
338  /* @brief Retrieves the peak data in the given mz-rt range and store data spectrum-wise in separate arrays.
339  *
340  * For fast pyOpenMS access to MS1 peak data in format: [rt, [mz, intensity, ion mobility]]
341  *
342  * @param min_rt The minimum retention time.
343  * @param max_rt The maximum retention time.
344  * @param min_mz The minimum m/z value.
345  * @param max_mz The maximum m/z value.
346  * @param ms_level The MS level of the spectra to consider.
347  * @param rt The vector to store the retention times in.
348  * @param mz The vector to store the m/z values in.
349  * @param intensity The vector to store the intensities in.
350  * @param ion_mobility The vector to store the ion mobility values in.
351  */
353  CoordinateType min_rt,
354  CoordinateType max_rt,
355  CoordinateType min_mz,
356  CoordinateType max_mz,
357  Size ms_level,
358  std::vector<float>& rt,
359  std::vector<std::vector<float>>& mz,
360  std::vector<std::vector<float>>& intensity,
361  std::vector<std::vector<float>>& ion_mobility) const;
362 
363  /* @brief Retrieves the peak data in the given mz-rt range and store in separate arrays.
364  *
365  * For fast pyOpenMS access to MS1 peak data in format: [rt, mz, intensity]
366  *
367  * @param min_rt The minimum retention time.
368  * @param max_rt The maximum retention time.
369  * @param min_mz The minimum m/z value.
370  * @param max_mz The maximum m/z value.
371  * @param ms_level The MS level of the spectra to consider.
372  * @param rt The vector to store the retention times in.
373  * @param mz The vector to store the m/z values in.
374  * @param intensity The vector to store the intensities in.
375  */
377  CoordinateType min_rt,
378  CoordinateType max_rt,
379  CoordinateType min_mz,
380  CoordinateType max_mz,
381  Size ms_level,
382  std::vector<float>& rt,
383  std::vector<float>& mz,
384  std::vector<float>& intensity) const;
385 
386 
387  /* @brief Retrieves the peak data in the given mz-rt range and store in separate arrays.
388  *
389  * For fast pyOpenMS access to MS1 peak data in format: [rt, mz, intensity, ion mobility]
390  *
391  * @param min_rt The minimum retention time.
392  * @param max_rt The maximum retention time.
393  * @param min_mz The minimum m/z value.
394  * @param max_mz The maximum m/z value.
395  * @param ms_level The MS level of the spectra to consider.
396  * @param rt The vector to store the retention times in.
397  * @param mz The vector to store the m/z values in.
398  * @param intensity The vector to store the intensities in.
399  */
401  CoordinateType min_rt,
402  CoordinateType max_rt,
403  CoordinateType min_mz,
404  CoordinateType max_mz,
405  Size ms_level,
406  std::vector<float>& rt,
407  std::vector<float>& mz,
408  std::vector<float>& intensity,
409  std::vector<float>& ion_mobility) const;
410 
422 
423  template <typename Iterator>
424  auto operator()(Iterator begin, Iterator end) const {
425  // Static assert to verify iterator type has intensity accessor
426  using ValueType = typename std::iterator_traits<Iterator>::value_type;
427  using IntensityType = decltype(std::declval<ValueType>().getIntensity());
428  static_assert(std::is_member_function_pointer_v<decltype(&ValueType::getIntensity)>,
429  "Iterator value type must have getIntensity() member function");
430 
431  IntensityType sum{};
432  for (auto it = begin; it != end; ++it) {
433  sum += it->getIntensity();
434  }
435  return sum;
436  }
437 };
438 
488 template<class MzReductionFunctionType>
489 std::vector<std::vector<MSExperiment::CoordinateType>> aggregate(
490  const std::vector<std::pair<RangeMZ, RangeRT>>& mz_rt_ranges,
491  unsigned int ms_level,
492  MzReductionFunctionType func_mz_reduction) const
493 {
494  // Early exit if there are no ranges
495  if (mz_rt_ranges.empty())
496  {
497  // likely an error, but we return an empty vector instead of throwing an exception for now
498  return {};
499  }
500 
501  // Create a view of the spectra with given MS level
502  std::vector<std::reference_wrapper<const MSSpectrum>> spectra_view;
503  spectra_view.reserve(spectra_.size());
504  std::copy_if(spectra_.begin(), spectra_.end(),
505  std::back_inserter(spectra_view),
506  [ms_level](const auto& spec) {
507  return spec.getMSLevel() == ms_level;
508  });
509 
510  // Early exit if there are no spectra with the given MS level
511  if (spectra_view.empty()) { // could be valid use or an error -> we return an empty vector
512  return {};
513  }
514 
515  // Get the indices of the spectra covered by the RT ranges by considering the MS level
516  // If start and stop are the same, the range is empty
517  auto getCoveredSpectra = [](
518  const std::vector<std::reference_wrapper<const MSSpectrum>>& spectra_view,
519  const std::vector<std::pair<RangeMZ, RangeRT>>& mz_rt_ranges)
520  -> std::vector<std::pair<size_t, size_t>>
521  {
522  std::vector<std::pair<size_t, size_t>> res;
523  res.reserve(mz_rt_ranges.size());
524 
525  for (const auto & mz_rt : mz_rt_ranges)
526  {
527  // std::cout << "rt range: " << mz_rt.second.getMin() << " - " << mz_rt.second.getMax() << std::endl;
528  // std::cout << "specs start:" << spectra_view[0].get().getRT() << " specs end:" << spectra_view[spectra_view.size() - 1].get().getRT() << std::endl;
529  auto start_it = std::lower_bound(spectra_view.begin(), spectra_view.end(), mz_rt.second.getMin(),
530  [](const auto& spec, double rt)
531  { return spec.get().getRT() < rt; });
532 
533  auto stop_it = std::upper_bound(spectra_view.begin(), spectra_view.end(), mz_rt.second.getMax(),
534  [](double rt, const auto& spec)
535  { return rt < spec.get().getRT(); });
536 
537  res.emplace_back(
538  std::distance(spectra_view.begin(), start_it),
539  std::distance(spectra_view.begin(), stop_it)
540  );
541  // std::cout << "start: " << std::distance(spectra_view.begin(), start_it) << " stop: " << std::distance(spectra_view.begin(), stop_it) << std::endl;
542  }
543  return res;
544  };
545 
546  // For each range, gets (spectrum start index, spectrum stop index). The spectra covered by each RT range.
547  const std::vector<std::pair<size_t, size_t>> rt_ranges_idcs = getCoveredSpectra(spectra_view, mz_rt_ranges);
548 
549  // Initialize result vector
550  std::vector<std::vector<MSExperiment::CoordinateType>> result(mz_rt_ranges.size());
551 
552  // Initialize counts per spectrum index and total mappings
553  std::vector<std::vector<size_t>> spec_idx_to_range_idx(spectra_view.size());
554 
555  // Build spectrum to range index mapping
556  for (size_t i = 0; i < rt_ranges_idcs.size(); ++i)
557  {
558  const auto& [start, stop] = rt_ranges_idcs[i];
559  result[i].resize(stop - start);
560  // std::cout << "start: " << start << " stop: " << stop << std::endl;
561  for (size_t j = start; j < stop; ++j)
562  {
563  spec_idx_to_range_idx[j].push_back(i);
564  }
565  }
566 
567  #pragma omp parallel for schedule(dynamic)
568  for (Int64 i = 0; i < (Int64)spec_idx_to_range_idx.size(); ++i) // OpenMP on windows still requires signed loop variable
569  {
570  if (spec_idx_to_range_idx[i].empty()) continue; // no ranges for this spectrum? skip it
571 
572  const auto& spec = spectra_view[i].get();
573  auto spec_begin = spec.cbegin();
574  auto spec_end = spec.cend();
575 
576  for (size_t range_idx : spec_idx_to_range_idx[i])
577  {
578  const auto& mz_range = mz_rt_ranges[range_idx].first;
579 
580  // Find data points within MZ range
581  auto start_it = spec.PosBegin(spec_begin, mz_range.getMinMZ(), spec_end);
582  auto end_it = start_it;
583 
584  while (end_it != spec_end && end_it->getPosition() <= mz_range.getMaxMZ())
585  {
586  ++end_it;
587  }
588 
589  // std::cout << "calculating reduction on range: " << range_idx << " for spectrum: " << i << " and peaks " << std::distance(spec.begin(), start_it) << " - " << std::distance(spec.begin(), end_it) << std::endl;
590 
591  // Calculate result using provided reduction function
592  result[range_idx][i - rt_ranges_idcs[range_idx].first] =
593  func_mz_reduction(start_it, end_it);
594  }
595  }
596  return result;
597  }
598 
599 // Overload without func_mz_reduction parameter (default to SumIntensityReduction). Needed because of template deduction issues
600 std::vector<std::vector<MSExperiment::CoordinateType>> aggregate(
601  const std::vector<std::pair<RangeMZ, RangeRT>>& mz_rt_ranges,
602  unsigned int ms_level) const
603 {
604  return aggregate(mz_rt_ranges, ms_level, SumIntensityReduction());
605 }
606 
619 template<class MzReductionFunctionType>
620 std::vector<MSChromatogram> extractXICs(
621  const std::vector<std::pair<RangeMZ, RangeRT>>& mz_rt_ranges,
622  unsigned int ms_level,
623  MzReductionFunctionType func_mz_reduction) const
624 {
625  // Early exit if there are no ranges
626  if (mz_rt_ranges.empty())
627  {
628  // likely an error, but we return an empty vector instead of throwing an exception for now
629  return {};
630  }
631 
632  // Create a view of the spectra with given MS level
633  std::vector<std::reference_wrapper<const MSSpectrum>> spectra_view;
634  spectra_view.reserve(spectra_.size());
635  std::copy_if(spectra_.begin(), spectra_.end(),
636  std::back_inserter(spectra_view),
637  [ms_level](const auto& spec) {
638  return spec.getMSLevel() == ms_level;
639  });
640 
641  // Early exit if there are no spectra with the given MS level
642  if (spectra_view.empty()) { // could be valid use or an error -> we return an empty vector
643  return {};
644  }
645 
646  // Get the indices of the spectra covered by the RT ranges by considering the MS level
647  // If start and stop are the same, the range is empty
648  auto getCoveredSpectra = [](
649  const std::vector<std::reference_wrapper<const MSSpectrum>>& spectra_view,
650  const std::vector<std::pair<RangeMZ, RangeRT>>& mz_rt_ranges)
651  -> std::vector<std::pair<size_t, size_t>>
652  {
653  std::vector<std::pair<size_t, size_t>> res;
654  res.reserve(mz_rt_ranges.size());
655 
656  for (const auto & mz_rt : mz_rt_ranges)
657  {
658  auto start_it = std::lower_bound(spectra_view.begin(), spectra_view.end(), mz_rt.second.getMin(),
659  [](const auto& spec, double rt)
660  { return spec.get().getRT() < rt; });
661 
662  auto stop_it = std::upper_bound(spectra_view.begin(), spectra_view.end(), mz_rt.second.getMax(),
663  [](double rt, const auto& spec)
664  { return rt < spec.get().getRT(); });
665 
666  res.emplace_back(
667  std::distance(spectra_view.begin(), start_it),
668  std::distance(spectra_view.begin(), stop_it)
669  );
670  }
671  return res;
672  };
673 
674  // For each range, gets (spectrum start index, spectrum stop index). The spectra covered by each RT range.
675  const std::vector<std::pair<size_t, size_t>> rt_ranges_idcs = getCoveredSpectra(spectra_view, mz_rt_ranges);
676 
677  // Initialize result vector
678  std::vector<MSChromatogram> result(mz_rt_ranges.size());
679 
680  // Initialize counts per spectrum index and total mappings
681  std::vector<std::vector<size_t>> spec_idx_to_range_idx(spectra_view.size());
682 
683  // Build spectrum to range index mapping
684  for (size_t i = 0; i < rt_ranges_idcs.size(); ++i)
685  {
686  const auto& [start, stop] = rt_ranges_idcs[i];
687  result[i].resize(stop - start);
688  result[i].getProduct().setMZ(
689  (mz_rt_ranges[i].first.getMinMZ() + mz_rt_ranges[i].first.getMaxMZ()) / 2.0);
690  for (size_t j = start; j < stop; ++j)
691  {
692  spec_idx_to_range_idx[j].push_back(i);
693  }
694  }
695 
696  #pragma omp parallel for schedule(dynamic)
697  for (Int64 i = 0; i < (Int64)spec_idx_to_range_idx.size(); ++i) // OpenMP on windows still requires signed loop variable
698  {
699  if (spec_idx_to_range_idx[i].empty()) continue; // no ranges for this spectrum? skip
700 
701  const auto& spec = spectra_view[i].get();
702  const double rt = spec.getRT();
703  auto spec_begin = spec.cbegin();
704  auto spec_end = spec.cend();
705 
706  for (size_t range_idx : spec_idx_to_range_idx[i])
707  {
708  const auto& mz_range = mz_rt_ranges[range_idx].first;
709 
710  // Find data points within MZ range
711  auto start_it = spec.PosBegin(spec_begin, mz_range.getMinMZ(), spec_end);
712  auto end_it = start_it;
713 
714  while (end_it != spec_end && end_it->getPosition() <= mz_range.getMaxMZ())
715  {
716  ++end_it;
717  }
718 
719  // Calculate result using provided reduction function
720  result[range_idx][i - rt_ranges_idcs[range_idx].first] =
721  ChromatogramPeak(rt, func_mz_reduction(start_it, end_it));
722  }
723  }
724 
725  for (auto& r : result) r.updateRanges(); // TODO: prob.. faster to look at first and last peaks as range is sorted
726 
727  return result;
728  }
729 
730 // Overload without func_mz_reduction parameter (needed because of template deduction issue)
731 std::vector<MSChromatogram> extractXICs(
732  const std::vector<std::pair<RangeMZ, RangeRT>>& mz_rt_ranges,
733  unsigned int ms_level) const
734 {
735  return extractXICs(mz_rt_ranges, ms_level, SumIntensityReduction());
736 }
737 
746  std::vector<std::vector<MSExperiment::CoordinateType>> aggregateFromMatrix(
747  const Matrix<double>& ranges,
748  unsigned int ms_level,
749  const std::string& mz_agg) const
750  {
751  // Check matrix dimensions
752  if (ranges.cols() != 4)
753  {
754  throw Exception::InvalidParameter(__FILE__, __LINE__, OPENMS_PRETTY_FUNCTION,
755  "Range matrix must have 4 columns [mz_min, mz_max, rt_min, rt_max]");
756  }
757 
758  // Convert matrix rows to vector of pairs
759  std::vector<std::pair<RangeMZ, RangeRT>> mz_rt_ranges;
760  mz_rt_ranges.reserve((Size)ranges.rows());
761 
762  for (Size i = 0; i < (Size)ranges.rows(); ++i)
763  {
764  mz_rt_ranges.emplace_back(
765  RangeMZ(ranges(i, 0), ranges(i, 1)), // min max mz
766  RangeRT(ranges(i, 2), ranges(i, 3)) // min max rt
767  );
768  // std::cout << "mz: " << ranges(i, 0) << " - " << ranges(i, 1) << " rt: " << ranges(i, 2) << " - " << ranges(i, 3) << std::endl;
769  }
770 
771  // Call appropriate aggregation function based on mz_agg parameter
772  if (mz_agg == "sum")
773  {
774  return aggregate(mz_rt_ranges, ms_level,
775  [](auto begin_it, auto end_it)
776  {
777  return std::accumulate(begin_it, end_it, 0.0,
778  [](double a, const Peak1D& b) { return a + b.getIntensity(); });
779  });
780  }
781  else if (mz_agg == "max")
782  {
783  return aggregate(mz_rt_ranges, ms_level,
784  [](auto begin_it, auto end_it)->double
785  {
786  if (begin_it == end_it) return 0.0;
787  return std::max_element(begin_it, end_it,
788  [](const Peak1D& a, const Peak1D& b) { return a.getIntensity() < b.getIntensity(); }
789  )->getIntensity();
790  });
791  }
792  else if (mz_agg == "min")
793  {
794  return aggregate(mz_rt_ranges, ms_level,
795  [](auto begin_it, auto end_it)->double
796  {
797  if (begin_it == end_it) return 0.0;
798  return std::min_element(begin_it, end_it,
799  [](const Peak1D& a, const Peak1D& b) { return a.getIntensity() < b.getIntensity(); }
800  )->getIntensity();
801  });
802  }
803  else if (mz_agg == "mean")
804  {
805  return aggregate(mz_rt_ranges, ms_level,
806  [](auto begin_it, auto end_it)
807  {
808  if (begin_it == end_it) return 0.0;
809  double sum = std::accumulate(begin_it, end_it, 0.0,
810  [](double a, const Peak1D& b) { return a + b.getIntensity(); });
811  return sum / static_cast<double>(std::distance(begin_it, end_it));
812  });
813  }
814  else
815  {
816  throw Exception::InvalidValue(__FILE__, __LINE__, OPENMS_PRETTY_FUNCTION,
817  "Invalid aggregation function", mz_agg);
818  }
819  }
820 
829  std::vector<MSChromatogram> extractXICsFromMatrix(
830  const Matrix<double>& ranges,
831  unsigned int ms_level,
832  const std::string& mz_agg) const
833  {
834  // Check matrix dimensions
835  if (ranges.cols() != 4)
836  {
837  throw Exception::InvalidParameter(__FILE__, __LINE__, OPENMS_PRETTY_FUNCTION,
838  "Range matrix must have 4 columns [mz_min, mz_max, rt_min, rt_max]");
839  }
840 
841  // Convert matrix rows to vector of pairs
842  std::vector<std::pair<RangeMZ, RangeRT>> mz_rt_ranges;
843  mz_rt_ranges.reserve((Size)ranges.rows());
844 
845  for (Size i = 0; i < (Size)ranges.rows(); ++i)
846  {
847  mz_rt_ranges.emplace_back(
848  RangeMZ(ranges(i, 0), ranges(i, 1)),
849  RangeRT(ranges(i, 2), ranges(i, 3))
850  );
851  }
852 
853  // Call appropriate extractXICs function based on mz_agg parameter
854  if (mz_agg == "sum")
855  {
856  return extractXICs(mz_rt_ranges, ms_level,
857  [](auto begin_it, auto end_it)
858  {
859  return std::accumulate(begin_it, end_it, 0.0,
860  [](double a, const Peak1D& b) { return a + b.getIntensity(); });
861  });
862  }
863  else if (mz_agg == "max")
864  {
865  return extractXICs(mz_rt_ranges, ms_level,
866  [](auto begin_it, auto end_it)->double
867  {
868  if (begin_it == end_it) return 0.0;
869  return std::max_element(begin_it, end_it,
870  [](const Peak1D& a, const Peak1D& b) { return a.getIntensity() < b.getIntensity(); }
871  )->getIntensity();
872  });
873  }
874  else if (mz_agg == "min")
875  {
876  return extractXICs(mz_rt_ranges, ms_level,
877  [](auto begin_it, auto end_it)->double
878  {
879  if (begin_it == end_it) return 0.0;
880  return std::min_element(begin_it, end_it,
881  [](const Peak1D& a, const Peak1D& b) { return a.getIntensity() < b.getIntensity(); }
882  )->getIntensity();
883  });
884  }
885  else if (mz_agg == "mean")
886  {
887  return extractXICs(mz_rt_ranges, ms_level,
888  [](auto begin_it, auto end_it)
889  {
890  if (begin_it == end_it) return 0.0;
891  double sum = std::accumulate(begin_it, end_it, 0.0,
892  [](double a, const Peak1D& b) { return a + b.getIntensity(); });
893  return sum / static_cast<double>(std::distance(begin_it, end_it));
894  });
895  }
896  else
897  {
898  throw Exception::InvalidValue(__FILE__, __LINE__, OPENMS_PRETTY_FUNCTION,
899  "Invalid aggregation function", mz_agg);
900  }
901  }
902 
911 
920 
927 
934 
935 
944 
954 
962 
969  void clearRanges()
970  {
971  combined_ranges_.clearRanges();
972  spectrum_ranges_.clearRanges();
973  chromatogram_ranges_.clearRanges();
974  }
975 
977  double getMinRT() const { return combined_ranges_.getMinRT(); }
978 
980  double getMaxRT() const { return combined_ranges_.getMaxRT(); }
981 
983  double getMinMZ() const { return combined_ranges_.getMinMZ(); }
984 
986  double getMaxMZ() const { return combined_ranges_.getMaxMZ(); }
987 
989  double getMinIntensity() const { return combined_ranges_.getMinIntensity(); }
990 
992  double getMaxIntensity() const { return combined_ranges_.getMaxIntensity(); }
993 
995  double getMinMobility() const { return combined_ranges_.getMinMobility(); }
996 
998  double getMaxMobility() const { return combined_ranges_.getMaxMobility(); }
999 
1011 
1013  UInt64 getSize() const;
1014 
1016  std::vector<UInt> getMSLevels() const;
1017 
1019 
1023 
1026 
1029 
1034  void sortSpectra(bool sort_mz = true);
1035 
1041  void sortChromatograms(bool sort_rt = true);
1042 
1048  bool isSorted(bool check_mz = true) const;
1049 
1051 
1053  void reset();
1054 
1061 
1064 
1067 
1069  void getPrimaryMSRunPath(StringList& toFill) const;
1070 
1087 
1093  int getPrecursorSpectrum(int zero_based_index) const;
1094 
1120 
1128  int getFirstProductSpectrum(int zero_based_index) const;
1129 
1131  void swap(MSExperiment& from);
1132 
1134  void setSpectra(const std::vector<MSSpectrum>& spectra);
1135  void setSpectra(std::vector<MSSpectrum>&& spectra);
1136 
1138  void addSpectrum(const MSSpectrum& spectrum);
1139  void addSpectrum(MSSpectrum&& spectrum);
1140 
1142  const std::vector<MSSpectrum>& getSpectra() const;
1143 
1145  std::vector<MSSpectrum>& getSpectra();
1146 
1148  ConstIterator getClosestSpectrumInRT(const double RT) const;
1150 
1152  ConstIterator getClosestSpectrumInRT(const double RT, UInt ms_level) const;
1153  Iterator getClosestSpectrumInRT(const double RT, UInt ms_level);
1154 
1156  void setChromatograms(const std::vector<MSChromatogram>& chromatograms);
1157  void setChromatograms(std::vector<MSChromatogram>&& chromatograms);
1158 
1160  void addChromatogram(const MSChromatogram& chromatogram);
1162 
1164  const std::vector<MSChromatogram>& getChromatograms() const;
1165 
1167  std::vector<MSChromatogram>& getChromatograms();
1168 
1170 
1171  MSChromatogram& getChromatogram(Size id);
1173 
1176 
1179 
1183 
1194  const MSChromatogram calculateTIC(float rt_bin_size = 0, UInt ms_level = 1) const;
1195 
1201  void clear(bool clear_meta_data);
1202 
1204  bool containsScanOfLevel(size_t ms_level) const;
1205 
1207  bool hasZeroIntensities(size_t ms_level) const;
1208 
1210  bool isIMFrame() const;
1211 
1212  protected:
1214  std::vector<MSChromatogram > chromatograms_;
1216  std::vector<SpectrumType> spectra_;
1219 
1222 
1225 
1226  public:
1236  const SpectrumRangeManagerType& spectrumRanges() const { return spectrum_ranges_; }
1237 
1247  const ChromatogramRangeManagerType& chromatogramRanges() const { return chromatogram_ranges_; }
1248 
1257  const RangeManagerType& combinedRanges() const { return combined_ranges_; }
1258 
1259  private:
1260 
1262  template<typename ContainerValueType, bool addMassTraces>
1264  {
1265  static void addData_(SpectrumType* spectrum, const ContainerValueType* item);
1266  static void addData_(SpectrumType* spectrum, const ContainerValueType* item, const StringList& store_metadata_names);
1267  };
1268 
1269  template<typename ContainerValueType>
1270  struct ContainerAdd_<ContainerValueType, false>
1271  {
1273  static void addData_(SpectrumType* spectrum, const ContainerValueType* item)
1274  {
1275  // create temporary peak and insert it into spectrum
1276  spectrum->insert(spectrum->end(), PeakType());
1277  spectrum->back().setIntensity(item->getIntensity());
1278  spectrum->back().setPosition(item->getMZ());
1279  }
1281  static void addData_(SpectrumType* spectrum, const ContainerValueType* item, const StringList& store_metadata_names)
1282  {
1283  addData_(spectrum, item);
1284  for (StringList::const_iterator itm = store_metadata_names.begin(); itm != store_metadata_names.end(); ++itm)
1285  {
1286  float val = std::numeric_limits<float>::quiet_NaN();
1287  if (item->metaValueExists(*itm)) val = item->getMetaValue(*itm);
1288  spectrum->getFloatDataArrays()[itm - store_metadata_names.begin()].push_back(val);
1289  }
1290  }
1291  };
1292 
1293  template<typename ContainerValueType>
1294  struct ContainerAdd_<ContainerValueType, true>
1295  {
1297  static void addData_(SpectrumType* spectrum, const ContainerValueType* item)
1298  {
1299  if (item->metaValueExists("num_of_masstraces"))
1300  {
1301  Size mts = item->getMetaValue("num_of_masstraces");
1302  int charge = (item->getCharge()==0 ? 1 : item->getCharge()); // set to 1 if charge is 0, otherwise div/0 below
1303  for (Size i = 0; i < mts; ++i)
1304  {
1305  String meta_name = String("masstrace_intensity_") + i;
1306  if (!item->metaValueExists(meta_name))
1307  {
1308  throw Exception::Precondition(__FILE__, __LINE__, OPENMS_PRETTY_FUNCTION, String("Meta value '") + meta_name + "' expected but not found in container.");
1309  }
1310  ContainerValueType p;
1311  p.setIntensity(item->getMetaValue(meta_name));
1312  p.setPosition(item->getMZ() + Constants::C13C12_MASSDIFF_U / charge * i);
1314  }
1315  }
1317  }
1318  };
1319 
1320 
1321  /*
1322  @brief Append a spectrum to current MSExperiment
1323 
1324  @param rt RT of new spectrum
1325  @return Pointer to newly created spectrum
1326  */
1328 
1329  /*
1330  @brief Append a spectrum including floatdata arrays to current MSExperiment
1331 
1332  @param rt RT of new spectrum
1333  @param metadata_names Names of floatdata arrays attached to this spectrum
1334  @return Pointer to newly created spectrum
1335  */
1337 
1338  };
1339 
1341  OPENMS_DLLAPI std::ostream& operator<<(std::ostream& os, const MSExperiment& exp);
1342 
1343 } // namespace OpenMS
1344 
1346 
1347 
A 1-dimensional raw data point or peak for chromatograms.
Definition: ChromatogramPeak.h:28
Range manager for chromatograms.
Definition: ChromatogramRangeManager.h:31
Exception indicating that an invalid parameter was handed over to an algorithm.
Definition: Exception.h:316
Invalid value exception.
Definition: Exception.h:305
Precondition failed exception.
Definition: Exception.h:128
Description of the experimental settings.
Definition: ExperimentalSettings.h:36
Forward iterator for an area of peaks in an experiment.
Definition: AreaIterator.h:36
The representation of a chromatogram.
Definition: MSChromatogram.h:30
In-Memory representation of a mass spectrometry run.
Definition: MSExperiment.h:49
const ExperimentalSettings & getExperimentalSettings() const
returns the meta information of this experiment (const access)
MSExperiment(MSExperiment &&)=default
Move constructor.
ConstIterator IMBegin(CoordinateType im) const
Fast search for spectrum range begin.
RangeManagerType combined_ranges_
Combined range manager that provides overall ranges across both spectra and chromatograms (maintained...
Definition: MSExperiment.h:1224
ConstIterator getClosestSpectrumInRT(const double RT, UInt ms_level) const
Returns the closest(=nearest) spectrum in retention time to the given RT of a certain MS level.
std::vector< SpectrumType > spectra_
spectra
Definition: MSExperiment.h:1216
const std::vector< MSChromatogram > & getChromatograms() const
returns the chromatogram list
std::vector< SpectrumType > Base
STL base class type.
Definition: MSExperiment.h:78
void setChromatograms(std::vector< MSChromatogram > &&chromatograms)
Base::iterator iterator
Definition: MSExperiment.h:97
bool containsScanOfLevel(size_t ms_level) const
returns true if at least one of the spectra has the specified level
ConstAreaIterator areaBeginConst(CoordinateType min_rt, CoordinateType max_rt, CoordinateType min_mz, CoordinateType max_mz, UInt ms_level=1) const
Returns a non-mutable area iterator for area.
double getMaxRT() const
Get the maximum RT value from the combined ranges (includes both chromatogram and spectra ranges)
Definition: MSExperiment.h:980
~MSExperiment() override
D'tor.
PeakType::CoordinateType CoordinateType
Coordinate type of peak positions.
Definition: MSExperiment.h:62
void swap(MSExperiment &from)
Swaps the content of this map with the content of from.
MSChromatogram ChromatogramType
Chromatogram type.
Definition: MSExperiment.h:76
void addSpectrum(const MSSpectrum &spectrum)
adds a spectrum to the list
PeakType::IntensityType IntensityType
Intensity type of peaks.
Definition: MSExperiment.h:64
void set2DData(const Container &container, const StringList &store_metadata_names)
Assignment of a data container with RT and MZ to an MSExperiment.
Definition: MSExperiment.h:222
std::vector< SpectrumType >::iterator Iterator
Mutable iterator.
Definition: MSExperiment.h:84
bool clearMetaDataArrays()
Clears the meta data arrays of all contained spectra (float, integer and string arrays)
SpectrumType * createSpec_(PeakType::CoordinateType rt)
ConstAreaIterator areaBeginConst(const RangeManagerType &range, UInt ms_level=1) const
Returns a non-mutable area iterator for all peaks in range. If a dimension is empty(),...
ConstIterator RTBegin(CoordinateType rt) const
Fast search for spectrum range begin.
Size getNrSpectra() const
get the total number of spectra available
std::vector< MSChromatogram > extractXICs(const std::vector< std::pair< RangeMZ, RangeRT >> &mz_rt_ranges, unsigned int ms_level, MzReductionFunctionType func_mz_reduction) const
Extracts extracted ion chromatograms (XICs) from the MSExperiment.
Definition: MSExperiment.h:620
UInt64 getSize() const
returns the total number of peaks (spectra and chromatograms included)
std::vector< MSChromatogram > extractXICs(const std::vector< std::pair< RangeMZ, RangeRT >> &mz_rt_ranges, unsigned int ms_level) const
Definition: MSExperiment.h:731
double getMaxMZ() const
Get the maximum m/z value from the combined ranges (includes both chromatogram and spectra ranges)
Definition: MSExperiment.h:986
MSExperiment & operator=(MSExperiment &&) &=default
Move assignment operator.
ConstIterator RTEnd(CoordinateType rt) const
Fast search for spectrum range end (returns the past-the-end iterator)
void addChromatogram(MSChromatogram &&chrom)
ExperimentalSettings & getExperimentalSettings()
returns the meta information of this experiment (mutable access)
Iterator getClosestSpectrumInRT(const double RT, UInt ms_level)
double getMinMobility() const
Get the minimum mobility value from the combined ranges (includes both chromatogram and spectra range...
Definition: MSExperiment.h:995
SpectrumRangeManager SpectrumRangeManagerType
Spectrum range manager type for tracking ranges with MS level separation.
Definition: MSExperiment.h:69
double getMinIntensity() const
Get the minimum intensity value from the combined ranges (includes both chromatogram and spectra rang...
Definition: MSExperiment.h:989
SpectrumType * createSpec_(PeakType::CoordinateType rt, const StringList &metadata_names)
ChromatogramPeakT ChromatogramPeakType
Chromatogram peak type.
Definition: MSExperiment.h:60
MSSpectrum & getSpectrum(Size id)
returns a single spectrum
AreaIterator areaBegin(const RangeManagerType &range, UInt ms_level=1)
Returns an area iterator for all peaks in range. If a dimension is empty(), it is ignored (i....
Iterator RTEnd(CoordinateType rt)
Fast search for spectrum range end (returns the past-the-end iterator)
MSExperiment & operator=(const MSExperiment &source)
Assignment operator.
MSSpectrum SpectrumType
Spectrum Type.
Definition: MSExperiment.h:74
double getMinMZ() const
Get the minimum m/z value from the combined ranges (includes both chromatogram and spectra ranges)
Definition: MSExperiment.h:983
Size getNrChromatograms() const
get the total number of chromatograms available
Iterator getClosestSpectrumInRT(const double RT)
Base::value_type value_type
Definition: MSExperiment.h:96
Size size() const noexcept
The number of spectra.
MSExperiment()
Constructor.
bool operator!=(const MSExperiment &rhs) const
Equality operator.
Peak1D PeakT
Definition: MSExperiment.h:52
ConstAreaIterator areaEndConst() const
Returns a non-mutable invalid area iterator marking the end of an area.
const RangeManagerType & combinedRanges() const
Returns a const reference to the combined range manager.
Definition: MSExperiment.h:1257
void get2DPeakDataIMPerSpectrum(CoordinateType min_rt, CoordinateType max_rt, CoordinateType min_mz, CoordinateType max_mz, Size ms_level, std::vector< float > &rt, std::vector< std::vector< float >> &mz, std::vector< std::vector< float >> &intensity, std::vector< std::vector< float >> &ion_mobility) const
void set2DData(const Container &container)
Assignment of a data container with RT and MZ to an MSExperiment.
Definition: MSExperiment.h:202
void setSpectra(std::vector< MSSpectrum > &&spectra)
void getPrimaryMSRunPath(StringList &toFill) const
get the file path to the first MS run
double getMaxMobility() const
Get the maximum mobility value from the combined ranges (includes both chromatogram and spectra range...
Definition: MSExperiment.h:998
void get2DPeakData(CoordinateType min_rt, CoordinateType max_rt, CoordinateType min_mz, CoordinateType max_mz, Size ms_level, std::vector< float > &rt, std::vector< float > &mz, std::vector< float > &intensity) const
std::vector< MSChromatogram > & getChromatograms()
returns the chromatogram list (mutable)
void setSpectra(const std::vector< MSSpectrum > &spectra)
sets the spectrum list
void get2DPeakDataIM(CoordinateType min_rt, CoordinateType max_rt, CoordinateType min_mz, CoordinateType max_mz, Size ms_level, std::vector< float > &rt, std::vector< float > &mz, std::vector< float > &intensity, std::vector< float > &ion_mobility) const
void sortChromatograms(bool sort_rt=true)
Sorts the data points of the chromatograms by m/z.
double getMaxIntensity() const
Get the maximum intensity value from the combined ranges (includes both chromatogram and spectra rang...
Definition: MSExperiment.h:992
int getFirstProductSpectrum(int zero_based_index) const
Returns the index of the first product spectrum given an index.
Iterator RTBegin(CoordinateType rt)
Fast search for spectrum range begin.
void clearRanges()
Clear all ranges in all range managers.
Definition: MSExperiment.h:969
std::vector< std::vector< MSExperiment::CoordinateType > > aggregateFromMatrix(const Matrix< double > &ranges, unsigned int ms_level, const std::string &mz_agg) const
Wrapper for aggregate function that takes a matrix of m/z and RT ranges.
Definition: MSExperiment.h:746
Internal::AreaIterator< const PeakT, const PeakT &, const PeakT *, ConstIterator, SpectrumType::ConstIterator > ConstAreaIterator
Immutable area iterator type (for traversal of a rectangular subset of the peaks)
Definition: MSExperiment.h:90
void setChromatograms(const std::vector< MSChromatogram > &chromatograms)
sets the chromatogram list
Internal::AreaIterator< PeakT, PeakT &, PeakT *, Iterator, SpectrumType::Iterator > AreaIterator
Mutable area iterator type (for traversal of a rectangular subset of the peaks)
Definition: MSExperiment.h:88
double getMinRT() const
Get the minimum RT value from the combined ranges (includes both chromatogram and spectra ranges)
Definition: MSExperiment.h:977
const MSChromatogram calculateTIC(float rt_bin_size=0, UInt ms_level=1) const
Computes the total ion chromatogram (TIC) for a given MS level (use ms_level = 0 for all levels).
const std::vector< MSSpectrum > & getSpectra() const
returns the spectrum list
std::vector< MSChromatogram > extractXICsFromMatrix(const Matrix< double > &ranges, unsigned int ms_level, const std::string &mz_agg) const
Wrapper for extractXICs function that takes a matrix of m/z and RT ranges.
Definition: MSExperiment.h:829
std::vector< std::vector< MSExperiment::CoordinateType > > aggregate(const std::vector< std::pair< RangeMZ, RangeRT >> &mz_rt_ranges, unsigned int ms_level) const
Definition: MSExperiment.h:600
bool isSorted(bool check_mz=true) const
Checks if all spectra are sorted with respect to ascending RT.
MSExperiment(const MSExperiment &source)
Copy constructor.
RangeManager< RangeRT, RangeMZ, RangeIntensity, RangeMobility > RangeManagerType
Combined RangeManager type to store the overall range of all spectra and chromatograms (for backward ...
Definition: MSExperiment.h:66
std::vector< MSSpectrum > & getSpectra()
returns the spectrum list (mutable)
ConstIterator getClosestSpectrumInRT(const double RT) const
Returns the closest(=nearest) spectrum in retention time to the given RT.
ChromatogramRangeManager ChromatogramRangeManagerType
Chromatogram range manager type for tracking chromatogram-specific ranges.
Definition: MSExperiment.h:72
void set2DData(const Container &container)
Assignment of a data container with RT and MZ to an MSExperiment.
Definition: MSExperiment.h:266
ChromatogramPeak ChromatogramPeakT
Definition: MSExperiment.h:53
void sortSpectra(bool sort_mz=true)
Sorts the data points by retention time.
std::vector< UInt > getMSLevels() const
returns a sorted array of MS levels (calculated on demand)
void reset()
Clear all internal data (spectra, ranges, metadata)
const ChromatogramRangeManagerType & chromatogramRanges() const
Returns a const reference to the chromatogram range manager.
Definition: MSExperiment.h:1247
void addSpectrum(MSSpectrum &&spectrum)
void updateRanges()
Updates the m/z, intensity, mobility, and retention time ranges of all spectra and chromatograms.
bool hasZeroIntensities(size_t ms_level) const
returns true if any MS spectra of trthe specified level contain at least one peak with intensity of 0...
bool operator==(const MSExperiment &rhs) const
Equality operator.
ConstIterator IMEnd(CoordinateType im) const
Fast search for spectrum range end (returns the past-the-end iterator)
SpectrumRangeManagerType spectrum_ranges_
Spectrum range manager for tracking m/z, intensity, RT, and ion mobility ranges of spectra with MS le...
Definition: MSExperiment.h:1218
void get2DPeakDataPerSpectrum(CoordinateType min_rt, CoordinateType max_rt, CoordinateType min_mz, CoordinateType max_mz, Size ms_level, std::vector< float > &rt, std::vector< std::vector< float >> &mz, std::vector< std::vector< float >> &intensity) const
ConstIterator getPrecursorSpectrum(ConstIterator iterator) const
Returns the precursor spectrum of the scan pointed to by iterator.
Base::const_iterator const_iterator
Definition: MSExperiment.h:98
std::vector< std::vector< MSExperiment::CoordinateType > > aggregate(const std::vector< std::pair< RangeMZ, RangeRT >> &mz_rt_ranges, unsigned int ms_level, MzReductionFunctionType func_mz_reduction) const
Aggregates data over specified m/z and RT ranges at a given MS level using a custom reduction functio...
Definition: MSExperiment.h:489
void setSqlRunID(UInt64 id)
sets the run-ID which is used when storing an sqMass file
MSExperiment & operator=(const ExperimentalSettings &source)
Assignment operator.
UInt64 getSqlRunID() const
void addChromatogram(const MSChromatogram &chromatogram)
adds a chromatogram to the list
std::vector< SpectrumType >::const_iterator ConstIterator
Non-mutable iterator.
Definition: MSExperiment.h:86
void clear(bool clear_meta_data)
Clears all data and meta data.
ConstIterator getFirstProductSpectrum(ConstIterator iterator) const
const SpectrumRangeManagerType & spectrumRanges() const
Returns a const reference to the spectrum range manager.
Definition: MSExperiment.h:1236
int getPrecursorSpectrum(int zero_based_index) const
Returns the index of the precursor spectrum for spectrum at index zero_based_index.
std::vector< MSChromatogram > chromatograms_
chromatograms
Definition: MSExperiment.h:1214
ChromatogramRangeManagerType chromatogram_ranges_
Chromatogram range manager for tracking RT, intensity, and m/z ranges of chromatograms.
Definition: MSExperiment.h:1221
AreaIterator areaEnd()
Returns an invalid area iterator marking the end of an area.
bool isIMFrame() const
Are all MSSpectra in this experiment part of an IM Frame? I.e. they all have the same RT,...
The representation of a 1D spectrum.
Definition: MSSpectrum.h:44
const FloatDataArrays & getFloatDataArrays() const
Returns a const reference to the float meta data arrays.
void setRT(double rt)
Sets the absolute retention time (in seconds)
A 1-dimensional raw data point or peak.
Definition: Peak1D.h:28
double CoordinateType
Coordinate type.
Definition: Peak1D.h:40
IntensityType getIntensity() const
Definition: Peak1D.h:82
float IntensityType
Intensity type.
Definition: Peak1D.h:36
Advanced range manager for MS spectra with separate ranges for each MS level.
Definition: SpectrumRangeManager.h:44
A more convenient string class.
Definition: String.h:34
int64_t Int64
Signed integer type (64bit)
Definition: Types.h:40
uint64_t UInt64
Unsigned integer type (64bit)
Definition: Types.h:47
unsigned int UInt
Unsigned integer type.
Definition: Types.h:64
size_t Size
Size type e.g. used as variable which can hold result of size()
Definition: Types.h:97
std::vector< String > StringList
Vector of String.
Definition: ListUtils.h:44
static double sum(IteratorType begin, IteratorType end)
Calculates the sum of a range of values.
Definition: StatisticFunctions.h:103
const double C13C12_MASSDIFF_U
Definition: Constants.h:95
Main OpenMS namespace.
Definition: openswathalgo/include/OpenMS/OPENSWATHALGO/DATAACCESS/ISpectrumAccess.h:19
Peak2D PeakType
Definition: MassTrace.h:21
std::ostream & operator<<(std::ostream &os, const AccurateMassSearchResult &amsr)
static void addData_(SpectrumType *spectrum, const ContainerValueType *item)
general method for adding data points
Definition: MSExperiment.h:1273
static void addData_(SpectrumType *spectrum, const ContainerValueType *item, const StringList &store_metadata_names)
general method for adding data points, including metadata arrays (populated from metainfointerface)
Definition: MSExperiment.h:1281
static void addData_(SpectrumType *spectrum, const ContainerValueType *item)
specialization for adding feature mass traces (does not support metadata_names currently)
Definition: MSExperiment.h:1297
Helper class to add either general data points in set2DData or use mass traces from meta values.
Definition: MSExperiment.h:1264
static void addData_(SpectrumType *spectrum, const ContainerValueType *item)
static void addData_(SpectrumType *spectrum, const ContainerValueType *item, const StringList &store_metadata_names)
Calculates the sum of intensities for a range of elements.
Definition: MSExperiment.h:421
auto operator()(Iterator begin, Iterator end) const
Definition: MSExperiment.h:424
Definition: RangeManager.h:358
Definition: RangeManager.h:295