Skip to content

Commit c28dc85

Browse files
committed
Materialize complex Symmetric matrices in eigen (#55348)
1 parent 8ca7e1e commit c28dc85

File tree

4 files changed

+23
-6
lines changed

4 files changed

+23
-6
lines changed

stdlib/LinearAlgebra/src/bunchkaufman.jl

+9-6
Original file line numberDiff line numberDiff line change
@@ -127,6 +127,9 @@ function bunchkaufman!(A::StridedMatrix{<:BlasFloat}, rook::Bool = false; check:
127127
end
128128
end
129129

130+
bkcopy_oftype(A, S) = eigencopy_oftype(A, S)
131+
bkcopy_oftype(A::Symmetric{<:Complex}, S) = Symmetric(copytrito!(similar(parent(A), S, size(A)), A.data, A.uplo), sym_uplo(A.uplo))
132+
130133
"""
131134
bunchkaufman(A, rook::Bool=false; check = true) -> S::BunchKaufman
132135
@@ -206,7 +209,7 @@ julia> S.L*S.D*S.L' - A[S.p, S.p]
206209
```
207210
"""
208211
bunchkaufman(A::AbstractMatrix{T}, rook::Bool=false; check::Bool = true) where {T} =
209-
bunchkaufman!(eigencopy_oftype(A, typeof(sqrt(oneunit(T)))), rook; check = check)
212+
bunchkaufman!(bkcopy_oftype(A, typeof(sqrt(oneunit(T)))), rook; check = check)
210213

211214
BunchKaufman{T}(B::BunchKaufman) where {T} =
212215
BunchKaufman(convert(Matrix{T}, B.LD), B.ipiv, B.uplo, B.symmetric, B.rook, B.info)
@@ -1529,7 +1532,7 @@ function bunchkaufman(A::AbstractMatrix{TS},
15291532
rook::Bool = false;
15301533
check::Bool = true
15311534
) where TS <: ClosedScalar{TR} where TR <: ClosedReal
1532-
return bunchkaufman!(eigencopy_oftype(A, TS), rook; check)
1535+
return bunchkaufman!(bkcopy_oftype(A, TS), rook; check)
15331536
end
15341537

15351538
function bunchkaufman(A::AbstractMatrix{TS},
@@ -1551,15 +1554,15 @@ function bunchkaufman(A::AbstractMatrix{TS},
15511554
# We promote input to BigInt to avoid overflow problems
15521555
if TA == Nothing
15531556
if TS <: Integer
1554-
M = Rational{BigInt}.(eigencopy_oftype(A, TS))
1557+
M = Rational{BigInt}.(bkcopy_oftype(A, TS))
15551558
else
1556-
M = Complex{Rational{BigInt}}.(eigencopy_oftype(A, TS))
1559+
M = Complex{Rational{BigInt}}.(bkcopy_oftype(A, TS))
15571560
end
15581561
else
15591562
if TS <: Integer
1560-
M = TA(Rational{BigInt}.(eigencopy_oftype(A, TS)), Symbol(A.uplo))
1563+
M = TA(Rational{BigInt}.(bkcopy_oftype(A, TS)), Symbol(A.uplo))
15611564
else
1562-
M = TA(Complex{Rational{BigInt}}.(eigencopy_oftype(A, TS)),
1565+
M = TA(Complex{Rational{BigInt}}.(bkcopy_oftype(A, TS)),
15631566
Symbol(A.uplo))
15641567
end
15651568
end

stdlib/LinearAlgebra/src/symmetriceigen.jl

+1
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@
33
# preserve HermOrSym wrapper
44
eigencopy_oftype(A::Hermitian, S) = Hermitian(copy_similar(A, S), sym_uplo(A.uplo))
55
eigencopy_oftype(A::Symmetric, S) = Symmetric(copy_similar(A, S), sym_uplo(A.uplo))
6+
eigencopy_oftype(A::Symmetric{<:Complex}, S) = copyto!(similar(parent(A), S), A)
67

78
# Eigensolvers for symmetric and Hermitian matrices
89
eigen!(A::RealHermSymComplexHerm{<:BlasReal,<:StridedMatrix}; sortby::Union{Function,Nothing}=nothing) =

stdlib/LinearAlgebra/test/hessenberg.jl

+7
Original file line numberDiff line numberDiff line change
@@ -250,4 +250,11 @@ end
250250
@test axes(S) === (r,r)
251251
end
252252

253+
@testset "complex Symmetric" begin
254+
D = diagm(0=>ComplexF64[1,2])
255+
S = Symmetric(D)
256+
H = hessenberg(S)
257+
@test H.H == D
258+
end
259+
253260
end # module TestHessenberg

stdlib/LinearAlgebra/test/symmetriceigen.jl

+6
Original file line numberDiff line numberDiff line change
@@ -151,4 +151,10 @@ end
151151
@test HT * V V * Diagonal(λ)
152152
end
153153

154+
@testset "complex Symmetric" begin
155+
S = Symmetric(rand(ComplexF64,2,2))
156+
λ, v = eigen(S)
157+
@test S * v v * Diagonal(λ)
158+
end
159+
154160
end # module TestSymmetricEigen

0 commit comments

Comments
 (0)