getInverse method

Array getInverse()

Implementation

Array getInverse() {
  assert(shape.item1 == shape.item2);

  var det = getDeterminent();
  if (det == 0) {
    throw 'This matrix is not inversible';
  }

  var m = shape.item1;
  var n = shape.item2; // mxn matrix

  var A = copy();
  var I = Array.identity(m);

  for (var j in range(end: n)) {
    var i0 = -1;
    var v0 = -1.0;

    for (var i = j; i != m; i++) {
      var k = A.getValue(Tuple2(i, j));
      if (k > v0) {
        i0 = i;
        v0 = k;
      }
    }

    var Aj = A.getRow(i0);
    A.values[i0] = A.values[j];
    A.values[j] = Aj;
    var Ij = I.getRow(i0);
    I.values[i0] = I.values[j];
    I.values[j] = Ij;

    var x = Aj[j];

    for (var k = j; k < n; ++k) {
      Aj[k] /= x;
    }
    for (var k = n - 1; k >= 0; k--) {
      Ij[k] /= x;
    }
    for (var i = m - 1; i >= 0; i--) {
      if (i != j) {
        var Ai = A.values[i];
        var Ii = I.values[i];
        var x = Ai[j];
        var k;

        for (k = j + 1; k != n; k++) {
          Ai[k] -= Aj[k] * x;
        }
        for (k = n - 1; k > 0; k--) {
          Ii[k] -= Ij[k] * x;
          --k;
          Ii[k] -= Ij[k] * x;
        }
        if (k == 0) Ii[0] -= Ij[0] * x;
      }
    }
  }

  return I;
}