public function strassenMultiply(LL_Matrix $matrix)
 {
     if ($this->columns() != $matrix->rows()) {
         // impossible operation.
         return false;
     }
     if ($this->columns() < 32) {
         return $this->naiveMultiply($matrix);
     }
     // get these from $this.
     $subdivisions = $this->subdivide($this, 2, 2);
     if ($subdivisions === false) {
         return $this->naiveMultiply($matrix);
     }
     $a11 = new LL_Matrix($subdivisions[0][0]);
     $a12 = new LL_Matrix($subdivisions[0][1]);
     $a21 = new LL_Matrix($subdivisions[1][0]);
     $a22 = new LL_Matrix($subdivisions[1][1]);
     // get these from $matrix
     $subdivisions = $this->subdivide($matrix, 2, 2);
     if ($subdivisions === false) {
         // fall back on naïve if even subdivide isn't possible.
         return $this->naiveMultiply($matrix);
     }
     $b11 = new LL_Matrix($subdivisions[0][0]);
     $b12 = new LL_Matrix($subdivisions[0][1]);
     $b21 = new LL_Matrix($subdivisions[1][0]);
     $b22 = new LL_Matrix($subdivisions[1][1]);
     // intermediaries
     /*
       M1 = (A11 + A22) (B11 + B22)
       M2 = (A21 + A22) B11
       M3 = A11 (B12 – B22)
       M4 = A22 (B21 – B11)
       M5 = (A11 + A12) B22
       M6 = (A21 – A11) (B11 + B12) M7 = (A12 – A22) (B21 + B22)
     */
     $m1_1 = $a11->add($a22);
     $m1_2 = $b11->add($b22);
     $m1 = $m1_1->strassenMultiply($m1_2);
     unset($m1_1);
     unset($m1_2);
     $m2_1 = $a21->add($a22);
     $m2 = $m2_1->strassenMultiply($b11);
     unset($m2_1);
     $m3_1 = $b12->subtract($b22);
     $m3 = $a11->strassenMultiply($m3_1);
     unset($m3_1);
     $m4_1 = $b21->subtract($b11);
     $m4 = $a22->strassenMultiply($m4_1);
     $m5_1 = $a11->add($a12);
     $m5 = $m5_1->strassenMultiply($b22);
     $m6_1 = $a21->subtract($a11);
     $m6_2 = $b11->add($b12);
     $m6 = $m6_1->strassenMultiply($m6_2);
     $m7_1 = $a12->add($a22);
     $m7_2 = $b21->add($b22);
     $m7 = $m7_1->strassenMultiply($m7_2);
     // result
     $c11 = $m1->add($m1);
     $c11 = $c11->add($m4);
     $c11 = $c11->subtract($m5);
     $c11 = $c11->add($m7);
     $c12 = $m3->add($m5);
     $c21 = $m2->add($m4);
     $c22 = $m1->subtract($m2);
     $c22 = $c22->add($m3);
     $c22 = $c22->add($m6);
     $result = array(array($c11, $c12), array($c21, $c22));
     return $this->rebuild($result);
 }