+++ /dev/null
-#include "muscle.h"\r
-#include "profile.h"\r
-#include "pwpath.h"\r
-#include <math.h>\r
-\r
-#define TRACE 0\r
-\r
-#define EQ(a, b) (fabs(a-b) < 0.1)\r
-\r
-SCORE TraceBack(const ProfPos *PA, unsigned uLengthA, const ProfPos *PB,\r
- unsigned uLengthB, const SCORE *DPM_, const SCORE *DPD_, const SCORE *DPI_,\r
- PWPath &Path)\r
- {\r
-#if TRACE\r
- Log("\n");\r
- Log("TraceBack LengthA=%u LengthB=%u\n", uLengthA, uLengthB);\r
-#endif\r
- assert(uLengthB > 0 && uLengthA > 0);\r
-\r
- const unsigned uPrefixCountA = uLengthA + 1;\r
- const unsigned uPrefixCountB = uLengthB + 1;\r
-\r
- Path.Clear();\r
-\r
- unsigned uPrefixLengthA = uLengthA;\r
- unsigned uPrefixLengthB = uLengthB;\r
-\r
- const SCORE scoreM = DPM(uPrefixLengthA, uPrefixLengthB);\r
- SCORE scoreD = DPD(uPrefixLengthA, uPrefixLengthB);\r
- SCORE scoreI = DPI(uPrefixLengthA, uPrefixLengthB);\r
-\r
- const ProfPos &LastPPA = PA[uLengthA - 1];\r
- const ProfPos &LastPPB = PB[uLengthB - 1];\r
-\r
- scoreD += LastPPA.m_scoreGapClose;\r
- scoreI += LastPPB.m_scoreGapClose;\r
-\r
- char cEdgeType = cInsane;\r
- SCORE scoreMax;\r
- if (scoreM >= scoreD && scoreM >= scoreI)\r
- {\r
- scoreMax = scoreM;\r
- cEdgeType = 'M';\r
- }\r
- else if (scoreD >= scoreM && scoreD >= scoreI)\r
- {\r
- scoreMax = scoreD;\r
- cEdgeType = 'D';\r
- }\r
- else\r
- {\r
- assert(scoreI >= scoreM && scoreI >= scoreD);\r
- scoreMax = scoreI;\r
- cEdgeType = 'I';\r
- }\r
-\r
- for (;;)\r
- {\r
- if ('S' == cEdgeType)\r
- break;\r
-\r
- PWEdge Edge;\r
- Edge.cType = cEdgeType;\r
- Edge.uPrefixLengthA = uPrefixLengthA;\r
- Edge.uPrefixLengthB = uPrefixLengthB;\r
- Path.PrependEdge(Edge);\r
-\r
- char cPrevEdgeType;\r
- unsigned uPrevPrefixLengthA = uPrefixLengthA;\r
- unsigned uPrevPrefixLengthB = uPrefixLengthB;\r
-\r
- switch (cEdgeType)\r
- {\r
- case 'M':\r
- {\r
- assert(uPrefixLengthA > 0);\r
- assert(uPrefixLengthB > 0);\r
- const ProfPos &PPA = PA[uPrefixLengthA - 1];\r
- const ProfPos &PPB = PB[uPrefixLengthB - 1];\r
-\r
- const SCORE Score = DPM(uPrefixLengthA, uPrefixLengthB);\r
- const SCORE scoreMatch = ScoreProfPos2(PPA, PPB);\r
-\r
- SCORE scoreSM;\r
- if (1 == uPrefixLengthA && 1 == uPrefixLengthB)\r
- scoreSM = scoreMatch;\r
- else\r
- scoreSM = MINUS_INFINITY;\r
-\r
- SCORE scoreMM = MINUS_INFINITY;\r
- SCORE scoreDM = MINUS_INFINITY;\r
- SCORE scoreIM = MINUS_INFINITY;\r
- if (uPrefixLengthA > 1 && uPrefixLengthB > 1)\r
- scoreMM = DPM(uPrefixLengthA-1, uPrefixLengthB-1) + scoreMatch;\r
- if (uPrefixLengthA > 1)\r
- {\r
- SCORE scoreTransDM = PA[uPrefixLengthA-2].m_scoreGapClose;\r
- scoreDM = DPD(uPrefixLengthA-1, uPrefixLengthB-1) + scoreTransDM + scoreMatch;\r
- }\r
- if (uPrefixLengthB > 1)\r
- {\r
- SCORE scoreTransIM = PB[uPrefixLengthB-2].m_scoreGapClose;\r
- scoreIM = DPI(uPrefixLengthA-1, uPrefixLengthB-1) + scoreTransIM + scoreMatch;\r
- }\r
-\r
- if (EQ(scoreMM, Score))\r
- cPrevEdgeType = 'M';\r
- else if (EQ(scoreDM, Score))\r
- cPrevEdgeType = 'D';\r
- else if (EQ(scoreIM, Score))\r
- cPrevEdgeType = 'I';\r
- else if (EQ(scoreSM, Score))\r
- cPrevEdgeType = 'S';\r
- else\r
- Quit("TraceBack: failed to match M score=%g M=%g D=%g I=%g S=%g",\r
- Score, scoreMM, scoreDM, scoreIM, scoreSM);\r
-\r
- --uPrevPrefixLengthA;\r
- --uPrevPrefixLengthB;\r
- break;\r
- }\r
-\r
- case 'D':\r
- {\r
- assert(uPrefixLengthA > 0);\r
- const SCORE Score = DPD(uPrefixLengthA, uPrefixLengthB);\r
-\r
- SCORE scoreMD = MINUS_INFINITY;\r
- SCORE scoreDD = MINUS_INFINITY;\r
- SCORE scoreSD = MINUS_INFINITY;\r
- if (uPrefixLengthB == 0)\r
- {\r
- if (uPrefixLengthA == 1)\r
- scoreSD = PA[0].m_scoreGapOpen;\r
- else\r
- scoreSD = DPD(uPrefixLengthA - 1, 0);\r
- }\r
- if (uPrefixLengthA > 1)\r
- {\r
- const ProfPos &PPA = PA[uPrefixLengthA - 1];\r
- SCORE scoreTransMD = PPA.m_scoreGapOpen;\r
- scoreMD = DPM(uPrefixLengthA-1, uPrefixLengthB) + scoreTransMD;\r
- scoreDD = DPD(uPrefixLengthA-1, uPrefixLengthB);\r
- }\r
-\r
- if (EQ(Score, scoreMD))\r
- cPrevEdgeType = 'M';\r
- else if (EQ(Score, scoreDD))\r
- cPrevEdgeType = 'D';\r
- else if (EQ(Score, scoreSD))\r
- cPrevEdgeType = 'S';\r
- else\r
- Quit("TraceBack: failed to match D");\r
-\r
- --uPrevPrefixLengthA;\r
- break;\r
- }\r
-\r
- case 'I':\r
- {\r
- assert(uPrefixLengthB > 0);\r
- const SCORE Score = DPI(uPrefixLengthA, uPrefixLengthB);\r
-\r
- SCORE scoreMI = MINUS_INFINITY;\r
- SCORE scoreII = MINUS_INFINITY;\r
- SCORE scoreSI = MINUS_INFINITY;\r
- if (uPrefixLengthA == 0)\r
- {\r
- if (uPrefixLengthB == 1)\r
- scoreSI = PB[0].m_scoreGapOpen;\r
- else\r
- scoreSI = DPI(0, uPrefixLengthB - 1);\r
- }\r
- if (uPrefixLengthB > 1)\r
- {\r
- const ProfPos &PPB = PB[uPrefixLengthB - 1];\r
- SCORE scoreTransMI = PPB.m_scoreGapOpen;\r
- scoreMI = DPM(uPrefixLengthA, uPrefixLengthB-1) + scoreTransMI;\r
- scoreII = DPI(uPrefixLengthA, uPrefixLengthB-1);\r
- }\r
-\r
- if (EQ(Score, scoreMI))\r
- cPrevEdgeType = 'M';\r
- else if (EQ(Score, scoreII))\r
- cPrevEdgeType = 'I';\r
- else if (EQ(Score, scoreSI))\r
- cPrevEdgeType = 'S';\r
- else\r
- Quit("TraceBack: failed to match I");\r
-\r
- --uPrevPrefixLengthB;\r
- break;\r
- }\r
-\r
- default:\r
- assert(false);\r
- }\r
-#if TRACE\r
- Log("Edge %c%c%u.%u", cPrevEdgeType, cEdgeType, uPrefixLengthA, uPrefixLengthB);\r
- Log("\n");\r
-#endif\r
- cEdgeType = cPrevEdgeType;\r
- uPrefixLengthA = uPrevPrefixLengthA;\r
- uPrefixLengthB = uPrevPrefixLengthB;\r
- }\r
-\r
- return scoreMax;\r
- }\r