ProteoWizard
PeptideTest.cpp
Go to the documentation of this file.
1 //
2 // $Id$
3 //
4 //
5 // Original author: Darren Kessner <darren@proteowizard.org>
6 //
7 // Copyright 2006 Louis Warschaw Prostate Cancer Center
8 // Cedars Sinai Medical Center, Los Angeles, California 90048
9 //
10 // Licensed under the Apache License, Version 2.0 (the "License");
11 // you may not use this file except in compliance with the License.
12 // You may obtain a copy of the License at
13 //
14 // http://www.apache.org/licenses/LICENSE-2.0
15 //
16 // Unless required by applicable law or agreed to in writing, software
17 // distributed under the License is distributed on an "AS IS" BASIS,
18 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
19 // See the License for the specific language governing permissions and
20 // limitations under the License.
21 //
22 
23 
25 #include "Peptide.hpp"
27 #include "boost/thread/thread.hpp"
28 #include "boost/thread/barrier.hpp"
29 
30 
31 using namespace pwiz::util;
32 using namespace pwiz::proteome;
33 using namespace pwiz::chemistry;
34 
35 
36 ostream* os_ = 0;
37 
38 
39 void test()
40 {
41  Peptide angiotensin("DRVYIHPF");
42  if (os_) *os_ << "angiotensin: " << angiotensin.sequence() << " " << angiotensin.formula() << endl;
43 
44  Peptide alpha16("WHWLQL");
45  if (os_) *os_ << "alpha16: " << alpha16.sequence() << " " << alpha16.formula() << endl;
46 }
47 
48 
49 const char* sequences[] =
50 {
51  "CLPMILDNK",
52  "AVSNPFQQR",
53  "CELLFFFK",
54  "AGASIVGVNCR",
55  "QPTPPFFGR",
56  "AVFHMQSVK",
57  "TRUCKER"
58 };
59 
60 
62 {
63  const char* sequence;
64  double monoMassNeutral, monoMassPlus1, monoMassPlus2;
65  double avgMassNeutral, avgMassPlus1, avgMassPlus2;
66 };
67 
69 {
70  { "ELK", 388.2322, 389.24005, 195.12396, 388.45918, 389.4665, 195.2369 },
71  { "DEERLICKER", 1289.6398, 1290.6477, 645.8278, 1290.44644, 1291.4537, 646.2305 },
72  { "ELVISLIVES", 1100.6329, 1101.6408, 551.3243, 1101.29052, 1102.2978, 551.6525 },
73  { "THEQUICKRWNFUMPSVERTHELAYDG", 3348.3249, 3349.3328, 1675.17035, 3348.44626, 3349.45416, 1675.23103 },
74  { "No?PepTidE...", 0, 0, 0, 0, 0, 0 }
75 };
76 
77 const size_t testPeptidesSize = sizeof(testPeptides)/sizeof(TestPeptide);
78 
80 {
81  for (size_t i=0; i < testPeptidesSize; ++i)
82  {
83  const TestPeptide& p = testPeptides[i];
84  double BIG_EPSILON = 0.001;
85 
87  if (os_) *os_ << peptide.sequence() << ": " << peptide.formula() <<
88  " " << peptide.monoisotopicMass() <<
89  " " << peptide.molecularWeight() << endl;
94  unit_assert_equal(peptide.monoisotopicMass(1, true), p.monoMassPlus1, BIG_EPSILON);
95  unit_assert_equal(peptide.molecularWeight(1, true), p.avgMassPlus1, BIG_EPSILON);
96  unit_assert_equal(peptide.monoisotopicMass(2, true), p.monoMassPlus2, BIG_EPSILON);
97  unit_assert_equal(peptide.molecularWeight(2, true), p.avgMassPlus2, BIG_EPSILON);
98 
99  peptide = p.sequence; // test assignment
100  if (os_) *os_ << peptide.sequence() << ": " << peptide.formula() <<
101  " " << peptide.monoisotopicMass() <<
102  " " << peptide.molecularWeight() << endl;
107  }
108 }
109 
110 
112 {
113  const char* motif;
114  const char* formula;
116  double deltaAvgMass;
117  bool isDynamic;
118 };
119 
121 {
122  { "M", "O1", 15.9949, 15.9994, true }, // Oxidation of M
123  { "C", "C2H3N1O1", 57.02146, 57.052, false }, // Carboxyamidomethylation of C
124  { "(Q", "N-1H-3", -17.02655, -17.0306, false }, // Pyroglutamic acid from Q at the N terminus
125  { "(E", "N-1H-3", -17.02655, -17.0306, true }, // Pyroglutamic acid from E at the N terminus
126  { "N!G", "N-1H-3", -17.02655, -17.0306, true }, // Succinimide from N when N terminal to G
127  //{ "[NQ]", "O1N-1H-2", 0.98402, 0.9847, true }, // Deamidation of N or Q
128  { "[STY]!{STY}", "H1P1O3", 79.96633, 79.9799, true }, // Phosphorylation of S, T, or Y when not N terminal to S, T, or Y
129  { "(", "C2H2O1", 42.010565, 42.0367, true }, // N-terminal acetylation
130  { "[ED)]", "C2H5N1", 43.042199, 43.0678, true }, // Carboxyl modification with ethanolamine
131 };
132 
134 {
135  const char* sequence;
136  const char* mods; // index pairs
138  ModificationParsing mp;
139  ModificationDelimiter md;
140  double monoMass;
141  double avgMass;
142  int exception; // if non-zero, test should cause this exception
143 };
144 
146 {
147  // M+16
148  { "MEERKAT",
149  "0 0",
150  false,
153  879.41205, 879.97844,
154  0
155  },
156 
157  // M+16
158  { "M[O1]EERKAT",
159  "0 0",
160  true,
163  879.41205, 879.97844,
164  0
165  },
166 
167  // M+16
168  { "M[O1]EERKAT",
169  "0 0",
170  true,
171  ModificationParsing_Auto,
173  879.41205, 879.97844,
174  0
175  },
176 
177  // M+16
178  { "M(15.9949,15.9994)EERKAT",
179  "0 0",
180  false,
183  879.41205, 879.97844,
184  1 //"[Peptide::Impl::parse()] Expected a chemical formula for all modifications in sequence "
185  },
186 
187  // M+16
188  { "M[15.9949,15.9994]EERKAT",
189  "0 0",
190  false,
193  879.41205, 879.97844,
194  0
195  },
196 
197  // M+16
198  { "M(15.9949,15.9994)EERKAT",
199  "0 0",
200  false,
201  ModificationParsing_Auto,
203  879.41205, 879.97844,
204  0
205  },
206 
207  // M+16
208  { "M[O1)EERKAT",
209  "0 0",
210  true,
213  879.41205, 879.97844,
214  1 //"[Peptide::Impl::parse()] Modification started but not ended in sequence "
215  },
216 
217  // C+57
218  { "THEQICKRWNFMPSVERTHELAYDG",
219  "1 5",
220  false,
223  3103.43929, 3105.4218,
224  0
225  },
226 
227  // C+57, M+16
228  { "THEQICKRWNFMPSVERTHELAYDG",
229  "0 11 1 5",
230  false,
233  3119.43419, 3121.4212,
234  0
235  },
236 
237  // C+57, M+16
238  { "THEQIC{C2H3N1O1}KRWNFM{O1}PSVERTHELAYDG",
239  "0 11 1 5",
240  true,
242  ModificationDelimiter_Braces,
243  3119.43419, 3121.4212,
244  0
245  },
246 
247  // C+57, M+16
248  { "THEQIC{C2H3N1O1}KRWNFM{15.9949,15.9994}PSVERTHELAYDG",
249  "0 11 1 5",
250  false,
251  ModificationParsing_Auto,
252  ModificationDelimiter_Braces,
253  3119.43419, 3121.4212,
254  0
255  },
256 
257  // C+57, Q-17
258  { "QICKRWNFMPSVERTHELAYDG",
259  "2 0 1 2",
260  false,
263  2719.26356, 2721.0341,
264  0
265  },
266 
267  // no mods
268  { "ELVISLIVES",
269  0,
270  false,
273  1100.63293, 1101.29052,
274  0
275  },
276 
277  // E-17
278  { "ELVISLIVES",
279  "3 0",
280  false,
283  1083.60638, 1084.26,
284  0
285  },
286 
287  // E-17
288  { "E(N-1H-3)LVISLIVES",
289  "3 0",
290  true,
293  1083.60638, 1084.26,
294  0
295  },
296 
297  // E-17
298  { "E(N-1H-3)LVISLIVES",
299  "3 0",
300  true,
303  1083.60638, 1084.26,
304  1 //"[Peptide::Impl::parse()] Expected one or two comma-separated numbers in sequence "
305  },
306 
307  // E-17
308  { "E(N-1H-3)LVISLIVES",
309  "3 0",
310  true,
311  ModificationParsing_Auto,
313  1083.60638, 1084.26,
314  0
315  },
316 
317  // E-17
318  { "E(-17.02655,-17.0306)LVISLIVES",
319  "3 0",
320  false,
323  1083.60638, 1084.26,
324  0
325  },
326 
327  // E-17
328  { "E(-17.02655,-17.0306)LVISLIVES",
329  "3 0",
330  false,
331  ModificationParsing_Auto,
333  1083.60638, 1084.26,
334  0
335  },
336 
337  // no mods
338  { "PINGPNG",
339  0,
340  false,
343  667.32898, 667.7112,
344  0
345  },
346 
347  // N-17
348  { "PINGPNG",
349  "4 2",
350  false,
353  650.30243, 650.6807,
354  0
355  },
356 
357  // no mods
358  { "MISSISSIPPI",
359  0,
360  false,
363  1143.62099, 1144.3815,
364  0
365  },
366 
367  // no mods
368  { "MISSISSIPPI",
369  0,
370  false,
371  ModificationParsing_Auto,
373  1143.62099, 1144.3815,
374  0
375  },
376 
377  // S+80, S+80
378  { "MISSISSIPPI",
379  "5 3 5 5",
380  true,
383  1303.55365, 1304.3413,
384  0
385  },
386 
387  // N-terminal +42
388  { "PINGPNG",
389  "6 n",
390  true,
393  709.339545, 709.7479,
394  0
395  },
396 
397  // C-terminal +43
398  { "PINGPNG",
399  "7 c",
400  true,
403  710.371179, 710.779,
404  0
405  }
406 };
407 
410 
412 {
413  for (size_t i=0; i < testModifiedPeptidesSize; ++i)
414  {
416  try
417  {
419  double monoDeltaMass = 0;
420  double avgDeltaMass = 0;
421  double BIG_EPSILON = 0.001;
422 
423  if (p.exception != 0)
424  {
425  //unit_assert_throws_what(Peptide(p.sequence, p.mp, p.md), exception, string(p.exception)+p.sequence);
426  continue;
427  }
428 
429  if (p.mp == ModificationParsing_Off || p.mods == NULL)
430  {
431  peptide = Peptide(p.sequence);
432 
433  if (p.mods != NULL)
434  {
436  vector<string> tokens;
437  boost::split(tokens, p.mods, boost::is_space());
438  for (size_t i=0; i < tokens.size(); i+=2)
439  {
440  TestModification& mod = testModifications[lexical_cast<size_t>(tokens[i])];
441 
442  int modOffset;
443  if (tokens[i+1] == "n")
444  modOffset = ModificationMap::NTerminus();
445  else if (tokens[i+1] == "c")
446  modOffset = ModificationMap::CTerminus();
447  else
448  modOffset = lexical_cast<int>(tokens[i+1]);
449 
450  if (p.modsHaveFormulas)
451  modMap[modOffset].push_back(Modification(mod.formula));
452  else
453  modMap[modOffset].push_back(Modification(mod.deltaMonoMass, mod.deltaAvgMass));
454  monoDeltaMass += mod.deltaMonoMass;
455  avgDeltaMass += mod.deltaAvgMass;
456  }
457  }
458  }
459  else
460  {
461  peptide = Peptide(p.sequence, p.mp, p.md);
462 
464  vector<string> tokens;
465  boost::split(tokens, p.mods, boost::is_space());
466  for (size_t i=0; i < tokens.size(); i+=2)
467  {
468  TestModification& mod = testModifications[lexical_cast<size_t>(tokens[i])];
469 
470  int modOffset;
471  if (tokens[i+1] == "n")
472  modOffset = ModificationMap::NTerminus();
473  else if (tokens[i+1] == "c")
474  modOffset = ModificationMap::CTerminus();
475  else
476  modOffset = lexical_cast<int>(tokens[i+1]);
477 
478  ModificationMap::const_iterator itr = modMap.find(modOffset);
479  unit_assert(itr != modMap.end());
480  const ModificationList& modList = itr->second;
481  if (p.modsHaveFormulas)
482  {
483  unit_assert(modList[0].hasFormula());
484  unit_assert(modList[0].formula() == mod.formula);
485  }
486  unit_assert_equal(modList[0].monoisotopicDeltaMass(), mod.deltaMonoMass, BIG_EPSILON);
487  unit_assert_equal(modList[0].averageDeltaMass(), mod.deltaAvgMass, BIG_EPSILON);
488  monoDeltaMass += mod.deltaMonoMass;
489  avgDeltaMass += mod.deltaAvgMass;
490  }
491  }
492 
493  if (os_) *os_ << peptide.sequence() << ": " << peptide.monoisotopicMass() << " " << peptide.molecularWeight() << endl;
494 
495  if (p.modsHaveFormulas)
496  {
497  unit_assert_equal(peptide.formula(true).monoisotopicMass(), p.monoMass, BIG_EPSILON);
498  unit_assert_equal(peptide.formula(true).molecularWeight(), p.avgMass, BIG_EPSILON);
499  } else if (p.mods != NULL)
500  unit_assert_throws_what(peptide.formula(true), runtime_error,
501  "[Peptide::formula()] peptide formula cannot be generated when any modifications have no formula info");
502 
503  unit_assert_equal(peptide.formula(false).monoisotopicMass(), p.monoMass-monoDeltaMass, BIG_EPSILON);
504  unit_assert_equal(peptide.formula(false).molecularWeight(), p.avgMass-avgDeltaMass, BIG_EPSILON);
505  unit_assert_equal(peptide.monoisotopicMass(0, true), p.monoMass, BIG_EPSILON);
506  unit_assert_equal(peptide.molecularWeight(0, true), p.avgMass, BIG_EPSILON);
507  unit_assert_equal(peptide.monoisotopicMass(0, false), p.monoMass-monoDeltaMass, BIG_EPSILON);
508  unit_assert_equal(peptide.molecularWeight(0, false), p.avgMass-avgDeltaMass, BIG_EPSILON);
509  }
510  catch (exception& e)
511  {
512  cout << "Unit test " << lexical_cast<string>(i+1) << " on modified peptide \"" << p.sequence << "\" failed:\n" << e.what() << endl;
513  }
514  }
515 }
516 
517 
519 {
520  const char* lhsPeptide;
521  const char* rhsPeptide;
522  int compare; // 0:lhs==rhs -1:lhs<rhs 1:lhs>rhs
523 };
524 
526 {
527  {"PEPTIDE", "PEPTIDE", 0},
528  {"PEPTIDE", "PEPTIDEK", -1},
529  {"PEPTIDEK", "PEPTIDE", 1},
530 
531  {"(42)PEPTIDE", "(42)PEPTIDE", 0},
532  {"PEP(42)TIDE", "PEP(42)TIDE", 0},
533  {"PEPTIDE(42)", "PEPTIDE(42)", 0},
534  {"PEPTIDE", "(42)PEPTIDE", -1},
535  {"(42)PEPTIDE", "PEPTIDE", 1},
536  {"PEPTIDE(41)", "PEPTIDE(42)", -1},
537  {"PEPTIDE(42)", "PEPTIDE(41)", 1},
538  {"(42)PEPTIDE(42)", "(42)PEPTIDE(42)", 0},
539  {"(42)PEPTIDE(41)", "(42)PEPTIDE(42)", -1},
540  {"(42)PEPTIDE(42)", "(42)PEPTIDE(41)", 1},
541  {"(42)PEPTIDE", "(42)PEPTIDE(42)", -1},
542  {"(42)PEPTIDE(42)", "PEPTIDE(42)", 1},
543  {"P(42)EPTIDE(42)", "PEPTIDE(42)", 1},
544  {"(42)PEPTIDE", "P(42)EPTIDE", -1},
545  {"P(42)EPTIDE", "(42)PEPTIDE", 1},
546 };
547 
548 const size_t testOperatorsSize = sizeof(testOperators)/sizeof(TestOperator);
549 
551 {
552  for (size_t i=0; i < testOperatorsSize; ++i)
553  {
554  const TestOperator& p = testOperators[i];
555  try
556  {
557  Peptide lhs(p.lhsPeptide);
558  Peptide rhs(p.rhsPeptide);
559 
560  switch(p.compare)
561  {
562  case 0:
563  unit_assert(lhs == rhs);
564  unit_assert(!(lhs < rhs));
565  unit_assert(lhs.modifications() == rhs.modifications());
566  unit_assert(!(lhs.modifications() < rhs.modifications()));
567  break;
568 
569  case -1:
570  unit_assert(lhs < rhs);
571  unit_assert(!(lhs == rhs));
572  if (!lhs.modifications().empty() || !rhs.modifications().empty())
573  {
574  unit_assert(lhs.modifications() < rhs.modifications());
575  unit_assert(!(lhs.modifications() == rhs.modifications()));
576  }
577  break;
578 
579  case 1:
580  unit_assert(!(lhs == rhs));
581  unit_assert(!(lhs < rhs));
582  if (!lhs.modifications().empty() || !rhs.modifications().empty())
583  {
584  unit_assert(!(lhs.modifications() == rhs.modifications()));
585  unit_assert(!(lhs.modifications() < rhs.modifications()));
586  }
587  break;
588  }
589  }
590  catch (exception& e)
591  {
592  cout << "Unit test " << lexical_cast<string>(i+1) << " comparing \"" << p.lhsPeptide << "\" and \"" << p.rhsPeptide << "\" failed:\n" << e.what() << endl;
593  }
594  }
595 }
596 
597 
599 {
600  const char* sequence;
601  double a1, aN, a1Plus2, aNPlus2;
602  double b1, bN, b1Plus2, bNPlus2;
603  double c1, cN, c1Plus2, cNPlus2;
604  double x1, xN, x1Plus2, xNPlus2;
605  double y1, yN, y1Plus2, yNPlus2;
606  double z1, zN, z1Plus2, zNPlus2;
607 };
608 
609 // test masses calculated at:
610 // $Id$tml
612 {
613  { "MEERKAT",
614  104.05344, 818.41949, 52.53066, 409.71368,
615  132.04836, 846.41441, 66.52811, 423.71114,
616  149.07490, 762.39328, 75.04139, 381.70057,
617  146.04538, 759.36375, 73.52662, 380.18581,
618  120.06611, 864.42497, 60.53699, 432.71642,
619  103.03956, 847.39842, 52.02372, 424.20315
620  },
621 
622  { "THEQICKRWNFMPSVERTHELAYDG",
623  74.06063, 3001.42018, 37.53425, 1501.21402,
624  102.05555, 3029.41509, 51.53171, 1515.21148,
625  119.08210, 2989.42018, 60.04498, 1495.21402,
626  102.01916, 2972.35724, 51.51352, 1486.68256,
627  76.03990, 3047.42566, 38.52388, 1524.21676,
628  59.01335, 3030.39911, 30.01061, 1515.70349
629  },
630 };
631 
633 
634 void writeFragmentation(const Peptide& p, const Fragmentation& f, ostream& os)
635 {
636  size_t length = p.sequence().length();
637 
638  os << "a:";
639  for (size_t i=1; i <= length; ++i)
640  os << " " << f.a(i);
641  os << endl;
642 
643  os << "b:";
644  for (size_t i=1; i <= length; ++i)
645  os << " " << f.b(i);
646  os << endl;
647 
648  os << "c:";
649  for (size_t i=1; i < length; ++i)
650  os << " " << f.c(i);
651  os << endl;
652 
653  os << "x:";
654  for (size_t i=1; i < length; ++i)
655  os << " " << f.x(i);
656  os << endl;
657 
658  os << "y:";
659  for (size_t i=1; i <= length; ++i)
660  os << " " << f.y(i);
661  os << endl;
662 
663  os << "z:";
664  for (size_t i=1; i <= length; ++i)
665  os << " " << f.z(i);
666  os << endl;
667 }
668 
670 {
671  const double EPSILON = 0.005;
672 
673  for (size_t i=0; i < testFragmentationsSize; ++i)
674  {
675  const TestFragmentation& tf = testFragmentations[i];
676  size_t length = string(tf.sequence).length();
678  if (os_) *os_ << peptide.sequence() << ": " << peptide.monoisotopicMass() << endl;
679 
681  if (os_) writeFragmentation(peptide, f, *os_);
682 
683  unit_assert_equal(tf.a1 - Proton, f.a(1), EPSILON);
684  unit_assert_equal(tf.b1 - Proton, f.b(1), EPSILON);
685  unit_assert_equal(tf.c1 - Proton, f.c(1), EPSILON);
686  unit_assert_equal(tf.x1 - Proton, f.x(1), EPSILON);
687  unit_assert_equal(tf.y1 - Proton, f.y(1), EPSILON);
688  unit_assert_equal(tf.z1 - Proton, f.z(1), EPSILON);
689 
690  unit_assert_equal(tf.aN - Proton, f.a(length), EPSILON);
691  unit_assert_equal(tf.bN - Proton, f.b(length), EPSILON);
692  unit_assert_equal(tf.cN - Proton, f.c(length-1), EPSILON);
693  unit_assert_equal(tf.xN - Proton, f.x(length-1), EPSILON);
694  unit_assert_equal(tf.yN - Proton, f.y(length), EPSILON);
695  unit_assert_equal(tf.zN - Proton, f.z(length), EPSILON);
696 
697  unit_assert_equal(tf.a1, f.a(1, 1), EPSILON);
698  unit_assert_equal(tf.b1, f.b(1, 1), EPSILON);
699  unit_assert_equal(tf.c1, f.c(1, 1), EPSILON);
700  unit_assert_equal(tf.x1, f.x(1, 1), EPSILON);
701  unit_assert_equal(tf.y1, f.y(1, 1), EPSILON);
702  unit_assert_equal(tf.z1, f.z(1, 1), EPSILON);
703 
704  unit_assert_equal(tf.aN, f.a(length, 1), EPSILON);
705  unit_assert_equal(tf.bN, f.b(length, 1), EPSILON);
706  unit_assert_equal(tf.cN, f.c(length-1, 1), EPSILON);
707  unit_assert_equal(tf.xN, f.x(length-1, 1), EPSILON);
708  unit_assert_equal(tf.yN, f.y(length, 1), EPSILON);
709  unit_assert_equal(tf.zN, f.z(length, 1), EPSILON);
710 
711  unit_assert_equal(tf.a1Plus2, f.a(1, 2), EPSILON);
712  unit_assert_equal(tf.b1Plus2, f.b(1, 2), EPSILON);
713  unit_assert_equal(tf.c1Plus2, f.c(1, 2), EPSILON);
714  unit_assert_equal(tf.x1Plus2, f.x(1, 2), EPSILON);
715  unit_assert_equal(tf.y1Plus2, f.y(1, 2), EPSILON);
716  unit_assert_equal(tf.z1Plus2, f.z(1, 2), EPSILON);
717 
718  unit_assert_equal(tf.aNPlus2, f.a(length, 2), EPSILON);
719  unit_assert_equal(tf.bNPlus2, f.b(length, 2), EPSILON);
720  unit_assert_equal(tf.cNPlus2, f.c(length-1, 2), EPSILON);
721  unit_assert_equal(tf.xNPlus2, f.x(length-1, 2), EPSILON);
722  unit_assert_equal(tf.yNPlus2, f.y(length, 2), EPSILON);
723  unit_assert_equal(tf.zNPlus2, f.z(length, 2), EPSILON);
724  }
725 
726  // test fragmentation with mods
727  {
728  Peptide p("THEQICKRWNFMPSVERTHELAYDG");
729  Modification C57("C2H3N1O1"), M16("O1");
730  (p.modifications())[5].push_back(C57);
731  (p.modifications())[11].push_back(M16);
732  Fragmentation f = p.fragmentation(true, false);
733  Fragmentation fWithMods = p.fragmentation(true, true);
734  if (os_) writeFragmentation(p, f, *os_);
735  if (os_) writeFragmentation(p, fWithMods, *os_);
736  double EPSILON = 0.00000001;
737  for (size_t i=1; i <= 5; ++i)
738  {
739  unit_assert_equal(f.a(i), fWithMods.a(i), EPSILON);
740  unit_assert_equal(f.b(i), fWithMods.b(i), EPSILON);
741  unit_assert_equal(f.c(i), fWithMods.c(i), EPSILON);
742  }
743 
744  for (size_t i=6; i <= 11; ++i)
745  {
746  double deltaMass = C57.monoisotopicDeltaMass();
747  unit_assert_equal(f.a(i)+deltaMass, fWithMods.a(i), EPSILON);
748  unit_assert_equal(f.b(i)+deltaMass, fWithMods.b(i), EPSILON);
749  unit_assert_equal(f.c(i)+deltaMass, fWithMods.c(i), EPSILON);
750  }
751 
752  for (size_t i=12; i <= p.sequence().length(); ++i)
753  {
754  double deltaMass = C57.monoisotopicDeltaMass() + M16.monoisotopicDeltaMass();
755  unit_assert_equal(f.a(i)+deltaMass, fWithMods.a(i), EPSILON);
756  unit_assert_equal(f.b(i)+deltaMass, fWithMods.b(i), EPSILON);
757  if (i < p.sequence().length())
758  unit_assert_equal(f.c(i)+deltaMass, fWithMods.c(i), EPSILON);
759  }
760 
761  for (size_t i=1; i <= 13; ++i)
762  {
763  unit_assert_equal(f.x(i), fWithMods.x(i), EPSILON);
764  unit_assert_equal(f.y(i), fWithMods.y(i), EPSILON);
765  unit_assert_equal(f.z(i), fWithMods.z(i), EPSILON);
766  }
767 
768  for (size_t i=14; i <= 19; ++i)
769  {
770  double deltaMass = M16.monoisotopicDeltaMass();
771  unit_assert_equal(f.x(i)+deltaMass, fWithMods.x(i), EPSILON);
772  unit_assert_equal(f.y(i)+deltaMass, fWithMods.y(i), EPSILON);
773  unit_assert_equal(f.z(i)+deltaMass, fWithMods.z(i), EPSILON);
774  }
775 
776  for (size_t i=20; i <= p.sequence().length(); ++i)
777  {
778  double deltaMass = C57.monoisotopicDeltaMass() + M16.monoisotopicDeltaMass();
779  if (i < p.sequence().length())
780  unit_assert_equal(f.x(i)+deltaMass, fWithMods.x(i), EPSILON);
781  unit_assert_equal(f.y(i)+deltaMass, fWithMods.y(i), EPSILON);
782  unit_assert_equal(f.z(i)+deltaMass, fWithMods.z(i), EPSILON);
783  }
784  }
785 
786  {
787  Peptide p("QICKRWNFMPSVERTHELAYDG");
788  Modification Q17("N-1H-3"), S80("H1P1O3");
789  (p.modifications())[ModificationMap::NTerminus()].push_back(Q17); // close enough
790  (p.modifications())[10].push_back(S80);
791  Fragmentation f = p.fragmentation(true, false);
792  Fragmentation fWithMods = p.fragmentation(true, true);
793  if (os_) writeFragmentation(p, f, *os_);
794  if (os_) writeFragmentation(p, fWithMods, *os_);
795  double EPSILON = 0.00000001;
796 
797  for (size_t i=0; i <= 10; ++i)
798  {
799  double deltaMass = Q17.monoisotopicDeltaMass();
800  unit_assert_equal(f.a(i)+deltaMass, fWithMods.a(i), EPSILON);
801  unit_assert_equal(f.b(i)+deltaMass, fWithMods.b(i), EPSILON);
802  unit_assert_equal(f.c(i)+deltaMass, fWithMods.c(i), EPSILON);
803  }
804 
805  for (size_t i=11; i <= p.sequence().length(); ++i)
806  {
807  double deltaMass = Q17.monoisotopicDeltaMass() + S80.monoisotopicDeltaMass();
808  unit_assert_equal(f.a(i)+deltaMass, fWithMods.a(i), EPSILON);
809  unit_assert_equal(f.b(i)+deltaMass, fWithMods.b(i), EPSILON);
810  if (i < p.sequence().length())
811  unit_assert_equal(f.c(i)+deltaMass, fWithMods.c(i), EPSILON);
812  }
813 
814  for (size_t i=1; i <= 11; ++i)
815  {
816  unit_assert_equal(f.x(i), fWithMods.x(i), EPSILON);
817  unit_assert_equal(f.y(i), fWithMods.y(i), EPSILON);
818  unit_assert_equal(f.z(i), fWithMods.z(i), EPSILON);
819  }
820 
821  for (size_t i=12; i <= p.sequence().length(); ++i)
822  {
823  double deltaMass = S80.monoisotopicDeltaMass();
824  if (i < p.sequence().length())
825  unit_assert_equal(f.x(i)+deltaMass, fWithMods.x(i), EPSILON);
826  unit_assert_equal(f.y(i)+deltaMass, fWithMods.y(i), EPSILON);
827  unit_assert_equal(f.z(i)+deltaMass, fWithMods.z(i), EPSILON);
828  }
829  }
830 }
831 
832 
833 void testThreadSafetyWorker(boost::barrier* testBarrier)
834 {
835  testBarrier->wait(); // wait until all threads have started
836 
837  try
838  {
839  peptideTest();
841  operatorTest();
842  fragmentTest();
843  }
844  catch (exception& e)
845  {
846  cerr << "Exception in worker thread: " << e.what() << endl;
847  }
848  catch (...)
849  {
850  cerr << "Unhandled exception in worker thread." << endl;
851  }
852 }
853 
854 void testThreadSafety(const int& testThreadCount)
855 {
856  boost::barrier testBarrier(testThreadCount);
857  boost::thread_group testThreadGroup;
858  for (int i=0; i < testThreadCount; ++i)
859  testThreadGroup.add_thread(new boost::thread(&testThreadSafetyWorker, &testBarrier));
860  testThreadGroup.join_all();
861 }
862 
863 
864 int main(int argc, char* argv[])
865 {
866  TEST_PROLOG(argc, argv)
867 
868  try
869  {
870  if (argc>1 && !strcmp(argv[1],"-v")) os_ = &cout;
871  if (os_) *os_ << "PeptideTest\n";
872  //test();
873  //isotopeTest();
874 
875  //testThreadSafety(1); // does not test thread-safety of singleton initialization
876  testThreadSafety(2);
877  testThreadSafety(4);
878  testThreadSafety(8);
879  testThreadSafety(16);
880  }
881  catch (exception& e)
882  {
883  TEST_FAILED(e.what())
884  }
885  catch (...)
886  {
887  TEST_FAILED("Caught unknown exception.")
888  }
889 
891 }
892 
TestOperator::rhsPeptide
const char * rhsPeptide
Definition: PeptideTest.cpp:521
testModifications
TestModification testModifications[]
Definition: PeptideTest.cpp:120
pwiz::proteome::ModificationMap
maps peptide/protein sequence indexes (0-based) to a modification list
Definition: Modification.hpp:106
testModifiedPeptidesSize
const size_t testModifiedPeptidesSize
Definition: PeptideTest.cpp:409
TestFragmentation::cN
double cN
Definition: PeptideTest.cpp:603
pwiz::proteome::Peptide::formula
chemistry::Formula formula(bool modified=false) const
if modified = false: returns the composition formula of sequence()+water if modified = true: returns ...
testModifiedPeptides
TestModifiedPeptide testModifiedPeptides[]
Definition: PeptideTest.cpp:145
pwiz::proteome::Fragmentation::c
double c(size_t length, size_t charge=0) const
returns the c ion of length <length> example: c(1) returns the c1 ion if <charge> = 0: returns neutra...
TestModification::deltaMonoMass
double deltaMonoMass
Definition: PeptideTest.cpp:115
operatorTest
void operatorTest()
Definition: PeptideTest.cpp:550
unit_assert_throws_what
#define unit_assert_throws_what(x, exception, whatStr)
Definition: unit.hpp:119
unit_assert_equal
#define unit_assert_equal(x, y, epsilon)
Definition: unit.hpp:99
TestFragmentation::y1
double y1
Definition: PeptideTest.cpp:605
TestFragmentation::c1Plus2
double c1Plus2
Definition: PeptideTest.cpp:603
TestFragmentation::xNPlus2
double xNPlus2
Definition: PeptideTest.cpp:604
TestPeptide::monoMassPlus2
double monoMassPlus2
Definition: PeptideTest.cpp:64
ModificationDelimiter_Parentheses
ModificationDelimiter_Parentheses
Definition: Peptide.hpp:51
TestFragmentation::c1
double c1
Definition: PeptideTest.cpp:603
testPeptides
TestPeptide testPeptides[]
Definition: PeptideTest.cpp:68
pwiz::proteome::Modification
represents a post-translational modification (PTM) modification formula or masses must be provided at...
Definition: Modification.hpp:42
pwiz::proteome::Fragmentation::a
double a(size_t length, size_t charge=0) const
returns the a ion of length <length>; example: a(1) returns the a1 ion if <charge> = 0: returns neutr...
TestModifiedPeptide::mods
const char * mods
Definition: PeptideTest.cpp:136
pwiz::proteome
Definition: AminoAcid.hpp:35
pwiz::chemistry::Formula::molecularWeight
double molecularWeight() const
TestFragmentation::bNPlus2
double bNPlus2
Definition: PeptideTest.cpp:602
testThreadSafety
void testThreadSafety(const int &testThreadCount)
Definition: PeptideTest.cpp:854
TestPeptide
Definition: PeptideTest.cpp:62
pwiz::proteome::Peptide::molecularWeight
double molecularWeight(int charge=0, bool modified=true) const
if charge = 0: returns neutral mass if charge > 0: returns charged m/z if modified = false: returns t...
pwiz::proteome::Peptide
represents a peptide or polypeptide (a sequence of amino acids)
Definition: Peptide.hpp:62
TestFragmentation::bN
double bN
Definition: PeptideTest.cpp:602
TestFragmentation::sequence
const char * sequence
Definition: PeptideTest.cpp:600
writeFragmentation
void writeFragmentation(const Peptide &p, const Fragmentation &f, ostream &os)
Definition: PeptideTest.cpp:634
TestFragmentation::cNPlus2
double cNPlus2
Definition: PeptideTest.cpp:603
TestOperator::compare
int compare
Definition: PeptideTest.cpp:522
TestPeptide::monoMassPlus1
double monoMassPlus1
Definition: PeptideTest.cpp:64
pwiz::proteome::Peptide::monoisotopicMass
double monoisotopicMass(int charge=0, bool modified=true) const
if charge = 0: returns neutral mass if charge > 0: returns charged m/z if modified = false: returns t...
TestFragmentation::zN
double zN
Definition: PeptideTest.cpp:606
sequences
const char * sequences[]
Definition: PeptideTest.cpp:49
ModificationDelimiter_Brackets
ModificationDelimiter_Brackets
'(' and ')'
Definition: Peptide.hpp:52
TestModification::deltaAvgMass
double deltaAvgMass
Definition: PeptideTest.cpp:116
pwiz::identdata::peptide
PWIZ_API_DECL proteome::Peptide peptide(const Peptide &peptide)
creates a proteome::Peptide from an identdata::Peptide
TestFragmentation::z1
double z1
Definition: PeptideTest.cpp:606
TestModifiedPeptide::avgMass
double avgMass
Definition: PeptideTest.cpp:141
pwiz::util
Definition: almost_equal.hpp:33
pwiz::chemistry::Formula::monoisotopicMass
double monoisotopicMass() const
os_
ostream * os_
Definition: PeptideTest.cpp:36
modificationTest
void modificationTest()
Definition: PeptideTest.cpp:411
TestModifiedPeptide::monoMass
double monoMass
Definition: PeptideTest.cpp:140
TEST_EPILOG
#define TEST_EPILOG
Definition: unit.hpp:183
pwiz::proteome::ModificationMap::end
virtual iterator end()
Returns an iterator pointing to the last element stored in the map; in other words,...
TestModification::isDynamic
bool isDynamic
Definition: PeptideTest.cpp:117
TestPeptide::avgMassPlus1
double avgMassPlus1
Definition: PeptideTest.cpp:65
TestFragmentation::xN
double xN
Definition: PeptideTest.cpp:604
pwiz::proteome::Fragmentation::y
double y(size_t length, size_t charge=0) const
returns the y ion of length <length> example: y(1) returns the y1 ion if <charge> = 0: returns neutra...
TestModifiedPeptide::sequence
const char * sequence
Definition: PeptideTest.cpp:135
TestModifiedPeptide::md
ModificationDelimiter md
Definition: PeptideTest.cpp:139
TestFragmentation::a1Plus2
double a1Plus2
Definition: PeptideTest.cpp:601
TestPeptide::avgMassPlus2
double avgMassPlus2
Definition: PeptideTest.cpp:65
testOperatorsSize
const size_t testOperatorsSize
Definition: PeptideTest.cpp:548
Std.hpp
peptideTest
void peptideTest()
Definition: PeptideTest.cpp:79
TestFragmentation::b1Plus2
double b1Plus2
Definition: PeptideTest.cpp:602
TestOperator
Definition: PeptideTest.cpp:519
TestFragmentation::x1
double x1
Definition: PeptideTest.cpp:604
testFragmentationsSize
const size_t testFragmentationsSize
Definition: PeptideTest.cpp:632
pwiz::proteome::Fragmentation::x
double x(size_t length, size_t charge=0) const
returns the x ion of length <length> example: x(1) returns the x1 ion if <charge> = 0: returns neutra...
TestFragmentation::aNPlus2
double aNPlus2
Definition: PeptideTest.cpp:601
testThreadSafetyWorker
void testThreadSafetyWorker(boost::barrier *testBarrier)
Definition: PeptideTest.cpp:833
ModificationParsing_ByMass
ModificationParsing_ByMass
oxidized P in peptide: PEP(O)TIDE
Definition: Peptide.hpp:44
TestModifiedPeptide::exception
int exception
Definition: PeptideTest.cpp:142
pwiz::chemistry
Definition: Chemistry.hpp:37
TestModifiedPeptide::mp
ModificationParsing mp
Definition: PeptideTest.cpp:138
pwiz::proteome::Modification::monoisotopicDeltaMass
double monoisotopicDeltaMass() const
TestFragmentation::b1
double b1
Definition: PeptideTest.cpp:602
TestModification::formula
const char * formula
Definition: PeptideTest.cpp:114
pwiz::proteome::Peptide::sequence
const std::string & sequence() const
returns the sequence of amino acids making up the peptide
testPeptidesSize
const size_t testPeptidesSize
Definition: PeptideTest.cpp:77
TEST_FAILED
#define TEST_FAILED(x)
Definition: unit.hpp:177
TEST_PROLOG
#define TEST_PROLOG(argc, argv)
Definition: unit.hpp:175
TestModifiedPeptide
Definition: PeptideTest.cpp:134
testModificationsSize
const size_t testModificationsSize
Definition: PeptideTest.cpp:408
TestModification::motif
const char * motif
Definition: PeptideTest.cpp:113
TestFragmentation::zNPlus2
double zNPlus2
Definition: PeptideTest.cpp:606
pwiz::proteome::ModificationMap::find
virtual iterator find(const key_type &x)
Searches the map for a pair with the key value x and returns an iterator to that pair if it is found....
TestFragmentation::z1Plus2
double z1Plus2
Definition: PeptideTest.cpp:606
TestPeptide::avgMassNeutral
double avgMassNeutral
Definition: PeptideTest.cpp:65
TestFragmentation::x1Plus2
double x1Plus2
Definition: PeptideTest.cpp:604
TestPeptide::monoMassNeutral
double monoMassNeutral
Definition: PeptideTest.cpp:64
TestFragmentation::yN
double yN
Definition: PeptideTest.cpp:605
ModificationParsing_Off
ModificationParsing_Off
Definition: Peptide.hpp:42
main
int main(int argc, char *argv[])
Definition: PeptideTest.cpp:864
pwiz::util::virtual_map::empty
virtual bool empty() const
Returns true if the map is empty, false otherwise.
Definition: virtual_map.hpp:153
pwiz::proteome::Fragmentation::z
double z(size_t length, size_t charge=0) const
returns the z ion of length <length> example: z(1) returns the z1 ion if <charge> = 0: returns neutra...
TestFragmentation::yNPlus2
double yNPlus2
Definition: PeptideTest.cpp:605
TestPeptide::sequence
const char * sequence
Definition: PeptideTest.cpp:63
ModificationParsing_ByFormula
ModificationParsing_ByFormula
any non-AA characters will cause an exception
Definition: Peptide.hpp:43
test
void test()
Definition: PeptideTest.cpp:39
pwiz::proteome::Peptide::modifications
ModificationMap & modifications()
the map of sequence offsets (0-based) to modifications; modifications can be added or removed from th...
TestFragmentation::a1
double a1
Definition: PeptideTest.cpp:601
TestFragmentation::aN
double aN
Definition: PeptideTest.cpp:601
unit.hpp
unit_assert
#define unit_assert(x)
Definition: unit.hpp:85
pwiz::proteome::ModificationList
represents a list of modifications on a single amino acid
Definition: Modification.hpp:80
TestOperator::lhsPeptide
const char * lhsPeptide
Definition: PeptideTest.cpp:520
testOperators
const TestOperator testOperators[]
Definition: PeptideTest.cpp:525
pwiz::proteome::Fragmentation
provides fragment ion masses for a peptide
Definition: Peptide.hpp:121
TestFragmentation
Definition: PeptideTest.cpp:599
TestModifiedPeptide::modsHaveFormulas
bool modsHaveFormulas
Definition: PeptideTest.cpp:137
TestModification
Definition: PeptideTest.cpp:112
testFragmentations
const TestFragmentation testFragmentations[]
Definition: PeptideTest.cpp:611
pwiz::proteome::Fragmentation::b
double b(size_t length, size_t charge=0) const
returns the b ion of length <length> example: b(1) returns the b1 ion if <charge> = 0: returns neutra...
pwiz::chemistry::Proton
const double Proton
the mass of a proton in unified atomic mass units
Definition: Chemistry.hpp:41
fragmentTest
void fragmentTest()
Definition: PeptideTest.cpp:669
Peptide.hpp
pwiz::proteome::Peptide::fragmentation
Fragmentation fragmentation(bool monoisotopic=true, bool modified=true) const
returns a fragmentation model for the peptide; fragment masses can calculated as mono/avg and as modi...
TestFragmentation::y1Plus2
double y1Plus2
Definition: PeptideTest.cpp:605