Skip to content

Commit 2d27d1c

Browse files
authored
Explicit loop in converting Bidiagonal/Tridiagonal to Matrix (#1283)
This reduces TTFX. ```julia julia> using LinearAlgebra julia> T = Bidiagonal(ones(4), ones(3), :L); julia> @time Matrix(T); 0.073467 seconds (125.49 k allocations: 6.207 MiB, 99.83% compilation time) # nightly 0.042144 seconds (46.61 k allocations: 2.310 MiB, 99.65% compilation time) # this PR ``` ```julia julia> T = Tridiagonal(ones(3), ones(4), ones(3)); julia> @time Matrix(T); 0.077513 seconds (138.71 k allocations: 6.792 MiB, 99.85% compilation time) # master 0.034220 seconds (37.27 k allocations: 1.867 MiB, 99.58% compilation time) # this PR ``` Performance is identical, as it's entirely dominated by setting the matrix to zero.
1 parent 0671a7b commit 2d27d1c

File tree

2 files changed

+19
-5
lines changed

2 files changed

+19
-5
lines changed

src/bidiag.jl

Lines changed: 12 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -189,10 +189,20 @@ end
189189
#Converting from Bidiagonal to dense Matrix
190190
function Matrix{T}(A::Bidiagonal) where T
191191
B = Matrix{T}(undef, size(A))
192+
iszero(size(B,1)) && return B
192193
if haszero(T) # optimized path for types with zero(T) defined
193194
size(B,1) > 1 && fill!(B, zero(T))
194-
copyto!(diagview(B), A.dv)
195-
copyto!(diagview(B, _offdiagind(A.uplo)), A.ev)
195+
isupper = A.uplo == 'U'
196+
if isupper
197+
B[1,1] = A.dv[1]
198+
end
199+
for col in axes(A.ev,1)
200+
B[col+!isupper, col+isupper] = A.ev[col]
201+
B[col+isupper, col+isupper] = A.dv[col+isupper]
202+
end
203+
if !isupper
204+
B[end,end] = A.dv[end]
205+
end
196206
else
197207
copyto!(B, A)
198208
end

src/tridiag.jl

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -635,11 +635,15 @@ axes(M::Tridiagonal) = (ax = axes(M.d,1); (ax, ax))
635635

636636
function Matrix{T}(M::Tridiagonal) where {T}
637637
A = Matrix{T}(undef, size(M))
638+
iszero(size(A,1)) && return A
638639
if haszero(T) # optimized path for types with zero(T) defined
639640
size(A,1) > 2 && fill!(A, zero(T))
640-
copyto!(diagview(A), M.d)
641-
copyto!(diagview(A,1), M.du)
642-
copyto!(diagview(A,-1), M.dl)
641+
for i in axes(M.dl,1)
642+
A[i,i] = M.d[i]
643+
A[i+1,i] = M.dl[i]
644+
A[i,i+1] = M.du[i]
645+
end
646+
A[end,end] = M.d[end]
643647
else
644648
copyto!(A, M)
645649
end

0 commit comments

Comments
 (0)