Skip to content

Commit cd1fe7e

Browse files
authored
Matrix-vector multiplication for compatible block sizes (#262)
* matrix-vector multiplication for compatible block sizes * _block_muladd for AbstractVector * use MatMulVecAdd alias * mul instead of muladd for block components
1 parent e359943 commit cd1fe7e

File tree

3 files changed

+34
-4
lines changed

3 files changed

+34
-4
lines changed

Project.toml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
name = "BlockArrays"
22
uuid = "8e7c35d0-a365-5155-bbbb-fb81a777f24e"
3-
version = "0.16.28"
3+
version = "0.16.29"
44

55
[deps]
66
ArrayLayouts = "4c555306-a7a7-4459-81d9-ec55ddd5c99a"

src/blocklinalg.jl

Lines changed: 19 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -199,10 +199,18 @@ function materialize!(M::MatMulVecAdd{<:AbstractBlockLayout,<:AbstractStridedLay
199199
y_in
200200
end
201201

202-
function _block_muladd!(α, A, X, β, Y)
202+
@inline function _block_muladd!(α, A, X::AbstractVector, β, Y::AbstractVector)
203+
_fill_lmul!(β, Y)
204+
for N = blockcolsupport(X), K = blockcolsupport(A,N)
205+
mul!(view(Y,K), view(A,K,N), view(X,N), α, one(β))
206+
end
207+
Y
208+
end
209+
210+
@inline function _block_muladd!(α, A, X, β, Y)
203211
_fill_lmul!(β, Y)
204212
for J = blockaxes(X,2), N = blockcolsupport(X,J), K = blockcolsupport(A,N)
205-
muladd!(α, view(A,K,N), view(X,N,J), one(α), view(Y,K,J))
213+
mul!(view(Y,K,J), view(A,K,N), view(X,N,J), α, one))
206214
end
207215
Y
208216
end
@@ -211,7 +219,7 @@ mul_blockscompatible(A, B, C) = blockisequal(axes(A,2), axes(B,1)) &&
211219
blockisequal(axes(A,1), axes(C,1)) &&
212220
blockisequal(axes(B,2), axes(C,2))
213221

214-
function materialize!(M::MatMulMatAdd{<:AbstractBlockLayout,<:AbstractBlockLayout,<:AbstractBlockLayout})
222+
@inline function _matmul(M)
215223
α, A, B, β, C = M.α, M.A, M.B, M.β, M.C
216224
if mul_blockscompatible(A,B,C)
217225
_block_muladd!(α, A, B, β, C)
@@ -220,6 +228,14 @@ function materialize!(M::MatMulMatAdd{<:AbstractBlockLayout,<:AbstractBlockLayou
220228
end
221229
end
222230

231+
function materialize!(M::MatMulMatAdd{<:AbstractBlockLayout,<:AbstractBlockLayout,<:AbstractBlockLayout})
232+
_matmul(M)
233+
end
234+
235+
function materialize!(M::MatMulVecAdd{<:AbstractBlockLayout, <:AbstractBlockLayout, <:AbstractBlockLayout})
236+
_matmul(M)
237+
end
238+
223239
function materialize!(M::MatMulMatAdd{<:AbstractBlockLayout,<:AbstractBlockLayout,<:AbstractColumnMajor})
224240
α, A, X, β, Y_in = M.α, M.A, M.B, M.β, M.C
225241
Y = PseudoBlockArray(Y_in, (axes(A,1), axes(X,2)))

test/test_blocklinalg.jl

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -92,6 +92,20 @@ import ArrayLayouts: DenseRowMajor, ColumnMajor, StridedLayout
9292
Matrix(A)*PseudoBlockArray(B) .=== Matrix(A)*Matrix(B))
9393
end
9494

95+
@testset "BlockMatrix * BlockVector" begin
96+
A = BlockArray(randn(6,6), fill(2,3), 1:3)
97+
v = BlockArray(rand(6), 1:3)
98+
w = A * v
99+
@test w isa BlockArray
100+
@test blocksizes(w,1) == fill(2, 3)
101+
@test w Array(A) * v A * Array(v) Array(A) * Array(v)
102+
103+
z = A * w
104+
@test z isa BlockArray
105+
@test blocksizes(z,1) == fill(2, 3)
106+
@test z Array(A) * w A * Array(w) Array(A) * Array(w)
107+
end
108+
95109
@testset "adjoint" begin
96110
A = BlockArray(randn(6,6), fill(2,3), 1:3)
97111
B = BlockArray(randn(6,6), 1:3, 1:3)

0 commit comments

Comments
 (0)