Skip to content

Commit a9c18ba

Browse files
committed
Merge pull request #8403 from JuliaLang/teh/cholesky
Use constants for BLAS chars (speed up Cholesky factorization of small matrices)
2 parents 65d1fad + 519a978 commit a9c18ba

File tree

5 files changed

+19
-9
lines changed

5 files changed

+19
-9
lines changed

base/linalg/bunchkaufman.jl

+4-4
Original file line numberDiff line numberDiff line change
@@ -11,12 +11,12 @@ end
1111

1212
function bkfact!{T<:BlasReal}(A::StridedMatrix{T}, uplo::Symbol=:U, symmetric::Bool=issym(A))
1313
symmetric || error("The Bunch-Kaufman decomposition is only valid for symmetric matrices")
14-
LD, ipiv = LAPACK.sytrf!(string(uplo)[1] , A)
15-
BunchKaufman(LD, ipiv, string(uplo)[1], symmetric)
14+
LD, ipiv = LAPACK.sytrf!(char_uplo(uplo) , A)
15+
BunchKaufman(LD, ipiv, char_uplo(uplo), symmetric)
1616
end
1717
function bkfact!{T<:BlasComplex}(A::StridedMatrix{T}, uplo::Symbol=:U, symmetric::Bool=issym(A))
18-
LD, ipiv = (symmetric ? LAPACK.sytrf! : LAPACK.hetrf!)(string(uplo)[1] , A)
19-
BunchKaufman(LD, ipiv, string(uplo)[1], symmetric)
18+
LD, ipiv = (symmetric ? LAPACK.sytrf! : LAPACK.hetrf!)(char_uplo(uplo) , A)
19+
BunchKaufman(LD, ipiv, char_uplo(uplo), symmetric)
2020
end
2121
bkfact{T<:BlasFloat}(A::StridedMatrix{T}, uplo::Symbol=:U, symmetric::Bool=issym(A)) = bkfact!(copy(A), uplo, symmetric)
2222
bkfact{T}(A::StridedMatrix{T}, uplo::Symbol=:U, symmetric::Bool=issym(A)) = bkfact!(convert(Matrix{promote_type(Float32,typeof(sqrt(one(T))))},A),uplo,symmetric)

base/linalg/cholesky.jl

+8-2
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,7 @@ immutable CholeskyPivoted{T} <: Factorization{T}
1414
end
1515

1616
function chol!{T<:BlasFloat}(A::StridedMatrix{T}, uplo::Symbol=:U)
17-
C, info = LAPACK.potrf!(string(uplo)[1], A)
17+
C, info = LAPACK.potrf!(char_uplo(uplo), A)
1818
return @assertposdef Triangular(C, uplo, false) info
1919
end
2020

@@ -57,7 +57,7 @@ function chol!{T}(A::AbstractMatrix{T}, uplo::Symbol=:U)
5757
end
5858

