@@ -379,6 +379,26 @@ function rmul!(T::Tridiagonal, D::Diagonal)
379379 end
380380 return T
381381end
382+ for T in [:UpperTriangular , :UnitUpperTriangular ,
383+ :LowerTriangular , :UnitLowerTriangular ]
384+ @eval rmul! (A:: $T{<:Any, <:StridedMatrix} , D:: Diagonal ) = _rmul! (A, D)
385+ @eval lmul! (D:: Diagonal , A:: $T{<:Any, <:StridedMatrix} ) = _lmul! (D, A)
386+ end
387+ function _rmul! (A:: UpperOrLowerTriangular , D:: Diagonal )
388+ P = parent (A)
389+ isunit = A isa UnitUpperOrUnitLowerTriangular
390+ isupper = A isa UpperOrUnitUpperTriangular
391+ for col in axes (A,2 )
392+ rowstart = isupper ? firstindex (A,1 ) : col+ isunit
393+ rowstop = isupper ? col- isunit : lastindex (A,1 )
394+ for row in rowstart: rowstop
395+ P[row, col] *= D. diag[col]
396+ end
397+ end
398+ isunit && _setdiag! (P, identity, D. diag)
399+ TriWrapper = isupper ? UpperTriangular : LowerTriangular
400+ return TriWrapper (P)
401+ end
382402
383403function lmul! (D:: Diagonal , B:: AbstractVecOrMat )
384404 matmul_size_check (size (D), size (B))
@@ -388,6 +408,13 @@ function lmul!(D::Diagonal, B::AbstractVecOrMat)
388408 end
389409 return B
390410end
411+ # A' = D * A' => A = A * D'
412+ # This uses the fact that D' is a Diagonal
413+ function lmul! (D:: Diagonal , A:: AdjOrTransAbsMat )
414+ f = wrapperop (A)
415+ rmul! (f (A), f (D))
416+ A
417+ end
391418
392419# in-place multiplication with a diagonal
393420# T .= D * T
@@ -402,12 +429,20 @@ function lmul!(D::Diagonal, T::Tridiagonal)
402429 end
403430 return T
404431end
405- # A' = D * A' => A = A * D'
406- # This uses the fact that D' is a Diagonal
407- function lmul! (D:: Diagonal , A:: AdjOrTransAbsMat )
408- f = wrapperop (A)
409- rmul! (f (A), f (D))
410- A
432+ function _lmul! (D:: Diagonal , A:: UpperOrLowerTriangular )
433+ P = parent (A)
434+ isunit = A isa UnitUpperOrUnitLowerTriangular
435+ isupper = A isa UpperOrUnitUpperTriangular
436+ for col in axes (A,2 )
437+ rowstart = isupper ? firstindex (A,1 ) : col+ isunit
438+ rowstop = isupper ? col- isunit : lastindex (A,1 )
439+ for row in rowstart: rowstop
440+ P[row, col] = D. diag[row] * P[row, col]
441+ end
442+ end
443+ isunit && _setdiag! (P, identity, D. diag)
444+ TriWrapper = isupper ? UpperTriangular : LowerTriangular
445+ return TriWrapper (P)
411446end
412447
413448@inline function __muldiag_nonzeroalpha! (out, D:: Diagonal , B, alpha:: Number , beta:: Number )
0 commit comments