2 * Jalview - A Sequence Alignment Editor and Viewer ($$Version-Rel$$)
3 * Copyright (C) $$Year-Rel$$ The Jalview Authors
5 * This file is part of Jalview.
7 * Jalview is free software: you can redistribute it and/or
8 * modify it under the terms of the GNU General Public License
9 * as published by the Free Software Foundation, either version 3
10 * of the License, or (at your option) any later version.
12 * Jalview is distributed in the hope that it will be useful, but
13 * WITHOUT ANY WARRANTY; without even the implied warranty
14 * of MERCHANTABILITY or FITNESS FOR A PARTICULAR
15 * PURPOSE. See the GNU General Public License for more details.
17 * You should have received a copy of the GNU General Public License
18 * along with Jalview. If not, see <http://www.gnu.org/licenses/>.
19 * The Jalview Authors are detailed in the 'AUTHORS' file.
23 import jalview.util.Format;
25 import java.lang.Math;
26 import java.util.Arrays;
29 * A collection of miscellaneous mathematical operations
30 * @AUTHOR MorellThomas
38 public static void print(double[] m, String format)
40 System.out.print("[ ");
43 Format.print(System.out, format + " ", a);
45 System.out.println("]");
49 * calculates the mean of an array
54 public static double mean(double[] m)
58 for (int i = 0; i < m.length; i++)
60 if (!Double.isNaN(m[i])) // ignore NaN values in the array
67 return sum / (double) (m.length - nanCount);
71 * calculates the sum of an array
76 public static double sum(double[] m)
79 for (int i = 0; i < m.length; i++)
81 if (!Double.isNaN(m[i])) // ignore NaN values in the array
90 * calculates the square root of each element in an array
96 * make general with function passed -> apply function to each element
98 public static double[] sqrt(double[] m)
100 double[] sqrts = new double[m.length];
101 for (int i = 0; i < m.length; i++)
103 sqrts[i] = Math.sqrt(m[i]);
109 * calculate element wise multiplication of two arrays with the same length
116 public static double[] elementwiseMultiply(byte[] a, double[] b) throws RuntimeException
118 if (a.length != b.length) // throw exception if the arrays do not have the same length
120 throw new SameLengthException(a.length, b.length);
122 double[] result = new double[a.length];
123 for (int i = 0; i < a.length; i++)
125 result[i] = a[i] * b[i];
129 public static double[] elementwiseMultiply(double[] a, double[] b) throws RuntimeException
131 if (a.length != b.length) // throw exception if the arrays do not have the same length
133 throw new SameLengthException(a.length, b.length);
135 double[] result = new double[a.length];
136 for (int i = 0; i < a.length; i++)
138 result[i] = a[i] * b[i];
142 public static byte[] elementwiseMultiply(byte[] a, byte[] b) throws RuntimeException
144 if (a.length != b.length) // throw exception if the arrays do not have the same length
146 throw new SameLengthException(a.length, b.length);
148 byte[] result = new byte[a.length];
149 for (int i = 0; i < a.length; i++)
151 result[i] = (byte) (a[i] * b[i]);
155 public static double[] elementwiseMultiply(double[] a, double b)
157 double[] result = new double[a.length];
158 for (int i = 0; i < a.length; i++)
160 result[i] = a[i] * b;
166 * calculate element wise division of two arrays ~ a / b
173 public static double[] elementwiseDivide(double[] a, double[] b) throws RuntimeException
175 if (a.length != b.length) // throw exception if the arrays do not have the same length
177 throw new SameLengthException(a.length, b.length);
179 double[] result = new double[a.length];
180 for (int i = 0; i < a.length; i++)
182 result[i] = a[i] / b[i];
188 * calculate element wise addition of two arrays
195 public static double[] elementwiseAdd(double[] a, double[] b) throws RuntimeException
197 if (a.length != b.length) // throw exception if the arrays do not have the same length
199 throw new SameLengthException(a.length, b.length);
201 double[] result = new double[a.length];
203 for (int i = 0; i < a.length; i++)
205 result[i] += a[i] + b[i];
209 public static double[] elementwiseAdd(double[] a, double b)
211 double[] result = new double[a.length];
212 for (int i = 0; i < a.length; i++)
214 result[i] = a[i] + b;
220 * returns true if two arrays are element wise within a tolerance
224 * @param rtol ~ relative tolerance
225 * @param atol ~ absolute tolerance
226 * @param equalNAN ~ whether NaN at the same position return true
230 public static boolean allClose(double[] a, double[] b, double rtol, double atol, boolean equalNAN)
232 boolean areEqual = true;
233 for (int i = 0; i < a.length; i++)
235 if (equalNAN && (Double.isNaN(a[i]) && Double.isNaN(b[i]))) // if equalNAN == true -> skip the NaN pair
239 if (Math.abs(a[i] - b[i]) > (atol + rtol * Math.abs(b[i]))) // check for the similarity condition -> if not met -> break and return false
249 * returns the index of the maximum and the maximum value of an array
255 public static int[] findMax(int[] a)
259 for (int i = 0; i < a.length; i++)
267 return new int[]{maxIndex, max};
271 * returns the dot product of two arrays
277 public static double dot(double[] a, double[] b)
279 if (a.length != b.length)
281 throw new IllegalArgumentException(String.format("Vectors do not have the same length (%d, %d)!", a.length, b.length));
285 for (int i = 0; i < a.length; i++)
293 * returns the euklidian norm of the vector
298 public static double norm(double[] v)
303 result += Math.pow(i, 2);
305 return Math.sqrt(result);
309 * returns the number of NaN in the vector
314 public static int countNaN(double[] v)
328 * recursively calculates the permutations of total n items with r items per combination
329 * according to n!/(n-r)! by only multiplying the relevant terms
333 * @return permutations
335 public static long permutations(int n, int r)
338 return permutations(r, n);
341 for (int i = 0; i < r; i++)
349 * calculate all unique combinations of n elements into r sized groups
355 public static int combinations(int n, int r)
358 for (int i = 0; i < r; i++)
362 return (int) (result / MiscMath.factorial(r));
366 * calculate the factorial of n (n >= 0)
371 public static int factorial(int n)
374 for (int i = 0; i < n; i++)