ProteoWizard
DigestionTest.cpp
Go to the documentation of this file.
1 //
2 // $Id: DigestionTest.cpp 9198 2015-12-04 23:48:50Z chambm $
3 //
4 //
5 // Original author: Matt Chambers <matt.chambers .@. vanderbilt.edu>
6 //
7 // Copyright 2006 Louis Warschaw Prostate Cancer Center
8 // Cedars Sinai Medical Center, Los Angeles, California 90048
9 // Copyright 2008 Vanderbilt University - Nashville, TN 37232
10 //
11 // Licensed under the Apache License, Version 2.0 (the "License");
12 // you may not use this file except in compliance with the License.
13 // You may obtain a copy of the License at
14 //
15 // http://www.apache.org/licenses/LICENSE-2.0
16 //
17 // Unless required by applicable law or agreed to in writing, software
18 // distributed under the License is distributed on an "AS IS" BASIS,
19 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
20 // See the License for the specific language governing permissions and
21 // limitations under the License.
22 //
23 
24 
26 #include "Peptide.hpp"
27 #include "Digestion.hpp"
29 #include "boost/thread/thread.hpp"
30 #include "boost/thread/barrier.hpp"
31 #include "boost/exception/all.hpp"
32 #include "boost/foreach_field.hpp"
33 
34 
35 using namespace pwiz::cv;
36 using namespace pwiz::util;
37 using namespace pwiz::proteome;
38 
39 
40 ostream* os_ = 0;
41 
42 
44 {
45  const set<CVID>& cleavageAgents = Digestion::getCleavageAgents();
46  const vector<string>& cleavageAgentNames = Digestion::getCleavageAgentNames();
47 
48  if (os_)
49  {
50  *os_ << "Cleavage agents:" << endl;
51  BOOST_FOREACH(CVID agentCvid, cleavageAgents)
52  {
53  *os_ << cvTermInfo(agentCvid).name << " ("
54  << Digestion::getCleavageAgentRegex(agentCvid)
55  << ")" << endl;
56  }
57 
58  *os_ << "\nCleavage agent names" << endl;
59  BOOST_FOREACH(string agentName, cleavageAgentNames)
60  {
61  *os_ << agentName << endl;
62  }
63  }
64 
65  unit_assert(cleavageAgents.size() >= 14);
66  unit_assert_operator_equal(MS_Trypsin, *cleavageAgents.begin());
67  unit_assert(!cleavageAgents.count(MS_NoEnzyme_OBSOLETE));
68  unit_assert(cleavageAgents.count(MS_no_cleavage));
69  unit_assert(cleavageAgents.count(MS_unspecific_cleavage));
70 
71  unit_assert_operator_equal(MS_Trypsin, Digestion::getCleavageAgentByName("TRYPSIN"));
72  unit_assert_operator_equal(MS_Trypsin, Digestion::getCleavageAgentByName("trypsin"));
73  unit_assert_operator_equal(MS_Trypsin_P, Digestion::getCleavageAgentByName("TRYPSIN/P"));
74  unit_assert_operator_equal(MS_Trypsin_P, Digestion::getCleavageAgentByName("trypsin/p"));
75  unit_assert_operator_equal(MS_glutamyl_endopeptidase, Digestion::getCleavageAgentByName("glutamyl endopeptidase"));
76  unit_assert_operator_equal(MS_Glu_C, Digestion::getCleavageAgentByName("Glu-C")); // test exact synonyms
77  unit_assert_operator_equal(CVID_Unknown, Digestion::getCleavageAgentByName("ion trap"));
78  unit_assert_operator_equal(CVID_Unknown, Digestion::getCleavageAgentByName("!@#$%^&*"));
79 
80  unit_assert_operator_equal(MS_Trypsin, Digestion::getCleavageAgentByRegex("(?<=[KR])(?!P)"));
81  unit_assert_operator_equal(MS_Trypsin_P, Digestion::getCleavageAgentByRegex("(?<=[KR])"));
82  unit_assert_operator_equal(MS_Lys_C_P, Digestion::getCleavageAgentByRegex("(?<=K)"));
83  unit_assert_operator_equal(CVID_Unknown, Digestion::getCleavageAgentByRegex("!@#$%^&*"));
84 
85  unit_assert_operator_equal(MS_Trypsin, Digestion::getCleavageAgentByName(cleavageAgentNames[0]));
86  unit_assert_operator_equal(MS_Arg_C, Digestion::getCleavageAgentByName(cleavageAgentNames[1]));
87  unit_assert_operator_equal(MS_Asp_N, Digestion::getCleavageAgentByName(cleavageAgentNames[2]));
88  unit_assert_operator_equal(MS_Asp_N_ambic, Digestion::getCleavageAgentByName(cleavageAgentNames[3]));
89  unit_assert_operator_equal(MS_Chymotrypsin, Digestion::getCleavageAgentByName(cleavageAgentNames[4]));
90  unit_assert_operator_equal(MS_CNBr, Digestion::getCleavageAgentByName(cleavageAgentNames[5]));
91  unit_assert_operator_equal(MS_Formic_acid, Digestion::getCleavageAgentByName(cleavageAgentNames[6]));
92  unit_assert_operator_equal(MS_Lys_C, Digestion::getCleavageAgentByName(cleavageAgentNames[7]));
93  unit_assert_operator_equal(MS_Lys_C_P, Digestion::getCleavageAgentByName(cleavageAgentNames[8]));
94  unit_assert_operator_equal(MS_PepsinA, Digestion::getCleavageAgentByName(cleavageAgentNames[9]));
95  unit_assert_operator_equal(MS_TrypChymo, Digestion::getCleavageAgentByName(cleavageAgentNames[10]));
96  unit_assert_operator_equal(MS_Trypsin_P, Digestion::getCleavageAgentByName(cleavageAgentNames[11]));
97  unit_assert_operator_equal(MS_V8_DE, Digestion::getCleavageAgentByName(cleavageAgentNames[12]));
98  unit_assert_operator_equal(MS_V8_E, Digestion::getCleavageAgentByName(cleavageAgentNames[13]));
99 
100  unit_assert_operator_equal("(?<=[KR])(?!P)", Digestion::getCleavageAgentRegex(MS_Trypsin));
101  unit_assert_operator_equal("(?<=[EZ])(?!P)", Digestion::getCleavageAgentRegex(MS_V8_E));
102  unit_assert_throws(Digestion::getCleavageAgentRegex(MS_ion_trap), std::invalid_argument);
103 
104  unit_assert_operator_equal("(?=[BD])", Digestion::getCleavageAgentRegex(MS_Asp_N));
105  unit_assert_operator_equal("(?=[BNDD])", Digestion::disambiguateCleavageAgentRegex(Digestion::getCleavageAgentRegex(MS_Asp_N)));
106  unit_assert_operator_equal("(?=[A-Z])", Digestion::disambiguateCleavageAgentRegex("(?=X)"));
107  unit_assert_operator_equal("(?=[A-Z])", Digestion::disambiguateCleavageAgentRegex("(?=[X])"));
108  unit_assert_operator_equal("(?![BND])", Digestion::disambiguateCleavageAgentRegex("(?!B)"));
109  unit_assert_operator_equal("(?<![JIL])(?=[BNDK])", Digestion::disambiguateCleavageAgentRegex("(?<![J])(?=[BK])"));
110 }
111 
112 
114 {
115  bool operator() (const DigestedPeptide& lhs, const DigestedPeptide& rhs) const
116  {
117  return lhs.sequence() < rhs.sequence();
118  }
119 };
120 
122  const string& expectedSequence,
123  size_t expectedOffset,
124  size_t expectedMissedCleavages,
125  size_t expectedSpecificTermini,
126  const string& expectedPrefix,
127  const string& expectedSuffix)
128 {
129  try
130  {
131  unit_assert_operator_equal(expectedSequence, peptide.sequence());
132  unit_assert_operator_equal(expectedOffset, peptide.offset());
133  unit_assert_operator_equal(expectedMissedCleavages, peptide.missedCleavages());
134  unit_assert_operator_equal(expectedSpecificTermini, peptide.specificTermini());
135  unit_assert_operator_equal(expectedPrefix, peptide.NTerminusPrefix());
136  unit_assert_operator_equal(expectedSuffix, peptide.CTerminusSuffix());
137  return true;
138  }
139  catch(exception& e)
140  {
141  cerr << "Testing peptide " << peptide.sequence() << ": " << e.what() << endl;
142  return false;
143  }
144 }
145 
146 void testTrypticBSA(const Digestion& trypticDigestion)
147 {
148  if (os_) *os_ << "Fully-specific BSA digest (offset, missed cleavages, specific termini, length, sequence)" << endl;
149 
150  vector<DigestedPeptide> trypticPeptides(trypticDigestion.begin(), trypticDigestion.end());
151  set<DigestedPeptide, DigestedPeptideLessThan> trypticPeptideSet(trypticPeptides.begin(), trypticPeptides.end());
152 
153  if (os_)
154  {
155  BOOST_FOREACH(const DigestedPeptide& peptide, trypticPeptides)
156  {
157  *os_ << peptide.offset() << "\t" << peptide.missedCleavages() << "\t" <<
158  peptide.specificTermini() << "\t" << peptide.sequence().length() <<
159  "\t" << peptide.sequence() << "\n";
160  }
161  }
162 
163  // test count
164  unit_assert(trypticPeptides.size() > 4);
165 
166  // test order of enumeration and metadata: sequence, Off, NMC, NTT, Pre, Suf
167  unit_assert(testDigestionMetadata(trypticPeptides[0], "MKWVTFISLLLLFSSAYSR", 0, 1, 2, "", "G"));
168  unit_assert(testDigestionMetadata(trypticPeptides[1], "MKWVTFISLLLLFSSAYSRGVFR", 0, 2, 2, "", "R"));
169  unit_assert(testDigestionMetadata(trypticPeptides[2], "MKWVTFISLLLLFSSAYSRGVFRR", 0, 3, 2, "", "D"));
170  unit_assert(testDigestionMetadata(trypticPeptides[3], "KWVTFISLLLLFSSAYSR", 1, 1, 2, "M", "G"));
171 
172  // test for non-tryptic peptides
173  unit_assert(!trypticPeptideSet.count("MKWVTFISLLLL"));
174  unit_assert(!trypticPeptideSet.count("STQTALA"));
175 
176  // test some middle peptides
177  unit_assert(trypticPeptideSet.count("RDTHKSEIAHRFK"));
178  unit_assert(trypticPeptideSet.count("DTHKSEIAHRFK"));
179 
180  // test trypticPeptides at the C terminus
181  unit_assert(trypticPeptideSet.count("EACFAVEGPKLVVSTQTALA"));
182  unit_assert(trypticPeptides.back().sequence() == "LVVSTQTALA");
183 
184  // test maximum missed cleavages
185  unit_assert(!trypticPeptideSet.count("MKWVTFISLLLLFSSAYSRGVFRRDTHK"));
186  unit_assert(!trypticPeptideSet.count("LKPDPNTLCDEFKADEKKFWGKYLYEIARR"));
187 
188  // test minimum peptide length
189  unit_assert(!trypticPeptideSet.count("LR"));
190  unit_assert(!trypticPeptideSet.count("QRLR"));
191  unit_assert(trypticPeptideSet.count("VLASSARQRLR"));
192 
193  // test maximum peptide length
194  unit_assert(!trypticPeptideSet.count("MKWVTFISLLLLFSSAYSRGVFRRDTHKSEIAHRFKDLGEEHFK"));
195 
196  // test methionine clipping at the N-terminus
197  unit_assert(trypticPeptideSet.count("KWVTFISLLLLFSSAYSR"));
198 }
199 
200 void testSemitrypticBSA(const Digestion& semitrypticDigestion)
201 {
202  if (os_) *os_ << "Semi-specific BSA digest (offset, missed cleavages, specific termini, length, sequence)" << endl;
203 
204  set<DigestedPeptide, DigestedPeptideLessThan>::const_iterator peptideItr;
205 
206  vector<DigestedPeptide> semitrypticPeptides(semitrypticDigestion.begin(), semitrypticDigestion.end());
207  set<DigestedPeptide, DigestedPeptideLessThan> semitrypticPeptideSet(semitrypticPeptides.begin(), semitrypticPeptides.end());
208 
209  if (os_)
210  {
211  BOOST_FOREACH(DigestedPeptide peptide, semitrypticPeptides)
212  {
213  *os_ << peptide.offset() << "\t" << peptide.missedCleavages() << "\t" <<
214  peptide.specificTermini() << "\t" << peptide.sequence().length() <<
215  "\t" << peptide.sequence() << "\n";
216  }
217  }
218 
219  // test count
220  unit_assert(semitrypticPeptides.size() > 3);
221 
222  // test order of enumeration and peptides at the N terminus
223  unit_assert_operator_equal("MKWVT", semitrypticPeptides[0].sequence());
224  unit_assert_operator_equal("MKWVTF", semitrypticPeptides[1].sequence());
225  unit_assert_operator_equal("MKWVTFI", semitrypticPeptides[2].sequence());
226 
227  // test order of enumeration and peptides at the C terminus
228  unit_assert_operator_equal("QTALA", semitrypticPeptides.rbegin()->sequence());
229  unit_assert_operator_equal("TQTALA", (semitrypticPeptides.rbegin()+1)->sequence());
230  unit_assert_operator_equal("STQTALA", (semitrypticPeptides.rbegin()+2)->sequence());
231  unit_assert_operator_equal("LVVSTQTALA", (semitrypticPeptides.rbegin()+5)->sequence());
232  unit_assert_operator_equal("LVVSTQTAL", (semitrypticPeptides.rbegin()+6)->sequence());
233  unit_assert_operator_equal("LVVST", (semitrypticPeptides.rbegin()+10)->sequence());
234 
235  // test digestion metadata
236  unit_assert_operator_equal(0, semitrypticPeptides[0].offset());
237  unit_assert_operator_equal(1, semitrypticPeptides[0].missedCleavages());
238  unit_assert_operator_equal(1, semitrypticPeptides[0].specificTermini());
239  unit_assert(semitrypticPeptides[0].NTerminusIsSpecific() &&
240  !semitrypticPeptides[0].CTerminusIsSpecific());
241 
242  peptideItr = semitrypticPeptideSet.find("MKWVTFISLLLLFSSAYSR");
243  unit_assert(peptideItr != semitrypticPeptideSet.end());
244  unit_assert_operator_equal(0, peptideItr->offset());
245  unit_assert_operator_equal(1, peptideItr->missedCleavages());
246  unit_assert_operator_equal(2, peptideItr->specificTermini());
247  unit_assert(peptideItr->NTerminusIsSpecific() &&
248  peptideItr->CTerminusIsSpecific());
249 
250  peptideItr = semitrypticPeptideSet.find("KWVTFISLLLLFSSAYSR");
251  unit_assert(peptideItr != semitrypticPeptideSet.end());
252  unit_assert_operator_equal(1, peptideItr->offset());
253  unit_assert_operator_equal(1, peptideItr->missedCleavages());
254  unit_assert_operator_equal(2, peptideItr->specificTermini());
255  unit_assert(peptideItr->NTerminusIsSpecific() &&
256  peptideItr->CTerminusIsSpecific());
257 
258  peptideItr = semitrypticPeptideSet.find("KWVTFISLLLLFSSAYSRG"); // 2 missed cleavages
259  unit_assert(peptideItr == semitrypticPeptideSet.end());
260 
261  peptideItr = semitrypticPeptideSet.find("WVTFISLLLLFSSAYSR");
262  unit_assert(peptideItr != semitrypticPeptideSet.end());
263  unit_assert_operator_equal(2, peptideItr->offset());
264  unit_assert_operator_equal(0, peptideItr->missedCleavages());
265  unit_assert_operator_equal(2, peptideItr->specificTermini());
266  unit_assert(peptideItr->NTerminusIsSpecific() &&
267  peptideItr->CTerminusIsSpecific());
268 
269  peptideItr = semitrypticPeptideSet.find("WVTFISLLLLFSSAYSRG");
270  unit_assert(peptideItr != semitrypticPeptideSet.end());
271  unit_assert_operator_equal(2, peptideItr->offset());
272  unit_assert_operator_equal(1, peptideItr->missedCleavages());
273  unit_assert_operator_equal(1, peptideItr->specificTermini());
274  unit_assert(peptideItr->NTerminusIsSpecific() &&
275  !peptideItr->CTerminusIsSpecific());
276 
277  peptideItr = semitrypticPeptideSet.find("VTFISLLLLFSSAYSRG"); // non-tryptic
278  unit_assert(peptideItr == semitrypticPeptideSet.end());
279 
280  // test for non-specific peptides
281  unit_assert(semitrypticPeptideSet.count("WVTFISLLLLFSSAYSR")); // tryptic
282  unit_assert(semitrypticPeptideSet.count("VTFISLLLLFSSAYSR")); // semi-tryptic
283  unit_assert(!semitrypticPeptideSet.count("VTFISLLLLFSSAYS")); // non-tryptic
284 
285  // test semi-specific peptides at the C terminus
286  unit_assert(semitrypticPeptideSet.count("FAVEGPKLVVSTQTALA")); // semi-tryptic
287  unit_assert(!semitrypticPeptideSet.count("FAVEGPKLVVSTQTAL")); // non-tryptic
288 }
289 
290 void testNontrypticBSA(const Digestion& nontrypticDigestion)
291 {
292  if (os_) *os_ << "Non-specific BSA digest (offset, missed cleavages, specific termini, length, sequence)" << endl;
293 
294  set<DigestedPeptide, DigestedPeptideLessThan>::const_iterator peptideItr;
295 
296  vector<DigestedPeptide> nontrypticPeptides(nontrypticDigestion.begin(), nontrypticDigestion.end());
297  set<DigestedPeptide, DigestedPeptideLessThan> nontrypticPeptideSet(nontrypticPeptides.begin(), nontrypticPeptides.end());
298 
299  if (os_)
300  {
301  BOOST_FOREACH(DigestedPeptide peptide, nontrypticPeptides)
302  {
303  *os_ << peptide.offset() << "\t" << peptide.missedCleavages() << "\t" <<
304  peptide.specificTermini() << "\t" << peptide.sequence().length() <<
305  "\t" << peptide.sequence() << "\n";
306  }
307  }
308 
309  // test count
310  unit_assert(nontrypticPeptides.size() > 3);
311 
312  // test order of enumeration and peptides at the N terminus
313  unit_assert_operator_equal("MKWVT", nontrypticPeptides[0].sequence());
314  unit_assert_operator_equal("MKWVTF", nontrypticPeptides[1].sequence());
315  unit_assert_operator_equal("MKWVTFI", nontrypticPeptides[2].sequence());
316 
317  // test digestion metadata
318  unit_assert_operator_equal(0, nontrypticPeptides[0].offset());
319  unit_assert_operator_equal(1, nontrypticPeptides[0].missedCleavages());
320  unit_assert_operator_equal(1, nontrypticPeptides[0].specificTermini());
321  unit_assert(nontrypticPeptides[0].NTerminusIsSpecific() &&
322  !nontrypticPeptides[0].CTerminusIsSpecific());
323 
324  peptideItr = nontrypticPeptideSet.find("MKWVTFISLLLLFSSAYSR");
325  unit_assert(peptideItr != nontrypticPeptideSet.end());
326  unit_assert_operator_equal(0, peptideItr->offset());
327  unit_assert_operator_equal(1, peptideItr->missedCleavages());
328  unit_assert_operator_equal(2, peptideItr->specificTermini());
329  unit_assert(peptideItr->NTerminusIsSpecific() &&
330  peptideItr->CTerminusIsSpecific());
331 
332  peptideItr = nontrypticPeptideSet.find("KWVTFISLLLLFSSAYSR");
333  unit_assert(peptideItr != nontrypticPeptideSet.end());
334  unit_assert_operator_equal(1, peptideItr->offset());
335  unit_assert_operator_equal(1, peptideItr->missedCleavages());
336  unit_assert_operator_equal(2, peptideItr->specificTermini());
337  unit_assert(peptideItr->NTerminusIsSpecific() &&
338  peptideItr->CTerminusIsSpecific());
339 
340  peptideItr = nontrypticPeptideSet.find("KWVTFISLLLLFSSAYSRG"); // 2 missed cleavages
341  unit_assert(peptideItr == nontrypticPeptideSet.end());
342 
343  peptideItr = nontrypticPeptideSet.find("WVTFISLLLLFSSAYSR");
344  unit_assert(peptideItr != nontrypticPeptideSet.end());
345  unit_assert_operator_equal(2, peptideItr->offset());
346  unit_assert_operator_equal(0, peptideItr->missedCleavages());
347  unit_assert_operator_equal(2, peptideItr->specificTermini());
348  unit_assert(peptideItr->NTerminusIsSpecific() &&
349  peptideItr->CTerminusIsSpecific());
350 
351  peptideItr = nontrypticPeptideSet.find("WVTFISLLLLFSSAYSRG");
352  unit_assert(peptideItr != nontrypticPeptideSet.end());
353  unit_assert_operator_equal(2, peptideItr->offset());
354  unit_assert_operator_equal(1, peptideItr->missedCleavages());
355  unit_assert_operator_equal(1, peptideItr->specificTermini());
356  unit_assert(peptideItr->NTerminusIsSpecific() &&
357  !peptideItr->CTerminusIsSpecific());
358 
359  peptideItr = nontrypticPeptideSet.find("VTFISLLLLFSSAYSRG");
360  unit_assert(peptideItr != nontrypticPeptideSet.end());
361  unit_assert_operator_equal(3, peptideItr->offset());
362  unit_assert_operator_equal(1, peptideItr->missedCleavages());
363  unit_assert_operator_equal(0, peptideItr->specificTermini());
364  unit_assert(!peptideItr->NTerminusIsSpecific() &&
365  !peptideItr->CTerminusIsSpecific());
366 
367  // test for peptides of all specificities
368  unit_assert(nontrypticPeptideSet.count("WVTFISLLLLFSSAYSR")); // tryptic
369  unit_assert(nontrypticPeptideSet.count("VTFISLLLLFSSAYSR")); // semi-tryptic
370  unit_assert(nontrypticPeptideSet.count("VTFISLLLLFSSAYS")); // non-tryptic
371 
372  // test non-specific peptides at the C terminus
373  unit_assert(nontrypticPeptideSet.count("FAVEGPKLVVSTQTALA")); // semi-tryptic
374  unit_assert(nontrypticPeptideSet.count("FAVEGPKLVVSTQTAL")); // non-tryptic
375  unit_assert_operator_equal("QTALA", nontrypticPeptides.back().sequence()); // semi-tryptic
376 
377  // test maximum missed cleavages
378  unit_assert(nontrypticPeptideSet.count("KWVTFISLLLLFSSAYSR"));
379  unit_assert(!nontrypticPeptideSet.count("KWVTFISLLLLFSSAYSRG"));
380 
381  // test minimum peptide length
382  unit_assert(!nontrypticPeptideSet.count("LR"));
383  unit_assert(!nontrypticPeptideSet.count("QRLR"));
384  unit_assert(nontrypticPeptideSet.count("VLASSAR"));
385 
386  // test maximum peptide length
387  unit_assert(!nontrypticPeptideSet.count("EYEATLEECCAKDDPHACYSTVFDK"));
388 }
389 
390 void testSemitrypticMethionineClippingBSA(const Digestion& semitrypticDigestion)
391 {
392  if (os_) *os_ << "Semi-specific BSA digest w/ methionine clipping (offset, missed cleavages, specific termini, length, sequence)" << endl;
393 
394  set<DigestedPeptide, DigestedPeptideLessThan>::const_iterator peptideItr;
395 
396  vector<DigestedPeptide> semitrypticPeptides(semitrypticDigestion.begin(), semitrypticDigestion.end());
397  set<DigestedPeptide, DigestedPeptideLessThan> semitrypticPeptideSet(semitrypticPeptides.begin(), semitrypticPeptides.end());
398 
399  if (os_)
400  {
401  BOOST_FOREACH(DigestedPeptide peptide, semitrypticPeptides)
402  {
403  *os_ << peptide.offset() << "\t" << peptide.missedCleavages() << "\t" <<
404  peptide.specificTermini() << "\t" << peptide.sequence().length() <<
405  "\t" << peptide.sequence() << "\n";
406  }
407  }
408 
409  // test count
410  unit_assert(semitrypticPeptides.size() > 3);
411 
412  // test order of enumeration and peptides at the N terminus;
413  // even with methionine clipping, MKWVT contains just one missed cleavage
414  unit_assert_operator_equal("MKWVT", semitrypticPeptides[0].sequence());
415  unit_assert_operator_equal("MKWVTF", semitrypticPeptides[1].sequence());
416  unit_assert_operator_equal("MKWVTFI", semitrypticPeptides[2].sequence());
417 
418  // test order of enumeration and peptides at the C terminus
419  unit_assert_operator_equal("QTALA", semitrypticPeptides.rbegin()->sequence());
420  unit_assert_operator_equal("TQTALA", (semitrypticPeptides.rbegin()+1)->sequence());
421  unit_assert_operator_equal("STQTALA", (semitrypticPeptides.rbegin()+2)->sequence());
422  unit_assert_operator_equal("LVVSTQTALA", (semitrypticPeptides.rbegin()+5)->sequence());
423  unit_assert_operator_equal("LVVSTQTAL", (semitrypticPeptides.rbegin()+6)->sequence());
424  unit_assert_operator_equal("LVVST", (semitrypticPeptides.rbegin()+10)->sequence());
425 
426  // test digestion metadata ([0]: MKWVT)
427  unit_assert_operator_equal(0, semitrypticPeptides[0].offset());
428  unit_assert_operator_equal(1, semitrypticPeptides[0].missedCleavages());
429  unit_assert_operator_equal(1, semitrypticPeptides[0].specificTermini());
430  unit_assert(semitrypticPeptides[0].NTerminusIsSpecific() &&
431  !semitrypticPeptides[0].CTerminusIsSpecific());
432 
433  peptideItr = semitrypticPeptideSet.find("KWVTFISLLLLFSSAYS"); // clipped methionine
434  unit_assert(peptideItr != semitrypticPeptideSet.end());
435  unit_assert_operator_equal(1, peptideItr->offset());
436  unit_assert_operator_equal(1, peptideItr->missedCleavages());
437  unit_assert_operator_equal(1, peptideItr->specificTermini());
438  unit_assert(peptideItr->NTerminusIsSpecific());
439 
440  peptideItr = semitrypticPeptideSet.find("KWVTFISLLLLFSSAYSR"); // clipped methionine
441  unit_assert(peptideItr != semitrypticPeptideSet.end());
442  unit_assert_operator_equal(1, peptideItr->offset());
443  unit_assert_operator_equal(1, peptideItr->missedCleavages());
444  unit_assert_operator_equal(2, peptideItr->specificTermini());
445  unit_assert(peptideItr->NTerminusIsSpecific() &&
446  peptideItr->CTerminusIsSpecific());
447 
448  peptideItr = semitrypticPeptideSet.find("KWVTFISLLLLFSSAYSRG"); // 2 missed cleavages
449  unit_assert(peptideItr == semitrypticPeptideSet.end());
450 
451  peptideItr = semitrypticPeptideSet.find("WVTFISLLLLFSSAYSR");
452  unit_assert(peptideItr != semitrypticPeptideSet.end());
453  unit_assert_operator_equal(2, peptideItr->offset());
454  unit_assert_operator_equal(0, peptideItr->missedCleavages());
455  unit_assert_operator_equal(2, peptideItr->specificTermini());
456  unit_assert(peptideItr->NTerminusIsSpecific() &&
457  peptideItr->CTerminusIsSpecific());
458 
459  peptideItr = semitrypticPeptideSet.find("WVTFISLLLLFSSAYSRG");
460  unit_assert(peptideItr != semitrypticPeptideSet.end());
461  unit_assert_operator_equal(2, peptideItr->offset());
462  unit_assert_operator_equal(1, peptideItr->missedCleavages());
463  unit_assert_operator_equal(1, peptideItr->specificTermini());
464  unit_assert(peptideItr->NTerminusIsSpecific() &&
465  !peptideItr->CTerminusIsSpecific());
466 
467  peptideItr = semitrypticPeptideSet.find("VTFISLLLLFSSAYSRG"); // non-tryptic
468  unit_assert(peptideItr == semitrypticPeptideSet.end());
469 
470  // test for non-specific peptides
471  unit_assert(semitrypticPeptideSet.count("WVTFISLLLLFSSAYSR")); // tryptic
472  unit_assert(semitrypticPeptideSet.count("KWVTFISLLLLFSSAYSR")); // semi-tryptic
473  unit_assert(semitrypticPeptideSet.count("KWVTFISLLLLFSSAYS")); // clipped methionine & semi-specific
474  unit_assert(!semitrypticPeptideSet.count("VTFISLLLLFSSAYS")); // non-specific
475 
476  // test semi-specific peptides at the C terminus
477  unit_assert(semitrypticPeptideSet.count("FAVEGPKLVVSTQTALA")); // semi-tryptic
478  unit_assert(!semitrypticPeptideSet.count("FAVEGPKLVVSTQTAL")); // non-tryptic
479 }
480 
482 {
483  if (os_) *os_ << "BSA digestion test" << endl;
484 
485  // >P02769|ALBU_BOVIN Serum albumin - Bos taurus (Bovine).
486  Peptide bsa("MKWVTFISLLLLFSSAYSRGVFRRDTHKSEIAHRFKDLGEEHFKGLVLIAFSQYLQQCPF"
487  "DEHVKLVNELTEFAKTCVADESHAGCEKSLHTLFGDELCKVASLRETYGDMADCCEKQEP"
488  "ERNECFLSHKDDSPDLPKLKPDPNTLCDEFKADEKKFWGKYLYEIARRHPYFYAPELLYY"
489  "ANKYNGVFQECCQAEDKGACLLPKIETMREKVLASSARQRLRCASIQKFGERALKAWSVA"
490  "RLSQKFPKAEFVEVTKLVTDLTKVHKECCHGDLLECADDRADLAKYICDNQDTISSKLKE"
491  "CCDKPLLEKSHCIAEVEKDAIPENLPPLTADFAEDKDVCKNYQEAKDAFLGSFLYEYSRR"
492  "HPEYAVSVLLRLAKEYEATLEECCAKDDPHACYSTVFDKLKHLVDEPQNLIKQNCDQFEK"
493  "LGEYGFQNALIVRYTRKVPQVSTPTLVEVSRSLGKVGTRCCTKPESERMPCTEDYLSLIL"
494  "NRLCVLHEKTPVSEKVTKCCTESLVNRRPCFSALTPDETYVPKAFDEKLFTFHADICTLP"
495  "DTEKQIKKQTALVELLKHKPKATEEQLKTVMENFVAFVDKCCAADDKEACFAVEGPKLVV"
496  "STQTALA");
497 
498  // test fully-specific trypsin digest
500  testTrypticBSA(Digestion(bsa, "(?<=[KR])", Digestion::Config(3, 5, 40)));
501 
502  // test semi-specific trypsin digest
505 
506  // test non-specific trypsin digest
509 
510  // test semi-specific trypsin digest with n-terminal methionine clipping (motif and regex only)
513 
514  // test funky digestion
515  Digestion funkyDigestion(bsa, "(?<=A[DE])(?=[FG])", Digestion::Config(0, 5, 100000, Digestion::FullySpecific, false));
516  vector<Peptide> funkyPeptides(funkyDigestion.begin(), funkyDigestion.end());
517 
518  unit_assert_operator_equal("MKWVTFISLLLLFSSAYSRGVFRRDTHKSEIAHRFKDLGEEHFKGLVLIAFSQYLQQCPFDEHVKLVNELTEFAKTCVADESHAGCEKSLHTLFGDELCKVASLRETYGDMADCCEKQEPERNECFLSHKDDSPDLPKLKPDPNTLCDEFKADEKKFWGKYLYEIARRHPYFYAPELLYYANKYNGVFQECCQAEDKGACLLPKIETMREKVLASSARQRLRCASIQKFGERALKAWSVARLSQKFPKAE", funkyPeptides[0].sequence());
519  unit_assert_operator_equal("FVEVTKLVTDLTKVHKECCHGDLLECADDRADLAKYICDNQDTISSKLKECCDKPLLEKSHCIAEVEKDAIPENLPPLTAD", funkyPeptides[1].sequence());
520  unit_assert_operator_equal("FAEDKDVCKNYQEAKDAFLGSFLYEYSRRHPEYAVSVLLRLAKEYEATLEECCAKDDPHACYSTVFDKLKHLVDEPQNLIKQNCDQFEKLGEYGFQNALIVRYTRKVPQVSTPTLVEVSRSLGKVGTRCCTKPESERMPCTEDYLSLILNRLCVLHEKTPVSEKVTKCCTESLVNRRPCFSALTPDETYVPKAFDEKLFTFHADICTLPDTEKQIKKQTALVELLKHKPKATEEQLKTVMENFVAFVDKCCAADDKEACFAVEGPKLVVSTQTALA", funkyPeptides[2].sequence());
521 
522  // test fully specific Asp-N digest (thus testing ambiguous residue disambiguation)
523  Digestion aspnDigestion(bsa, MS_Asp_N, Digestion::Config(0, 5, 100000, Digestion::FullySpecific, false));
524  vector<Peptide> aspnPeptides(aspnDigestion.begin(), aspnDigestion.end());
525  unit_assert_operator_equal("MKWVTFISLLLLFSSAYSRGVFRR", aspnPeptides[0].sequence());
526  unit_assert_operator_equal("DTHKSEIAHRFK", aspnPeptides[1].sequence());
527  unit_assert_operator_equal("DLGEEHFKGLVLIAFSQYLQQCPF", aspnPeptides[2].sequence());
528  unit_assert_operator_equal("DEHVKLV", aspnPeptides[3].sequence());
529  unit_assert_operator_equal("NELTEFAKTCVA", aspnPeptides[4].sequence());
530 
531  // test no cleavage "digestion"
532  Digestion noCleavageDigestion("ELVISLIVESK", MS_no_cleavage);
533  vector<Peptide> noCleavagePeptides(noCleavageDigestion.begin(), noCleavageDigestion.end());
534 
535  unit_assert_operator_equal(1, noCleavagePeptides.size());
536  unit_assert_operator_equal("ELVISLIVESK", noCleavagePeptides[0].sequence());
537 
538  // test unspecific cleavage digestion
539  Digestion unspecificCleavageDigestion("ELVISLK", MS_unspecific_cleavage, Digestion::Config(0, 5, 5, Digestion::FullySpecific, false));
540  vector<Peptide> unspecificCleavagePeptides(unspecificCleavageDigestion.begin(), unspecificCleavageDigestion.end());
541 
542  unit_assert_operator_equal(3, unspecificCleavagePeptides.size());
543  unit_assert_operator_equal("ELVIS", unspecificCleavagePeptides[0].sequence());
544  unit_assert_operator_equal("LVISL", unspecificCleavagePeptides[1].sequence());
545  unit_assert_operator_equal("VISLK", unspecificCleavagePeptides[2].sequence());
546 }
547 
548 
549 void testFind()
550 {
551  Digestion fully("PEPKTIDEKPEPTIDERPEPKTIDEKKKPEPTIDER", MS_Lys_C_P, Digestion::Config(2, 5, 10));
552  Digestion semi("PEPKTIDEKPEPTIDERPEPKTIDEKKKPEPTIDER", MS_Lys_C_P, Digestion::Config(2, 5, 10, Digestion::SemiSpecific));
553  Digestion non("PEPKTIDEKPEPTIDERPEPKTIDEKKKPEPTIDER", MS_Lys_C_P, Digestion::Config(2, 5, 10, Digestion::NonSpecific));
554  Digestion clipped("MPEPKTIDEKPEPTIDERPEPKTIDEKKKPEPTIDER", MS_Lys_C_P, Digestion::Config(2, 5, 10));
555 
556  // test find_all
557  unit_assert(fully.find_all("ABC").empty()); // not in peptide
558  unit_assert(fully.find_all("PEPK").empty()); // too short
559  unit_assert(fully.find_all("PEPKTIDEKK").empty()); // no N-terminal cleavage
560  unit_assert(fully.find_all("PEPTIDERPEPK").empty()); // too long
561  unit_assert(fully.find_all("PEPTIDERPEPTIDEK").empty()); // too long
562  unit_assert(semi.find_all("PEPKTIDEKKK").empty()); // too many missed cleavages
563  unit_assert(semi.find_all("EPKTIDE").empty()); // no specific termini
564  unit_assert(non.find_all("EPKTIDEKKK").empty()); // too many missed cleavages
565 
566  unit_assert(fully.find_all("PEPKTIDEK").size() == 1);
567  unit_assert(testDigestionMetadata(fully.find_all("PEPKTIDEK")[0], "PEPKTIDEK", 0, 1, 2, "", "P"));
568 
569  unit_assert(fully.find_all("TIDEK").size() == 2);
570  unit_assert(testDigestionMetadata(fully.find_all("TIDEK")[0], "TIDEK", 4, 0, 2, "K", "P"));
571  unit_assert(testDigestionMetadata(fully.find_all("TIDEK")[1], "TIDEK", 21, 0, 2, "K", "K"));
572 
573  unit_assert(fully.find_all("TIDEKK").size() == 1);
574  unit_assert(testDigestionMetadata(fully.find_all("TIDEKK")[0], "TIDEKK", 21, 1, 2, "K", "K"));
575 
576  unit_assert(fully.find_all("TIDEKKK").size() == 1);
577  unit_assert(testDigestionMetadata(fully.find_all("TIDEKKK")[0], "TIDEKKK", 21, 2, 2, "K", "P"));
578 
579  unit_assert(fully.find_all("PEPTIDER").size() == 1);
580  unit_assert(testDigestionMetadata(fully.find_all("PEPTIDER")[0], "PEPTIDER", 28, 0, 2, "K", ""));
581 
582  unit_assert(semi.find_all("PEPKTIDEKK").size() == 1);
583  unit_assert(testDigestionMetadata(semi.find_all("PEPKTIDEKK")[0], "PEPKTIDEKK", 17, 2, 1, "R", "K"));
584 
585  unit_assert(semi.find_all("EPKTIDEKK").size() == 1);
586  unit_assert(testDigestionMetadata(semi.find_all("EPKTIDEKK")[0], "EPKTIDEKK", 18, 2, 1, "P", "K"));
587 
588  unit_assert(non.find_all("PEPKTIDE").size() == 2);
589  unit_assert(testDigestionMetadata(non.find_all("PEPKTIDE")[0], "PEPKTIDE", 0, 1, 1, "", "K"));
590  unit_assert(testDigestionMetadata(non.find_all("PEPKTIDE")[1], "PEPKTIDE", 17, 1, 0, "R", "K"));
591 
592  unit_assert(fully.find_all("EPKTIDEK").empty()); // N-terminal 'P' is not clipped
593  unit_assert(clipped.find_all("PEPKTIDEK").size() == 1); // N-terminal 'M' is clipped
594  unit_assert(testDigestionMetadata(clipped.find_all("PEPKTIDEK")[0], "PEPKTIDEK", 1, 1, 2, "M", "P"));
595 
596  // test find_first
597  unit_assert_throws(fully.find_first("ABC"), runtime_error); // not in peptide
598  unit_assert_throws(fully.find_first("PEPK"), runtime_error); // too short
599  unit_assert_throws(fully.find_first("PEPKTIDEKK"), runtime_error); // no N-terminal cleavage
600  unit_assert_throws(fully.find_first("PEPTIDERPEPK"), runtime_error); // too long
601  unit_assert_throws(fully.find_first("PEPTIDERPEPTIDEK"), runtime_error); // too long
602  unit_assert_throws(semi.find_first("EPKTIDE"), runtime_error); // no specific termini
603  unit_assert_throws(semi.find_first("PEPKTIDEKKK"), runtime_error); // too many missed cleavages
604  unit_assert_throws(non.find_first("PEPKTIDEKKK"), runtime_error); // too many missed cleavages
605 
606  unit_assert(testDigestionMetadata(fully.find_first("PEPKTIDEK"), "PEPKTIDEK", 0, 1, 2, "", "P"));
607  unit_assert(testDigestionMetadata(fully.find_first("PEPKTIDEK", 4242), "PEPKTIDEK", 0, 1, 2, "", "P"));
608 
609  unit_assert(testDigestionMetadata(fully.find_first("TIDEK"), "TIDEK", 4, 0, 2, "K", "P"));
610  unit_assert(testDigestionMetadata(fully.find_first("TIDEK", 4242), "TIDEK", 4, 0, 2, "K", "P"));
611  unit_assert(testDigestionMetadata(fully.find_first("TIDEK", 15), "TIDEK", 21, 0, 2, "K", "K"));
612  unit_assert(testDigestionMetadata(fully.find_first("TIDEK", 21), "TIDEK", 21, 0, 2, "K", "K"));
613 
614  unit_assert(testDigestionMetadata(fully.find_first("TIDEKK"), "TIDEKK", 21, 1, 2, "K", "K"));
615  unit_assert(testDigestionMetadata(fully.find_first("TIDEKKK"), "TIDEKKK", 21, 2, 2, "K", "P"));
616  unit_assert(testDigestionMetadata(fully.find_first("PEPTIDER"), "PEPTIDER", 28, 0, 2, "K", ""));
617 
618  unit_assert(testDigestionMetadata(semi.find_first("IDEKK"), "IDEKK", 22, 1, 1, "T", "K"));
619  unit_assert(testDigestionMetadata(semi.find_first("IDEKKK"), "IDEKKK", 22, 2, 1, "T", "P"));
620  unit_assert(testDigestionMetadata(semi.find_first("PEPTIDER"), "PEPTIDER", 9, 0, 1, "K", "P"));
621  unit_assert(testDigestionMetadata(semi.find_first("PEPTIDER", 28), "PEPTIDER", 28, 0, 2, "K", ""));
622 
623  unit_assert(testDigestionMetadata(non.find_first("EPTIDE"), "EPTIDE", 10, 0, 0, "P", "R"));
624  unit_assert(testDigestionMetadata(non.find_first("EPTIDE", 29), "EPTIDE", 29, 0, 0, "P", "R"));
625 }
626 
627 
629 {
630  boost::exception_ptr exception;
631 
633  ThreadStatus(const boost::exception_ptr& e) : exception(e) {}
634 };
635 
636 
637 void testThreadSafetyWorker(boost::barrier* testBarrier, ThreadStatus& status)
638 {
639  testBarrier->wait(); // wait until all threads have started
640 
641  try
642  {
645  testFind();
646  }
647  catch (exception& e)
648  {
649  status.exception = boost::copy_exception(runtime_error(e.what()));
650  }
651  catch (...)
652  {
653  status.exception = boost::copy_exception(runtime_error("Unhandled exception in worker thread."));
654  }
655 }
656 
657 void testThreadSafety(const int& testThreadCount)
658 {
659  using boost::thread;
660 
661  boost::barrier testBarrier(testThreadCount);
662  list<pair<boost::shared_ptr<thread>, ThreadStatus> > threads;
663  for (int i=0; i < testThreadCount; ++i)
664  {
665  threads.push_back(make_pair(boost::shared_ptr<thread>(), ThreadStatus()));
666  threads.back().first.reset(new thread(testThreadSafetyWorker, &testBarrier, boost::ref(threads.back().second)));
667  }
668 
669  set<boost::shared_ptr<thread> > finishedThreads;
670  while (finishedThreads.size() < threads.size())
671  BOOST_FOREACH_FIELD((boost::shared_ptr<thread>& t)(ThreadStatus& status), threads)
672  {
673  if (t->timed_join(boost::posix_time::seconds(1)))
674  finishedThreads.insert(t);
675 
676  if (status.exception != NULL) // non-null exception?
677  boost::rethrow_exception(status.exception);
678  }
679 }
680 
681 
682 int main(int argc, char* argv[])
683 {
684  TEST_PROLOG(argc, argv)
685 
686  if (argc>1 && !strcmp(argv[1],"-v")) os_ = &cout;
687  if (os_) *os_ << "DigestionTest\n";
688 
689  try
690  {
691  //testThreadSafety(1); // does not test thread-safety of singleton initialization
692  testThreadSafety(2);
693  testThreadSafety(4);
694  //testThreadSafety(8);
695  //testThreadSafety(16); // high thread count fails non-deterministically on MSVC; I haven't been able to find the cause.
696  }
697  catch (exception& e)
698  {
699  TEST_FAILED(e.what())
700  }
701  catch (...)
702  {
703  TEST_FAILED("Caught unknown exception.")
704  }
705 
707 }
void testSemitrypticBSA(const Digestion &semitrypticDigestion)
void testCleavageAgents()
MS_Asp_N
Asp-N: Endoproteinase Asp-N.
Definition: cv.hpp:4165
PWIZ_API_DECL const CVTermInfo & cvTermInfo(CVID cvid)
returns CV term info for the specified CVID
MS_Arg_C
Arg-C: Endoproteinase Arg-C.
Definition: cv.hpp:4159
#define unit_assert_throws(x, exception)
Definition: unit.hpp:106
void testBSADigestion()
void testTrypticBSA(const Digestion &trypticDigestion)
bool testDigestionMetadata(const DigestedPeptide &peptide, const string &expectedSequence, size_t expectedOffset, size_t expectedMissedCleavages, size_t expectedSpecificTermini, const string &expectedPrefix, const string &expectedSuffix)
void testThreadSafety(const int &testThreadCount)
MS_Trypsin
Trypsin: Enzyme trypsin.
Definition: cv.hpp:4027
PWIZ_API_DECL proteome::Peptide peptide(const Peptide &peptide)
creates a proteome::Peptide from an identdata::Peptide
size_t offset() const
returns the zero-based offset of the N terminus of the peptide in the polypeptide from which it was d...
#define TEST_EPILOG
Definition: unit.hpp:182
MS_Glu_C
Glu-C (glutamyl endopeptidase): Enzyme glutamyl endopeptidase (EC 3.4.21.19).
Definition: cv.hpp:6013
NonSpecific
Definition: Digestion.hpp:119
sets constraints for valid peptides produced by iterating the digestion
Definition: Digestion.hpp:125
MS_TrypChymo
TrypChymo: Cleavage agent TrypChymo.
Definition: cv.hpp:4189
MS_Asp_N_ambic
Asp-N_ambic: Enzyme Asp-N, Ammonium Bicarbonate (AmBic).
Definition: cv.hpp:4168
MS_CNBr
CNBr: Cyanogen bromide.
Definition: cv.hpp:4174
ostream * os_
MS_V8_E
V8-E: Cleavage agent V8-E.
Definition: cv.hpp:4198
ThreadStatus(const boost::exception_ptr &e)
PWIZ_API_DECL std::vector< CVID > cleavageAgents(const Enzymes &enzymes)
returns a list of cleavage agent CVIDs for an identdata::Enzymes instance
MS_V8_DE
V8-DE: Cleavage agent V8-DE.
Definition: cv.hpp:4195
represents a peptide or polypeptide (a sequence of amino acids)
Definition: Peptide.hpp:61
MS_Lys_C_P
Lys-C/P: Proteinase Lys-C/P.
Definition: cv.hpp:4183
std::string NTerminusPrefix() const
returns residue preceding digestion site
SemiSpecific
neither termini must match digestion motif(s)
Definition: Digestion.hpp:120
#define unit_assert_operator_equal(expected, actual)
Definition: unit.hpp:92
MS_no_cleavage
no cleavage: No cleavage.
Definition: cv.hpp:6130
size_t missedCleavages() const
returns the number of missed cleavage sites in the peptide
void testFind()
std::vector< DigestedPeptide > find_all(const Peptide &peptide) const
returns all instances of the given peptide in the polypeptide under digestion; note: the filters set ...
MS_Trypsin_P
Trypsin/P: Cleavage agent Trypsin/P.
Definition: cv.hpp:4192
void testNontrypticBSA(const Digestion &nontrypticDigestion)
std::string name
Definition: cv.hpp:13385
MS_Lys_C
Lys-C: Endoproteinase Lys-C.
Definition: cv.hpp:4180
DigestedPeptide find_first(const Peptide &peptide, size_t offsetHint=0) const
returns the first instance of the given peptide in the polypeptide under digestion; if offsetHint is ...
const_iterator end() const
#define TEST_FAILED(x)
Definition: unit.hpp:176
size_t specificTermini() const
returns the number of termini that matched to the digestion rules
void testSemitrypticMethionineClippingBSA(const Digestion &semitrypticDigestion)
boost::exception_ptr exception
CVID_Unknown
Definition: cv.hpp:97
MS_ion_trap
ion trap: A device for spatially confining ions using electric and magnetic fields alone or in combin...
Definition: cv.hpp:1126
MS_Formic_acid
Formic_acid: Formic acid.
Definition: cv.hpp:4177
#define TEST_PROLOG(argc, argv)
Definition: unit.hpp:174
int main(int argc, char *argv[])
MS_glutamyl_endopeptidase
glutamyl endopeptidase: Enzyme glutamyl endopeptidase (EC 3.4.21.19).
Definition: cv.hpp:6007
enumerates the peptides from proteolytic digestion of a polypeptide or protein;
Definition: Digestion.hpp:111
std::string CTerminusSuffix() const
returns residue following digestion site
const_iterator begin() const
peptide subclass that contains extra metadata provided by digestion
Definition: Digestion.hpp:47
MS_unspecific_cleavage
unspecific cleavage: Unspecific cleavage.
Definition: cv.hpp:6133
#define unit_assert(x)
Definition: unit.hpp:85
MS_NoEnzyme_OBSOLETE
NoEnzyme:
Definition: cv.hpp:3580
MS_Chymotrypsin
Chymotrypsin: Enzyme chymotrypsin.
Definition: cv.hpp:4171
Definition: cv.hpp:91
void testThreadSafetyWorker(boost::barrier *testBarrier, ThreadStatus &status)
const std::string & sequence() const
returns the sequence of amino acids making up the peptide
MS_PepsinA
PepsinA: PepsinA proteinase.
Definition: cv.hpp:4186