OpTime Gemv64 <M, N>(IEnumerable <double> src, int cycles, M m = default, N n = default) where M : ITypeNat, new() where N : ITypeNat, new() { var A = BlockMatrix.Alloc <M, N, double>(); var x = BlockVector.Alloc <N, double>(); var y = BlockVector.Alloc <M, double>(); var z = BlockVector.Alloc <M, double>(); var sw = stopwatch(false); for (var i = 0; i < cycles; i++) { src.StreamTo(A.Unsized); src.StreamTo(x.Unsized); src.StreamTo(y.Unsized); sw.Start(); mkl.gemv(A, x, ref y); sw.Stop(); refmul(A, x, z); Claim.yea(z == y); } var label = $"gemv<{nati<M>()},{nati<N>()},{PrimalKinds.kind<double>()}>"; return(optime(cycles, sw, label)); }
OpTime gemm_direct_check <M, K, N>(IEnumerable <double> src, M m = default, K k = default, N n = default) where M : ITypeNat, new() where K : ITypeNat, new() where N : ITypeNat, new() { var A = BlockMatrix.Alloc <M, K, double>(); var B = BlockMatrix.Alloc <K, N, double>(); var X = BlockMatrix.Alloc <M, N, double>(); var E = BlockMatrix.Alloc <M, N, double>(); var collect = false; var runtime = Duration.Zero; for (var i = 0; i < CycleCount; i++) { src.StreamTo(A.Unblocked); src.StreamTo(B.Unblocked); var sw = stopwatch(); mkl.gemm(A, B, ref X); runtime += snapshot(sw); Mul(A, B, ref E); Claim.yea(E == X); } var label = $"gemm<{nati<M>()},{nati<K>()},{nati<N>()}>"; var timing = optime(CycleCount, runtime, label); if (collect) { Collect(timing, 30); } return(timing); }
void GemmInt32Format() { var domain = closed(-32768, 32768); var n = n5; var m = n5; var m1 = Random.BlockMatrix(domain, m, n); var m2 = Random.BlockMatrix(domain, m, n); var m3 = BlockMatrix.Alloc(m, n, 0); var m4 = mkl.gemm(m1, m2, ref m3); }
/// <summary> /// Allocates a target matrix and populates it with the product of the operands /// </summary> /// <param name="A">The left matrix</param> /// <param name="B">The right matrix</param> /// <param name="M">The number of rows in A and C</param> /// <param name="N">The number of columns in B and C</param> /// <param name="K">The number of columns in A and rows in B</param> public static BlockMatrix <M, N, double> gemm <M, K, N>(BlockMatrix <M, K, double> A, BlockMatrix <K, N, double> B) where M : ITypeNat, new() where K : ITypeNat, new() where N : ITypeNat, new() { var m = nati <M>(); var k = nati <K>(); var n = nati <N>(); var lda = k; var ldb = n; var ldx = n; var X = BlockMatrix.Alloc <M, N, double>(); CBLAS.cblas_dgemm(RowMajor, NoTranspose, NoTranspose, m, n, k, 1.0f, ref head(A), lda, ref head(B), ldb, 0, ref head(X), ldx); return(X); }
void Getrf64 <M, N>() where M : ITypeNat, new() where N : ITypeNat, new() { var m = nati <M>(); var n = nati <N>(); var cells = m * n; Span <int> pivots = new int[math.max(m, n) * 2]; var A = RMat <M, N, double>(closed(1, 250.0)).Apply(x => x.Truncate()); var X = BlockMatrix.Alloc <M, N, double>(); mkl.getrf(A, pivots, ref X); X.Apply(x => x.Round(4)); }
OpTime gemm_check <M, K, N, T>(IEnumerable <T> src, T epsilon = default, M m = default, K k = default, N n = default, bool trace = false) where M : ITypeNat, new() where K : ITypeNat, new() where N : ITypeNat, new() where T : struct { var A = BlockMatrix.Alloc <M, K, T>(); var B = BlockMatrix.Alloc <K, N, T>(); var X = BlockMatrix.Alloc <M, N, T>(); var E = BlockMatrix.Alloc <M, N, T>(); var collect = false; var runtime = Duration.Zero; for (var i = 0; i < CycleCount; i++) { src.StreamTo(A.Unblocked); src.StreamTo(B.Unblocked); var sw = stopwatch(); mkl.gemm(A, B, ref X); runtime += snapshot(sw); MatMulRef.Mul(A, B, ref E); if (trace) { var padlen = Int32.MinValue.ToString().Length + 2; Trace($"X = {X.Format()}"); Trace($"E = {E.Format()}"); } E.Unblocked.ClaimEqual(X.Unblocked, epsilon); } var label = $"gemm<N{nati<M>()},N{nati<K>()},N{nati<N>()},{typeof(T).Name}>"; OpTime timing = optime(CycleCount, runtime, label); if (collect) { Collect(timing, 30); } return(timing); }