5959
function cholfact!{T<:BlasFloat}(A::StridedMatrix{T}, uplo::Symbol=:U; pivot=false, tol=0.0)
60-
uplochar = string(uplo)[1]
60+
uplochar = char_uplo(uplo)
6161
if pivot
6262
A, piv, rank, info = LAPACK.pstrf!(uplochar, A, tol)
6363
return CholeskyPivoted{T}(A, uplochar, piv, rank, tol, info)
@@ -66,6 +66,12 @@ function cholfact!{T<:BlasFloat}(A::StridedMatrix{T}, uplo::Symbol=:U; pivot=fal
6666
end
6767
cholfact!(A::AbstractMatrix, uplo::Symbol=:U) = Cholesky{eltype(A),typeof(A),uplo}(chol!(A, uplo).data)
6868

69+
function cholfact!{T<:BlasFloat,S,UpLo}(C::Cholesky{T,S,UpLo})
70+
_, info = LAPACK.potrf!(char_uplo(UpLo), C.UL)
71+
info[1]>0 && throw(PosDefException(info[1]))
72+
C
73+
end
74+
6975
cholfact{T<:BlasFloat}(A::StridedMatrix{T}, uplo::Symbol=:U; pivot=false, tol=0.0) = cholfact!(copy(A), uplo, pivot=pivot, tol=tol)
7076
function cholfact{T}(A::StridedMatrix{T}, uplo::Symbol=:U; pivot=false, tol=0.0)
7177
S = promote_type(typeof(chol(one(T))),Float32)

base/linalg/dense.jl

+1-1
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,7 @@ scale!{T<:BlasFloat}(X::Array{T}, s::Number) = scale!(X, convert(T, s))
2020
scale!{T<:BlasComplex}(X::Array{T}, s::Real) = BLAS.scal!(length(X), oftype(real(zero(T)),s), X, 1)
2121

2222
#Test whether a matrix is positive-definite
23-
isposdef!{T<:BlasFloat}(A::StridedMatrix{T}, UL::Symbol) = LAPACK.potrf!(string(UL)[1], A)[2] == 0
23+
isposdef!{T<:BlasFloat}(A::StridedMatrix{T}, UL::Symbol) = LAPACK.potrf!(char_uplo(UL), A)[2] == 0
2424
isposdef!(A::StridedMatrix) = ishermitian(A) && isposdef!(A, :U)
2525

2626
isposdef{T}(A::AbstractMatrix{T}, UL::Symbol) = (S = typeof(sqrt(one(T))); isposdef!(S == T ? copy(A) : convert(AbstractMatrix{S}, A), UL))

base/linalg/symmetric.jl

+2-2
Original file line numberDiff line numberDiff line change
@@ -3,12 +3,12 @@ immutable Symmetric{T,S<:AbstractMatrix{T}} <: AbstractMatrix{T}
33
data::S
44
uplo::Char
55
end
6-
Symmetric(A::AbstractMatrix, uplo::Symbol=:U) = (chksquare(A);Symmetric{eltype(A),typeof(A)}(A, string(uplo)[1]))
6+
Symmetric(A::AbstractMatrix, uplo::Symbol=:U) = (chksquare(A);Symmetric{eltype(A),typeof(A)}(A, char_uplo(uplo)))
77
immutable Hermitian{T,S<:AbstractMatrix{T}} <: AbstractMatrix{T}
88
data::S
99
uplo::Char
1010
end
11-
Hermitian(A::AbstractMatrix, uplo::Symbol=:U) = (chksquare(A);Hermitian{eltype(A),typeof(A)}(A, string(uplo)[1]))
11+
Hermitian(A::AbstractMatrix, uplo::Symbol=:U) = (chksquare(A);Hermitian{eltype(A),typeof(A)}(A, char_uplo(uplo)))
1212
typealias HermOrSym{T,S} Union(Hermitian{T,S}, Symmetric{T,S})
1313
typealias RealHermSymComplexHerm{T<:Real,S} Union(Hermitian{T,S}, Symmetric{T,S}, Hermitian{Complex{T},S})
1414

base/linalg/triangular.jl

+4
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,10 @@ function Triangular{T}(A::AbstractMatrix{T}, uplo::Symbol, isunit::Bool=false)
77
return Triangular{T,typeof(A),uplo,isunit}(A)
88
end
99

10+
const CHARU = 'U'
11+
const CHARL = 'L'
12+
char_uplo(uplo::Symbol) = uplo == :U ? CHARU : (uplo == :L ? CHARL : throw(ArgumentError("uplo argument must be either :U or :L")))
13+
1014
+{T, MT, uplo}(A::Triangular{T, MT, uplo, false}, B::Triangular{T, MT, uplo, false}) = Triangular(A.data + B.data, uplo)
1115
+{T, MT}(A::Triangular{T, MT, :U, false}, B::Triangular{T, MT, :U, true}) = Triangular(A.data + triu(B.data, 1) + I, :U)
1216
+{T, MT}(A::Triangular{T, MT, :L, false}, B::Triangular{T, MT, :L, true}) = Triangular(A.data + tril(B.data, -1) + I, :L)

0 commit comments

Comments
 (0)