Report a bug
If you spot a problem with this page, click here to create a GitHub issue.
Improve this page
Quickly fork, edit online, and submit a pull request for this page. Requires a signed-in GitHub account. This works well for small changes. If you'd like to make larger changes you may want to consider using a local clone.

mir.sparse.blas.gemm

Authors:
Ilya Yaroshenko
void gemm(CR, CL, SliceKind kind1, T1, I1, J1, SliceKind kind2, Iterator2, SliceKind kind3, Iterator3)(in CR alpha, Slice!(ChopIterator!(J1*, Series!(I1*, T1*)), 1, kind1) a, Slice!(Iterator2, 2, kind2) b, in CL beta, Slice!(Iterator3, 2, kind3) c);
General matrix-matrix multiplication.
Parameters:
CR alpha scalar
Slice!(ChopIterator!(J1*, Series!(I1*, T1*)), 1, kind1) a sparse matrix (CSR format)
Slice!(Iterator2, 2, kind2) b dense matrix
CL beta scalar
Slice!(Iterator3, 2, kind3) c dense matrix
Returns:
c = alpha * a × b + beta * c if beta does not equal null and c = alpha * a × b otherwise.
Examples:
import mir.ndslice;
import mir.sparse;

auto sp = sparse!int(3, 5);
sp[] =
    [[-5, 1, 7, 7, -4],
     [-1, -5, 6, 3, -3],
     [-5, -2, -3, 6, 0]];

auto a = sp.compress;

auto b = slice!double(5, 4);
b[] =
    [[-5.0, -3, 3, 1],
     [4.0, 3, 6, 4],
     [-4.0, -2, -2, 2],
     [-1.0, 9, 4, 8],
     [9.0, 8, 3, -2]];

auto c = slice!double(3, 4);

gemm(1.0, a, b, 0, c);

assert(c ==
    [[-42.0, 35, -7, 77],
     [-69.0, -21, -42, 21],
     [23.0, 69, 3, 29]]);
void gemtm(CR, CL, SliceKind kind1, T1, I1, J1, SliceKind kind2, Iterator2, SliceKind kind3, Iterator3)(in CR alpha, Slice!(ChopIterator!(J1*, Series!(I1*, T1*)), 1, kind1) a, Slice!(Iterator2, 2, kind2) b, in CL beta, Slice!(Iterator3, 2, kind3) c);
General matrix-matrix multiplication with transformation.
Parameters:
CR alpha scalar
Slice!(ChopIterator!(J1*, Series!(I1*, T1*)), 1, kind1) a sparse matrix (CSR format)
Slice!(Iterator2, 2, kind2) b dense matrix
CL beta scalar
Slice!(Iterator3, 2, kind3) c dense matrix
Returns:
c = alpha * aᵀ × b + beta * c if beta does not equal null and c = alpha * aᵀ × b otherwise.
Examples:
import mir.ndslice;
import mir.sparse;

auto sp = sparse!int(5, 3);
sp[] =
    [[-5, -1, -5],
     [1, -5, -2],
     [7, 6, -3],
     [7, 3, 6],
     [-4, -3, 0]];

auto a = sp.compress;

auto b = slice!double(5, 4);
b[] =
    [[-5.0, -3, 3, 1],
     [4.0, 3, 6, 4],
     [-4.0, -2, -2, 2],
     [-1.0, 9, 4, 8],
     [9.0, 8, 3, -2]];

auto c = slice!double(3, 4);

gemtm(1.0, a, b, 0, c);

assert(c ==
    [[-42.0, 35, -7, 77],
     [-69.0, -21, -42, 21],
     [23.0, 69, 3, 29]]);
void selectiveGemm(string op = "", SliceKind kind1, SliceKind kind2, SliceKind kind3, T, T3, I3, J3)(Slice!(T*, 2, kind1) a, Slice!(T*, 2, kind2) b, Slice!(ChopIterator!(J3*, Series!(I3*, T3*)), 1, kind3) c);
Selective general matrix multiplication with selector sparse matrix.
Parameters:
Slice!(T*, 2, kind1) a dense matrix
Slice!(T*, 2, kind2) b dense matrix
Slice!(ChopIterator!(J3*, Series!(I3*, T3*)), 1, kind3) c sparse matrix (CSR format)
Returns:
c[available indexes] <op>= (a × b)[available indexes].
Examples:
import mir.ndslice;
import mir.sparse;

auto a = slice!double(3, 5);
a[] =
    [[-5, 1, 7, 7, -4],
     [-1, -5, 6, 3, -3],
     [-5, -2, -3, 6, 0]];

auto b = slice!double(5, 4);
b[] =
    [[-5.0, -3, 3, 1],
     [4.0, 3, 6, 4],
     [-4.0, -2, -2, 2],
     [-1.0, 9, 4, 8],
     [9.0, 8, 3, -2]];

// a * b ==
//    [[-42.0, 35, -7, 77],
//     [-69.0, -21, -42, 21],
//     [23.0, 69, 3, 29]]);

auto cs = sparse!double(3, 4);
cs[0, 2] = 1;
cs[0, 1] = 3;
cs[2, 3] = 2;

auto c = cs.compress;

selectiveGemm!"*"(a, b, c);
assert(c.length == 3);
assert(c[0].index == [1, 2]);
assert(c[0].value == [105, -7]);
assert(c[1].empty);
assert(c[2].index == [3]);
assert(c[2].value == [58]);