Merge branch 'merge/JAL-3285_mchmmer_with_211_develop' into alpha/JAL-3362_Jalview_21...
[jalview.git] / test / jalview / analysis / scoremodels / PIDModelTest.java
1 package jalview.analysis.scoremodels;
2
3 import static org.testng.Assert.assertEquals;
4
5 import jalview.api.analysis.SimilarityParamsI;
6 import jalview.util.Comparison;
7
8 import org.testng.annotations.Test;
9
10 public class PIDModelTest
11 {
12   private static final double DELTA = 0.00001D;
13
14   @Test(groups = "Functional")
15   public void testGetPairwiseScore()
16   {
17     PIDModel sm = new PIDModel();
18     assertEquals(sm.getPairwiseScore('A', 'A'), 1f);
19     assertEquals(sm.getPairwiseScore('A', 'a'), 1f);
20     assertEquals(sm.getPairwiseScore('a', 'A'), 1f);
21     assertEquals(sm.getPairwiseScore('A', 'B'), 0f);
22     assertEquals(sm.getPairwiseScore('A', ' '), 0f);
23     assertEquals(sm.getPairwiseScore(' ', ' '), 0f);
24     assertEquals(sm.getPairwiseScore('.', '.'), 0f);
25     assertEquals(sm.getPairwiseScore('-', '-'), 0f);
26   }
27
28   /**
29    * Regression test to verify that a (suitably configured) PIDModel computes
30    * the same percentage identities as the Comparison.PID method
31    */
32   @Test(groups = "Functional")
33   public void testComputePID_matchesComparisonPID()
34   {
35     SimilarityParamsI params = new SimilarityParams(true, true, true, true);
36
37     /*
38      * same length, no gaps
39      */
40     String s1 = "ARFNQDWSGI";
41     String s2 = "ARKNQDQSGI";
42
43     new PIDModel();
44     double newScore = PIDModel.computePID(s1, s2, params);
45     double oldScore = Comparison.PID(s1, s2);
46     assertEquals(newScore, oldScore, DELTA);
47     // and verify PIDModel calculation is symmetric
48     assertEquals(newScore, PIDModel.computePID(s2, s1, params));
49
50     /*
51      * same length, with gaps
52      */
53     s1 = "-RFNQDWSGI";
54     s2 = "ARKNQ-QSGI";
55     new PIDModel();
56     newScore = PIDModel.computePID(s1, s2, params);
57     oldScore = Comparison.PID(s1, s2);
58     assertEquals(newScore, oldScore, DELTA);
59     assertEquals(newScore, PIDModel.computePID(s2, s1, params));
60
61     /*
62      * s2 longer than s1, with gaps
63      */
64     s1 = "ARK-";
65     s2 = "-RFNQ";
66     new PIDModel();
67     newScore = PIDModel.computePID(s1, s2, params);
68     oldScore = Comparison.PID(s1, s2);
69     assertEquals(newScore, oldScore, DELTA);
70     assertEquals(newScore, PIDModel.computePID(s2, s1, params));
71
72     /*
73      * s1 longer than s2, with gaps
74      */
75     s1 = "-RFNQ";
76     s2 = "ARK-";
77     new PIDModel();
78     newScore = PIDModel.computePID(s1, s2, params);
79     oldScore = Comparison.PID(s1, s2);
80     assertEquals(newScore, oldScore, DELTA);
81     assertEquals(newScore, PIDModel.computePID(s2, s1, params));
82
83     /*
84      * same but now also with gapped columns
85      */
86     s1 = "-R-F-NQ";
87     s2 = "AR-K--";
88     new PIDModel();
89     newScore = PIDModel.computePID(s1, s2, params);
90     oldScore = Comparison.PID(s1, s2);
91     assertEquals(newScore, oldScore, DELTA);
92     assertEquals(newScore, PIDModel.computePID(s2, s1, params));
93   }
94
95   /**
96    * Tests for percentage identity variants where only the shorter length of two
97    * sequences is used
98    */
99   @Test(groups = "Functional")
100   public void testComputePID_matchShortestSequence()
101   {
102     String s1 = "FR-K-S";
103     String s2 = "FS--L";
104
105     /*
106      * match gap-gap and gap-char
107      * PID = 4/5 = 80%
108      */
109     SimilarityParamsI params = new SimilarityParams(true, true, true, true);
110     assertEquals(PIDModel.computePID(s1, s2, params), 80d);
111     assertEquals(PIDModel.computePID(s2, s1, params), 80d);
112
113     /*
114      * match gap-char but not gap-gap
115      * PID = 3/4 = 75%
116      */
117     params = new SimilarityParams(false, true, true, true);
118     assertEquals(PIDModel.computePID(s1, s2, params), 75d);
119     assertEquals(PIDModel.computePID(s2, s1, params), 75d);
120
121     /*
122      * include gaps but don't match them
123      * include gap-gap, counted as identity
124      * PID = 2/5 = 40%
125      */
126     params = new SimilarityParams(true, false, true, true);
127     assertEquals(PIDModel.computePID(s1, s2, params), 40d);
128     assertEquals(PIDModel.computePID(s2, s1, params), 40d);
129
130     /*
131      * include gaps but don't match them
132      * exclude gap-gap
133      * PID = 1/4 = 25%
134      */
135     params = new SimilarityParams(false, false, true, true);
136     assertEquals(PIDModel.computePID(s1, s2, params), 25d);
137     assertEquals(PIDModel.computePID(s2, s1, params), 25d);
138   }
139
140   /**
141    * Tests for percentage identity variants where the longer length of two
142    * sequences is used
143    */
144   @Test(groups = "Functional")
145   public void testComputePID_matchLongestSequence()
146   {
147     String s1 = "FR-K-S";
148     String s2 = "FS--L";
149   
150     /*
151      * match gap-gap and gap-char
152      * shorter sequence treated as if with trailing gaps
153      * PID = 5/6 = 83.333...%
154      */
155     SimilarityParamsI params = new SimilarityParams(true, true, true, false);
156     assertEquals(PIDModel.computePID(s1, s2, params), 500d / 6);
157     assertEquals(PIDModel.computePID(s2, s1, params), 500d / 6);
158   
159     /*
160      * match gap-char but not gap-gap
161      * PID = 4/5 = 80%
162      */
163     params = new SimilarityParams(false, true, true, false);
164     assertEquals(PIDModel.computePID(s1, s2, params), 80d);
165     assertEquals(PIDModel.computePID(s2, s1, params), 80d);
166   
167     /*
168      * include gaps but don't match them
169      * include gap-gap, counted as identity
170      * PID = 2/6 = 33.333...%
171      */
172     params = new SimilarityParams(true, false, true, false);
173     assertEquals(PIDModel.computePID(s1, s2, params), 100d / 3);
174     assertEquals(PIDModel.computePID(s2, s1, params), 100d / 3);
175   
176     /*
177      * include gaps but don't match them
178      * exclude gap-gap
179      * PID = 1/5 = 25%
180      */
181     params = new SimilarityParams(false, false, true, false);
182     assertEquals(PIDModel.computePID(s1, s2, params), 20d);
183     assertEquals(PIDModel.computePID(s2, s1, params), 20d);
184
185     /*
186      * no tests for matchGaps=true, includeGaps=false
187      * as it don't make sense
188      */
189   }
190 }