1  public abstract class GenericMatrix<E extends Number> {
  2    /** Abstract method for adding two elements of the matrices */
  3    protected abstract E add(E o1, E o2);
  4  
  5    /** Abstract method for multiplying two elements of the matrices */
  6    protected abstract E multiply(E o1, E o2);
  7  
  8    /** Abstract method for defining zero for the matrix element */
  9    protected abstract E zero();
 10  
 11    /** Add two matrices */
 12    public E[][] addMatrix(E[][] matrix1, E[][] matrix2) {
 13      // Check bounds of the two matrices
 14      if ((matrix1.length != matrix2.length) ||
 15          (matrix1[0].length != matrix2[0].length)) {
 16        throw new RuntimeException(
 17          "The matrices do not have the same size");
 18      }
 19  
 20      E[][] result =
 21        (E[][])new Number[matrix1.length][matrix1[0].length];
 22  
 23      // Perform addition
 24      for (int i = 0; i < result.length; i++)
 25        for (int j = 0; j < result[i].length; j++) {
 26          result[i][j] = add(matrix1[i][j], matrix2[i][j]);
 27        }
 28  
 29      return result;
 30    }
 31  
 32    /** Multiply two matrices */
 33    public E[][] multiplyMatrix(E[][] matrix1, E[][] matrix2) {
 34      // Check bounds
 35      if (matrix1[0].length != matrix2.length) {
 36        throw new RuntimeException(
 37          "The matrices do not have compatible size");
 38      }
 39  
 40      // Create result matrix
 41      E[][] result =
 42        (E[][])new Number[matrix1.length][matrix2[0].length];
 43  
 44      // Perform multiplication of two matrices
 45      for (int i = 0; i < result.length; i++) {
 46        for (int j = 0; j < result[0].length; j++) {
 47          result[i][j] = zero();
 48  
 49          for (int k = 0; k < matrix1[0].length; k++) {
 50            result[i][j] = add(result[i][j],
 51              multiply(matrix1[i][k], matrix2[k][j]));
 52          }
 53        }
 54      }
 55  
 56      return result;
 57    }
 58  
 59    /** Print matrices, the operator, and their operation result */
 60    public static void printResult(
 61        Number[][] m1, Number[][] m2, Number[][] m3, char op) {
 62      for (int i = 0; i < m1.length; i++) {
 63        for (int j = 0; j < m1[0].length; j++)
 64          System.out.print(" " + m1[i][j]);
 65  
 66        if (i == m1.length / 2)
 67          System.out.print("  " + op + "  ");
 68        else
 69          System.out.print("     ");
 70  
 71        for (int j = 0; j < m2.length; j++)
 72          System.out.print(" " + m2[i][j]);
 73  
 74        if (i == m1.length / 2)
 75          System.out.print("  =  ");
 76        else
 77          System.out.print("     ");
 78  
 79        for (int j = 0; j < m3.length; j++)
 80          System.out.print(m3[i][j] + " ");
 81  
 82        System.out.println();
 83      }
 84    }
 85  }