001 /*
002 * BasicScoringScheme.java
003 *
004 * Copyright 2003 Sergio Anibal de Carvalho Junior
005 *
006 * This file is part of NeoBio.
007 *
008 * NeoBio is free software; you can redistribute it and/or modify it under the terms of
009 * the GNU General Public License as published by the Free Software Foundation; either
010 * version 2 of the License, or (at your option) any later version.
011 *
012 * NeoBio is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
013 * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
014 * PURPOSE. See the GNU General Public License for more details.
015 *
016 * You should have received a copy of the GNU General Public License along with NeoBio;
017 * if not, write to the Free Software Foundation, Inc., 59 Temple Place, Suite 330,
018 * Boston, MA 02111-1307, USA.
019 *
020 * Proper attribution of the author as the source of the software would be appreciated.
021 *
022 * Sergio Anibal de Carvalho Junior mailto:sergioanibaljr@users.sourceforge.net
023 * Department of Computer Science http://www.dcs.kcl.ac.uk
024 * King's College London, UK http://www.kcl.ac.uk
025 *
026 * Please visit http://neobio.sourceforge.net
027 *
028 * This project was supervised by Professor Maxime Crochemore.
029 *
030 */
031
032 package neobio.alignment;
033
034 /**
035 * This class implements a basic scoring scheme. At least three parameters must be
036 * provided to the constructor: the reward for a match (a substitution of equal
037 * characters), the penalty for a mismatch (a substitution of different characters) and
038 * the cost of a gap (an insertion or deletion of a character). Note that it only supports
039 * an additive gap cost function.
040 *
041 * <P>Although the match reward is expected to be a positive value, and the mismatch
042 * penalty and the gap cost are expected to be negative, no attempt is made to enforce
043 * these behaviour.</P>
044 *
045 * @author Sergio A. de Carvalho Jr.
046 */
047 public class BasicScoringScheme extends ScoringScheme
048 {
049 /**
050 * The reward for a match (a substitution of equal characters).
051 */
052 protected int match_reward;
053
054 /**
055 * The penalty for a mismatch (a substitution of different characters).
056 */
057 protected int mismatch_penalty;
058
059 /**
060 * The cost of a gap (an insertion or deletion of a character).
061 */
062 protected int gap_cost;
063
064 /**
065 * The maximum absolute score that this scoring scheme can return, which is the
066 * maximum absolute value among <CODE>match_reward</CODE>,
067 * <CODE>mismatch_penalty</CODE> and <CODE>gap_cost</CODE>.
068 */
069 protected int max_absolute_score;
070
071 /**
072 * Creates a new instance of a basic scoring scheme with the specified values of
073 * match reward, mismatch penalty and gap cost. The case of characters is significant
074 * when subsequently computing their score.
075 *
076 * @param match_reward reward for a substitution of equal characters
077 * @param mismatch_penalty penalty for a substitution of different characters
078 * @param gap_cost cost of an insertion or deletion of any character
079 */
080 public BasicScoringScheme (int match_reward, int mismatch_penalty, int gap_cost)
081 {
082 this (match_reward, mismatch_penalty, gap_cost, true);
083 }
084
085 /**
086 * Creates a new instance of basic scoring scheme with the specified values of
087 * match reward, mismatch penalty and gap cost. If <CODE>case_sensitive</CODE> is
088 * <CODE>true</CODE>, the case of characters is significant when subsequently
089 * computing their score; otherwise the case is ignored.
090 *
091 * @param match_reward reward for a substitution of equal characters
092 * @param mismatch_penalty penalty for a substitution of different characters
093 * @param gap_cost cost of an insertion or deletion of any character
094 * @param case_sensitive <CODE>true</CODE> if the case of characters must be
095 * significant, <CODE>false</CODE> otherwise
096 */
097 public BasicScoringScheme (int match_reward, int mismatch_penalty, int gap_cost,
098 boolean case_sensitive)
099 {
100 super(case_sensitive);
101
102 this.match_reward = match_reward;
103 this.mismatch_penalty = mismatch_penalty;
104 this.gap_cost = gap_cost;
105
106 // store the maximum absolute score that this scoring scheme can return,
107 // which is the maximum absolute value among match_reward, mismatch_penalty
108 // and gap_cost
109 if (Math.abs(match_reward) >= Math.abs(mismatch_penalty))
110 if (Math.abs(match_reward) >= Math.abs(gap_cost))
111 this.max_absolute_score = Math.abs(match_reward);
112 else
113 this.max_absolute_score = Math.abs(gap_cost);
114 else
115 if (Math.abs(mismatch_penalty) >= Math.abs(gap_cost))
116 this.max_absolute_score = Math.abs(mismatch_penalty);
117 else
118 this.max_absolute_score = Math.abs(gap_cost);
119 }
120
121 /**
122 * Returns the score of a substitution of character <CODE>a</CODE> for character
123 * <CODE>b</CODE> according to this scoring scheme. It is <CODE>match_reward</CODE>
124 * if <CODE>a</CODE> equals <CODE>b</CODE>, <CODE>mismatch_penalty</CODE> otherwise.
125 *
126 * @param a first character
127 * @param b second character
128 * @return <CODE>match_reward</CODE> if <CODE>a</CODE> equals <CODE>b</CODE>,
129 * <CODE>mismatch_penalty</CODE> otherwise.
130 */
131 public int scoreSubstitution (char a, char b)
132 {
133 if (isCaseSensitive())
134 if (a == b)
135 return match_reward;
136 else
137 return mismatch_penalty;
138 else
139 if (Character.toLowerCase(a) == Character.toLowerCase(b))
140 return match_reward;
141 else
142 return mismatch_penalty;
143 }
144
145 /**
146 * Always returns <CODE>gap_cost</CODE> for the insertion of any character.
147 *
148 * @param a the character to be inserted
149 * @return <CODE>gap_cost</CODE>
150 */
151 public int scoreInsertion (char a)
152 {
153 return gap_cost;
154 }
155
156 /**
157 * Always returns <CODE>gap_cost</CODE> for the deletion of any character.
158 *
159 * @param a the character to be deleted
160 * @return <CODE>gap_cost</CODE>
161 */
162 public int scoreDeletion (char a)
163 {
164 return gap_cost;
165 }
166
167 /**
168 * Returns the maximum absolute score that this scoring scheme can return for any
169 * substitution, deletion or insertion, which is the maximum absolute value among
170 * <CODE>match_reward</CODE>, <CODE>mismatch_penalty</CODE> and
171 * <CODE>gap_cost</CODE>.
172 *
173 * @return the maximum absolute value among <CODE>match_reward</CODE>,
174 * <CODE>mismatch_penalty</CODE> and <CODE>gap_cost</CODE>.
175 */
176 public int maxAbsoluteScore ()
177 {
178 return max_absolute_score;
179 }
180
181 /**
182 * Tells whether this scoring scheme supports partial matches, which it does not.
183 *
184 * @return always return <CODE>false</CODE>
185 */
186 public boolean isPartialMatchSupported ()
187 {
188 return false;
189 }
190
191 /**
192 * Returns a String representation of this scoring scheme.
193 *
194 * @return a String representation of this scoring scheme
195 */
196 public String toString ()
197 {
198 return "Basic scoring scheme: match reward = " + match_reward +
199 ", mismatch penalty = " + mismatch_penalty + ", gap cost = " + gap_cost;
200 }
201 }