func TestMatMul(t *testing.T) { const ( m = 3 k = 4 n = 5 ) alpha := rand.NormFloat64() a, b := randMat(m, k), randMat(k, n) got := blas.MatMul(alpha, a, b) want := mat.Scale(alpha, mat.Mul(a, b)) checkEqualMat(t, want, got, 1e-9) // Try with non-copying transposes. alpha = rand.NormFloat64() a, b = randMat(k, m).T(), randMat(k, n) got = blas.MatMul(alpha, a, b) want = mat.Scale(alpha, mat.Mul(a, b)) checkEqualMat(t, want, got, 1e-9) alpha = rand.NormFloat64() a, b = randMat(m, k), randMat(n, k).T() got = blas.MatMul(alpha, a, b) want = mat.Scale(alpha, mat.Mul(a, b)) checkEqualMat(t, want, got, 1e-9) alpha = rand.NormFloat64() a, b = randMat(k, m).T(), randMat(n, k).T() got = blas.MatMul(alpha, a, b) want = mat.Scale(alpha, mat.Mul(a, b)) checkEqualMat(t, want, got, 1e-9) }
func TestEigSymm(t *testing.T) { n := 100 a := randMat(n, n) a = mat.Plus(a, mat.T(a)) // Take eigen decomposition. v, d, err := EigSymm(a) if err != nil { t.Fatal(err) } got := mat.Mul(mat.Mul(v, mat.NewDiag(d)), mat.T(v)) testMatEq(t, a, got) }
func TestSVD(t *testing.T) { m, n := 150, 100 want := randMat(m, n) // Take singular value decomposition. u, s, vt, err := SVD(want) if err != nil { t.Fatal(err) } // Check that A = U S V'. got := mat.Mul(u, mat.Mul(mat.NewDiag(s), vt)) testMatEq(t, want, got) }
func ExampleInvertPosDef() { // A = V' V, with V = [1, 1; 2, 1] v := mat.NewRows([][]float64{ {1, 1}, {2, 1}, }) a := mat.Mul(mat.T(v), v) b, err := InvertPosDef(a) if err != nil { fmt.Println(err) return } for j := 0; j < 2; j++ { for i := 0; i < 2; i++ { if i > 0 { fmt.Printf(" ") } fmt.Printf("%.3g", b.At(i, j)) } fmt.Println() } // Output: // 2 -3 // -3 5 }
func ExampleCholFact_Solve() { // A = V' V, with V = [1, 1; 2, 1] v := mat.NewRows([][]float64{ {1, 1}, {2, 1}, }) a := mat.Mul(mat.T(v), v) // x = [1; 2] // b = V' V x // = V' [1, 1; 2, 1] [1; 2] // = [1, 2; 1, 1] [3; 4] // = [11; 7] b := []float64{11, 7} chol, err := Chol(a) if err != nil { fmt.Println(err) return } x, err := chol.Solve(b) if err != nil { fmt.Println(err) return } fmt.Printf("%.6g", x) // Output: // [1 2] }
func TestSVD_vsEig(t *testing.T) { m, n := 150, 100 a := randMat(m, n) g := mat.Mul(mat.T(a), a) // Take eigen decomposition of Gram matrix. _, eigs, err := EigSymm(g) if err != nil { t.Fatal(err) } // Sort in descending order. sort.Sort(sort.Reverse(sort.Float64Slice(eigs))) // Take square root of eigenvalues. for i := range eigs { // Clip small negative values to zero. eigs[i] = math.Sqrt(math.Max(0, eigs[i])) } // Take singular value decomposition. _, svals, _, err := SVD(a) if err != nil { t.Fatal(err) } testSliceEq(t, eigs, svals) }
func benchmarkMatMul(b *testing.B, m, k, n int, naive bool) { x, y := randMat(m, k), randMat(k, n) b.ResetTimer() for i := 0; i < b.N; i++ { if naive { mat.Mul(x, y) } else { blas.MatMul(1, x, y) } } }
func TestGenMatMul(t *testing.T) { const ( m = 3 k = 4 n = 5 ) alpha, beta := rand.NormFloat64(), rand.NormFloat64() a, b, c := randMat(m, k), randMat(k, n), randMat(m, n) want := mat.Plus(mat.Scale(alpha, mat.Mul(a, b)), mat.Scale(beta, c)) // Over-write c with result. blas.GenMatMul(alpha, a, b, beta, c) checkEqualMat(t, want, c, 1e-9) }
func TestSolvePosDef(t *testing.T) { n := 100 // Random symmetric positive definite matrix. a := randMat(2*n, n) a = mat.Mul(mat.T(a), a) // Random vector. want := randVec(n) b := mat.MulVec(a, want) got, err := SolvePosDef(a, b) if err != nil { t.Fatal(err) } testSliceEq(t, want, got) }
func overDetProb(m, n int) (a *mat.Mat, b, x []float64, err error) { if m < n { panic("expect m >= n") } a = randMat(m, n) b = randVec(m) // Compute pseudo-inverse explicitly. // y <- (A' A) \ b x, err = SolveSymm(mat.Mul(mat.T(a), a), mat.MulVec(mat.T(a), b)) if err != nil { return nil, nil, nil, err } return }
func underDetProb(m, n int) (a *mat.Mat, b, x []float64, err error) { if m > n { panic("expect m <= n") } a = randMat(m, n) b = randVec(m) // Compute pseudo-inverse explicitly. // y <- (A A') \ b y, err := SolveSymm(mat.Mul(a, mat.T(a)), b) if err != nil { return nil, nil, nil, err } // x <- A' y x = mat.MulVec(mat.T(a), y) return }
func TestCholFact_Solve(t *testing.T) { n := 100 // Random symmetric positive definite matrix. a := randMat(2*n, n) a = mat.Mul(mat.T(a), a) // Random vector. want := randVec(n) b := mat.MulVec(a, want) // Factorize matrix. chol, err := Chol(a) if err != nil { t.Fatal(err) } got, err := chol.Solve(b) if err != nil { t.Fatal(err) } testSliceEq(t, want, got) }