diff options
Diffstat (limited to 'lib')
-rw-r--r-- | lib/Numeric/LinearAlgebra/Algorithms.hs | 10 | ||||
-rw-r--r-- | lib/Numeric/LinearAlgebra/LAPACK.hs | 16 | ||||
-rw-r--r-- | lib/Numeric/LinearAlgebra/LAPACK/lapack-aux.c | 36 | ||||
-rw-r--r-- | lib/Numeric/LinearAlgebra/Tests.hs | 3 |
4 files changed, 62 insertions, 3 deletions
diff --git a/lib/Numeric/LinearAlgebra/Algorithms.hs b/lib/Numeric/LinearAlgebra/Algorithms.hs index 6b0fb08..0f2ccef 100644 --- a/lib/Numeric/LinearAlgebra/Algorithms.hs +++ b/lib/Numeric/LinearAlgebra/Algorithms.hs | |||
@@ -27,6 +27,7 @@ module Numeric.LinearAlgebra.Algorithms ( | |||
27 | -- * Linear Systems | 27 | -- * Linear Systems |
28 | linearSolve, | 28 | linearSolve, |
29 | luSolve, | 29 | luSolve, |
30 | cholSolve, | ||
30 | linearSolveLS, | 31 | linearSolveLS, |
31 | linearSolveSVD, | 32 | linearSolveSVD, |
32 | inv, pinv, | 33 | inv, pinv, |
@@ -91,6 +92,7 @@ class (Normed (Matrix t), Linear Vector t, Linear Matrix t) => Field t where | |||
91 | luPacked' :: Matrix t -> (Matrix t, [Int]) | 92 | luPacked' :: Matrix t -> (Matrix t, [Int]) |
92 | luSolve' :: (Matrix t, [Int]) -> Matrix t -> Matrix t | 93 | luSolve' :: (Matrix t, [Int]) -> Matrix t -> Matrix t |
93 | linearSolve' :: Matrix t -> Matrix t -> Matrix t | 94 | linearSolve' :: Matrix t -> Matrix t -> Matrix t |
95 | cholSolve' :: Matrix t -> Matrix t -> Matrix t | ||
94 | linearSolveSVD' :: Matrix t -> Matrix t -> Matrix t | 96 | linearSolveSVD' :: Matrix t -> Matrix t -> Matrix t |
95 | linearSolveLS' :: Matrix t -> Matrix t -> Matrix t | 97 | linearSolveLS' :: Matrix t -> Matrix t -> Matrix t |
96 | eig' :: Matrix t -> (Vector (Complex Double), Matrix (Complex Double)) | 98 | eig' :: Matrix t -> (Vector (Complex Double), Matrix (Complex Double)) |
@@ -112,6 +114,7 @@ instance Field Double where | |||
112 | luPacked' = luR | 114 | luPacked' = luR |
113 | luSolve' (l_u,perm) = lusR l_u perm | 115 | luSolve' (l_u,perm) = lusR l_u perm |
114 | linearSolve' = linearSolveR -- (luSolve . luPacked) ?? | 116 | linearSolve' = linearSolveR -- (luSolve . luPacked) ?? |
117 | cholSolve' = cholSolveR | ||
115 | linearSolveLS' = linearSolveLSR | 118 | linearSolveLS' = linearSolveLSR |
116 | linearSolveSVD' = linearSolveSVDR Nothing | 119 | linearSolveSVD' = linearSolveSVDR Nothing |
117 | ctrans' = trans | 120 | ctrans' = trans |
@@ -132,6 +135,7 @@ instance Field (Complex Double) where | |||
132 | luPacked' = luC | 135 | luPacked' = luC |
133 | luSolve' (l_u,perm) = lusC l_u perm | 136 | luSolve' (l_u,perm) = lusC l_u perm |
134 | linearSolve' = linearSolveC | 137 | linearSolve' = linearSolveC |
138 | cholSolve' = cholSolveC | ||
135 | linearSolveLS' = linearSolveLSC | 139 | linearSolveLS' = linearSolveLSC |
136 | linearSolveSVD' = linearSolveSVDC Nothing | 140 | linearSolveSVD' = linearSolveSVDC Nothing |
137 | ctrans' = conj . trans | 141 | ctrans' = conj . trans |
@@ -229,6 +233,10 @@ luSolve = luSolve' | |||
229 | linearSolve :: Field t => Matrix t -> Matrix t -> Matrix t | 233 | linearSolve :: Field t => Matrix t -> Matrix t -> Matrix t |
230 | linearSolve = linearSolve' | 234 | linearSolve = linearSolve' |
231 | 235 | ||
236 | -- | Solve a symmetric or Hermitian positive definite linear system using a precomputed Cholesky decomposition obtained by 'chol'. | ||
237 | cholSolve :: Field t => Matrix t -> Matrix t -> Matrix t | ||
238 | cholSolve = cholSolve' | ||
239 | |||
232 | -- | Minimum norm solution of a general linear least squares problem Ax=B using the SVD. Admits rank-deficient systems but it is slower than 'linearSolveLS'. The effective rank of A is determined by treating as zero those singular valures which are less than 'eps' times the largest singular value. | 240 | -- | Minimum norm solution of a general linear least squares problem Ax=B using the SVD. Admits rank-deficient systems but it is slower than 'linearSolveLS'. The effective rank of A is determined by treating as zero those singular valures which are less than 'eps' times the largest singular value. |
233 | linearSolveSVD :: Field t => Matrix t -> Matrix t -> Matrix t | 241 | linearSolveSVD :: Field t => Matrix t -> Matrix t -> Matrix t |
234 | linearSolveSVD = linearSolveSVD' | 242 | linearSolveSVD = linearSolveSVD' |
@@ -322,7 +330,7 @@ cholSH = cholSH' | |||
322 | 330 | ||
323 | -- | Cholesky factorization of a positive definite hermitian or symmetric matrix. | 331 | -- | Cholesky factorization of a positive definite hermitian or symmetric matrix. |
324 | -- | 332 | -- |
325 | -- If @c = chol m@ then @m == ctrans c \<> c@. | 333 | -- If @c = chol m@ then @c@ is upper triangular and @m == ctrans c \<> c@. |
326 | chol :: Field t => Matrix t -> Matrix t | 334 | chol :: Field t => Matrix t -> Matrix t |
327 | chol m | exactHermitian m = cholSH m | 335 | chol m | exactHermitian m = cholSH m |
328 | | otherwise = error "chol requires positive definite complex hermitian or real symmetric matrix" | 336 | | otherwise = error "chol requires positive definite complex hermitian or real symmetric matrix" |
diff --git a/lib/Numeric/LinearAlgebra/LAPACK.hs b/lib/Numeric/LinearAlgebra/LAPACK.hs index a1ac1cf..5d4eb0d 100644 --- a/lib/Numeric/LinearAlgebra/LAPACK.hs +++ b/lib/Numeric/LinearAlgebra/LAPACK.hs | |||
@@ -18,6 +18,7 @@ module Numeric.LinearAlgebra.LAPACK ( | |||
18 | -- * Linear systems | 18 | -- * Linear systems |
19 | linearSolveR, linearSolveC, | 19 | linearSolveR, linearSolveC, |
20 | lusR, lusC, | 20 | lusR, lusC, |
21 | cholSolveR, cholSolveC, | ||
21 | linearSolveLSR, linearSolveLSC, | 22 | linearSolveLSR, linearSolveLSC, |
22 | linearSolveSVDR, linearSolveSVDC, | 23 | linearSolveSVDR, linearSolveSVDC, |
23 | -- * SVD | 24 | -- * SVD |
@@ -312,8 +313,10 @@ eigOnlyH = vrev . fst. eigSHAux (zheev 1) "eigH'" . fmat | |||
312 | vrev = flatten . flipud . reshape 1 | 313 | vrev = flatten . flipud . reshape 1 |
313 | 314 | ||
314 | ----------------------------------------------------------------------------- | 315 | ----------------------------------------------------------------------------- |
315 | foreign import ccall "LAPACK/lapack-aux.h linearSolveR_l" dgesv :: TMMM | 316 | foreign import ccall "linearSolveR_l" dgesv :: TMMM |
316 | foreign import ccall "LAPACK/lapack-aux.h linearSolveC_l" zgesv :: TCMCMCM | 317 | foreign import ccall "linearSolveC_l" zgesv :: TCMCMCM |
318 | foreign import ccall "cholSolveR_l" dpotrs :: TMMM | ||
319 | foreign import ccall "cholSolveC_l" zpotrs :: TCMCMCM | ||
317 | 320 | ||
318 | linearSolveSQAux f st a b | 321 | linearSolveSQAux f st a b |
319 | | n1==n2 && n1==r = unsafePerformIO $ do | 322 | | n1==n2 && n1==r = unsafePerformIO $ do |
@@ -334,6 +337,15 @@ linearSolveR a b = linearSolveSQAux dgesv "linearSolveR" (fmat a) (fmat b) | |||
334 | linearSolveC :: Matrix (Complex Double) -> Matrix (Complex Double) -> Matrix (Complex Double) | 337 | linearSolveC :: Matrix (Complex Double) -> Matrix (Complex Double) -> Matrix (Complex Double) |
335 | linearSolveC a b = linearSolveSQAux zgesv "linearSolveC" (fmat a) (fmat b) | 338 | linearSolveC a b = linearSolveSQAux zgesv "linearSolveC" (fmat a) (fmat b) |
336 | 339 | ||
340 | |||
341 | -- | Solves a symmetric positive definite system of linear equations using a precomputed Cholesky factorization obtained by 'cholS'. | ||
342 | cholSolveR :: Matrix Double -> Matrix Double -> Matrix Double | ||
343 | cholSolveR a b = linearSolveSQAux dpotrs "cholSolveR" (fmat a) (fmat b) | ||
344 | |||
345 | -- | Solves a Hermitian positive definite system of linear equations using a precomputed Cholesky factorization obtained by 'cholH'. | ||
346 | cholSolveC :: Matrix (Complex Double) -> Matrix (Complex Double) -> Matrix (Complex Double) | ||
347 | cholSolveC a b = linearSolveSQAux zpotrs "cholSolveC" (fmat a) (fmat b) | ||
348 | |||
337 | ----------------------------------------------------------------------------------- | 349 | ----------------------------------------------------------------------------------- |
338 | foreign import ccall "LAPACK/lapack-aux.h linearSolveLSR_l" dgels :: TMMM | 350 | foreign import ccall "LAPACK/lapack-aux.h linearSolveLSR_l" dgels :: TMMM |
339 | foreign import ccall "LAPACK/lapack-aux.h linearSolveLSC_l" zgels :: TCMCMCM | 351 | foreign import ccall "LAPACK/lapack-aux.h linearSolveLSC_l" zgels :: TCMCMCM |
diff --git a/lib/Numeric/LinearAlgebra/LAPACK/lapack-aux.c b/lib/Numeric/LinearAlgebra/LAPACK/lapack-aux.c index 06c2479..fd840e3 100644 --- a/lib/Numeric/LinearAlgebra/LAPACK/lapack-aux.c +++ b/lib/Numeric/LinearAlgebra/LAPACK/lapack-aux.c | |||
@@ -492,6 +492,42 @@ int linearSolveC_l(KCMAT(a),KCMAT(b),CMAT(x)) { | |||
492 | OK | 492 | OK |
493 | } | 493 | } |
494 | 494 | ||
495 | //////// symmetric positive definite real linear system using Cholesky //////////// | ||
496 | |||
497 | int cholSolveR_l(KDMAT(a),KDMAT(b),DMAT(x)) { | ||
498 | integer n = ar; | ||
499 | integer nhrs = bc; | ||
500 | REQUIRES(n>=1 && ar==ac && ar==br,BAD_SIZE); | ||
501 | DEBUGMSG("cholSolveR_l"); | ||
502 | memcpy(xp,bp,n*nhrs*sizeof(double)); | ||
503 | integer res; | ||
504 | dpotrs_ ("U", | ||
505 | &n,&nhrs, | ||
506 | (double*)ap, &n, | ||
507 | xp, &n, | ||
508 | &res); | ||
509 | CHECK(res,res); | ||
510 | OK | ||
511 | } | ||
512 | |||
513 | //////// Hermitian positive definite real linear system using Cholesky //////////// | ||
514 | |||
515 | int cholSolveC_l(KCMAT(a),KCMAT(b),CMAT(x)) { | ||
516 | integer n = ar; | ||
517 | integer nhrs = bc; | ||
518 | REQUIRES(n>=1 && ar==ac && ar==br,BAD_SIZE); | ||
519 | DEBUGMSG("cholSolveC_l"); | ||
520 | memcpy(xp,bp,2*n*nhrs*sizeof(double)); | ||
521 | integer res; | ||
522 | zpotrs_ ("U", | ||
523 | &n,&nhrs, | ||
524 | (doublecomplex*)ap, &n, | ||
525 | (doublecomplex*)xp, &n, | ||
526 | &res); | ||
527 | CHECK(res,res); | ||
528 | OK | ||
529 | } | ||
530 | |||
495 | //////////////////// least squares real linear system //////////// | 531 | //////////////////// least squares real linear system //////////// |
496 | 532 | ||
497 | int linearSolveLSR_l(KDMAT(a),KDMAT(b),DMAT(x)) { | 533 | int linearSolveLSR_l(KDMAT(a),KDMAT(b),DMAT(x)) { |
diff --git a/lib/Numeric/LinearAlgebra/Tests.hs b/lib/Numeric/LinearAlgebra/Tests.hs index f8f8bd5..36efab6 100644 --- a/lib/Numeric/LinearAlgebra/Tests.hs +++ b/lib/Numeric/LinearAlgebra/Tests.hs | |||
@@ -208,6 +208,9 @@ runTests n = do | |||
208 | putStrLn "------ luSolve" | 208 | putStrLn "------ luSolve" |
209 | test (linearSolveProp (luSolve.luPacked) . rSqWC) | 209 | test (linearSolveProp (luSolve.luPacked) . rSqWC) |
210 | test (linearSolveProp (luSolve.luPacked) . cSqWC) | 210 | test (linearSolveProp (luSolve.luPacked) . cSqWC) |
211 | putStrLn "------ cholSolve" | ||
212 | test (linearSolveProp (cholSolve.chol) . rPosDef) | ||
213 | test (linearSolveProp (cholSolve.chol) . cPosDef) | ||
211 | putStrLn "------ luSolveLS" | 214 | putStrLn "------ luSolveLS" |
212 | test (linearSolveProp linearSolveLS . rSqWC) | 215 | test (linearSolveProp linearSolveLS . rSqWC) |
213 | test (linearSolveProp linearSolveLS . cSqWC) | 216 | test (linearSolveProp linearSolveLS . cSqWC) |