{-# OPTIONS_GHC -fno-warn-missing-signatures #-}
{-# OPTIONS_GHC -fno-warn-unused-top-binds #-}
module Numeric.GSL.LinearAlgebra (
RandDist(..), randomVector,
saveMatrix,
fwriteVector, freadVector, fprintfVector, fscanfVector,
fileDimensions, loadMatrix, fromFile
) where
import Numeric.LinearAlgebra.HMatrix hiding (RandDist,randomVector,saveMatrix,loadMatrix)
import Numeric.GSL.Internal hiding (TV,TM,TCV,TCM)
import Foreign.Marshal.Alloc(free)
import Foreign.Ptr(Ptr)
import Foreign.C.Types
import Foreign.C.String(newCString)
import System.IO.Unsafe(unsafePerformIO)
import System.Process(readProcess)
fromei :: a -> CInt
fromei a
x = Int -> CInt
forall a b. (Integral a, Num b) => a -> b
fromIntegral (a -> Int
forall a. Enum a => a -> Int
fromEnum a
x) :: CInt
data RandDist = Uniform
| Gaussian
deriving Int -> RandDist
RandDist -> Int
RandDist -> [RandDist]
RandDist -> RandDist
RandDist -> RandDist -> [RandDist]
RandDist -> RandDist -> RandDist -> [RandDist]
(RandDist -> RandDist)
-> (RandDist -> RandDist)
-> (Int -> RandDist)
-> (RandDist -> Int)
-> (RandDist -> [RandDist])
-> (RandDist -> RandDist -> [RandDist])
-> (RandDist -> RandDist -> [RandDist])
-> (RandDist -> RandDist -> RandDist -> [RandDist])
-> Enum RandDist
forall a.
(a -> a)
-> (a -> a)
-> (Int -> a)
-> (a -> Int)
-> (a -> [a])
-> (a -> a -> [a])
-> (a -> a -> [a])
-> (a -> a -> a -> [a])
-> Enum a
enumFromThenTo :: RandDist -> RandDist -> RandDist -> [RandDist]
$cenumFromThenTo :: RandDist -> RandDist -> RandDist -> [RandDist]
enumFromTo :: RandDist -> RandDist -> [RandDist]
$cenumFromTo :: RandDist -> RandDist -> [RandDist]
enumFromThen :: RandDist -> RandDist -> [RandDist]
$cenumFromThen :: RandDist -> RandDist -> [RandDist]
enumFrom :: RandDist -> [RandDist]
$cenumFrom :: RandDist -> [RandDist]
fromEnum :: RandDist -> Int
$cfromEnum :: RandDist -> Int
toEnum :: Int -> RandDist
$ctoEnum :: Int -> RandDist
pred :: RandDist -> RandDist
$cpred :: RandDist -> RandDist
succ :: RandDist -> RandDist
$csucc :: RandDist -> RandDist
Enum
randomVector :: Int
-> RandDist
-> Int
-> Vector Double
randomVector :: Int -> RandDist -> Int -> Vector Double
randomVector Int
seed RandDist
dist Int
n = IO (Vector Double) -> Vector Double
forall a. IO a -> a
unsafePerformIO (IO (Vector Double) -> Vector Double)
-> IO (Vector Double) -> Vector Double
forall a b. (a -> b) -> a -> b
$ do
Vector Double
r <- Int -> IO (Vector Double)
forall a. Storable a => Int -> IO (Vector a)
createVector Int
n
(Vector Double
r Vector Double
-> (IO CInt -> IO CInt)
-> TransRaw (Vector Double) (IO CInt)
-> IO CInt
forall c b r.
TransArray c =>
c -> (b -> IO r) -> TransRaw c b -> IO r
`applyRaw` IO CInt -> IO CInt
forall a. a -> a
id) (CInt -> CInt -> TV
c_random_vector (Int -> CInt
fi Int
seed) ((Int -> CInt
fi(Int -> CInt) -> (RandDist -> Int) -> RandDist -> CInt
forall b c a. (b -> c) -> (a -> b) -> a -> c
.RandDist -> Int
forall a. Enum a => a -> Int
fromEnum) RandDist
dist)) IO CInt -> String -> IO ()
#|String
"randomVector"
Vector Double -> IO (Vector Double)
forall (m :: * -> *) a. Monad m => a -> m a
return Vector Double
r
foreign import ccall unsafe "random_vector" c_random_vector :: CInt -> CInt -> TV
saveMatrix :: FilePath
-> String
-> Matrix Double
-> IO ()
saveMatrix :: String -> String -> Matrix Double -> IO ()
saveMatrix String
filename String
fmt Matrix Double
m = do
CString
charname <- String -> IO CString
newCString String
filename
CString
charfmt <- String -> IO CString
newCString String
fmt
let o :: CInt
o = if Matrix Double -> MatrixOrder
forall t. Matrix t -> MatrixOrder
orderOf Matrix Double
m MatrixOrder -> MatrixOrder -> Bool
forall a. Eq a => a -> a -> Bool
== MatrixOrder
RowMajor then CInt
1 else CInt
0
(Matrix Double
m Matrix Double
-> (IO CInt -> IO CInt)
-> TransRaw (Matrix Double) (IO CInt)
-> IO CInt
forall c b r.
TransArray c =>
c -> (b -> IO r) -> TransRaw c b -> IO r
`applyRaw` IO CInt -> IO CInt
forall a. a -> a
id) (CString -> CString -> CInt -> CInt -> TV
matrix_fprintf CString
charname CString
charfmt CInt
o) IO CInt -> String -> IO ()
#|String
"matrix_fprintf"
CString -> IO ()
forall a. Ptr a -> IO ()
free CString
charname
CString -> IO ()
forall a. Ptr a -> IO ()
free CString
charfmt
foreign import ccall unsafe "matrix_fprintf" matrix_fprintf :: Ptr CChar -> Ptr CChar -> CInt -> TM
fscanfVector :: FilePath -> Int -> IO (Vector Double)
fscanfVector :: String -> Int -> IO (Vector Double)
fscanfVector String
filename Int
n = do
CString
charname <- String -> IO CString
newCString String
filename
Vector Double
res <- Int -> IO (Vector Double)
forall a. Storable a => Int -> IO (Vector a)
createVector Int
n
(Vector Double
res Vector Double
-> (IO CInt -> IO CInt)
-> TransRaw (Vector Double) (IO CInt)
-> IO CInt
forall c b r.
TransArray c =>
c -> (b -> IO r) -> TransRaw c b -> IO r
`applyRaw` IO CInt -> IO CInt
forall a. a -> a
id) (CString -> TV
gsl_vector_fscanf CString
charname) IO CInt -> String -> IO ()
#|String
"gsl_vector_fscanf"
CString -> IO ()
forall a. Ptr a -> IO ()
free CString
charname
Vector Double -> IO (Vector Double)
forall (m :: * -> *) a. Monad m => a -> m a
return Vector Double
res
foreign import ccall unsafe "vector_fscanf" gsl_vector_fscanf:: Ptr CChar -> TV
fprintfVector :: FilePath -> String -> Vector Double -> IO ()
fprintfVector :: String -> String -> Vector Double -> IO ()
fprintfVector String
filename String
fmt Vector Double
v = do
CString
charname <- String -> IO CString
newCString String
filename
CString
charfmt <- String -> IO CString
newCString String
fmt
(Vector Double
v Vector Double
-> (IO CInt -> IO CInt)
-> TransRaw (Vector Double) (IO CInt)
-> IO CInt
forall c b r.
TransArray c =>
c -> (b -> IO r) -> TransRaw c b -> IO r
`applyRaw` IO CInt -> IO CInt
forall a. a -> a
id) (CString -> CString -> TV
gsl_vector_fprintf CString
charname CString
charfmt) IO CInt -> String -> IO ()
#|String
"gsl_vector_fprintf"
CString -> IO ()
forall a. Ptr a -> IO ()
free CString
charname
CString -> IO ()
forall a. Ptr a -> IO ()
free CString
charfmt
foreign import ccall unsafe "vector_fprintf" gsl_vector_fprintf :: Ptr CChar -> Ptr CChar -> TV
freadVector :: FilePath -> Int -> IO (Vector Double)
freadVector :: String -> Int -> IO (Vector Double)
freadVector String
filename Int
n = do
CString
charname <- String -> IO CString
newCString String
filename
Vector Double
res <- Int -> IO (Vector Double)
forall a. Storable a => Int -> IO (Vector a)
createVector Int
n
(Vector Double
res Vector Double
-> (IO CInt -> IO CInt)
-> TransRaw (Vector Double) (IO CInt)
-> IO CInt
forall c b r.
TransArray c =>
c -> (b -> IO r) -> TransRaw c b -> IO r
`applyRaw` IO CInt -> IO CInt
forall a. a -> a
id) (CString -> TV
gsl_vector_fread CString
charname) IO CInt -> String -> IO ()
#| String
"gsl_vector_fread"
CString -> IO ()
forall a. Ptr a -> IO ()
free CString
charname
Vector Double -> IO (Vector Double)
forall (m :: * -> *) a. Monad m => a -> m a
return Vector Double
res
foreign import ccall unsafe "vector_fread" gsl_vector_fread:: Ptr CChar -> TV
fwriteVector :: FilePath -> Vector Double -> IO ()
fwriteVector :: String -> Vector Double -> IO ()
fwriteVector String
filename Vector Double
v = do
CString
charname <- String -> IO CString
newCString String
filename
(Vector Double
v Vector Double
-> (IO CInt -> IO CInt)
-> TransRaw (Vector Double) (IO CInt)
-> IO CInt
forall c b r.
TransArray c =>
c -> (b -> IO r) -> TransRaw c b -> IO r
`applyRaw` IO CInt -> IO CInt
forall a. a -> a
id) (CString -> TV
gsl_vector_fwrite CString
charname) IO CInt -> String -> IO ()
#|String
"gsl_vector_fwrite"
CString -> IO ()
forall a. Ptr a -> IO ()
free CString
charname
foreign import ccall unsafe "vector_fwrite" gsl_vector_fwrite :: Ptr CChar -> TV
type PD = Ptr Double
type TV = CInt -> PD -> IO CInt
type TM = CInt -> CInt -> PD -> IO CInt
fileDimensions :: FilePath -> IO (Int,Int)
fileDimensions :: String -> IO (Int, Int)
fileDimensions String
fname = do
String
wcres <- String -> [String] -> String -> IO String
readProcess String
"wc" [String
"-w",String
fname] String
""
String
contents <- String -> IO String
readFile String
fname
let tot :: Int
tot = String -> Int
forall a. Read a => String -> a
read (String -> Int) -> (String -> String) -> String -> Int
forall b c a. (b -> c) -> (a -> b) -> a -> c
. [String] -> String
forall a. [a] -> a
head ([String] -> String) -> (String -> [String]) -> String -> String
forall b c a. (b -> c) -> (a -> b) -> a -> c
. String -> [String]
words (String -> Int) -> String -> Int
forall a b. (a -> b) -> a -> b
$ String
wcres
c :: Int
c = [String] -> Int
forall (t :: * -> *) a. Foldable t => t a -> Int
length ([String] -> Int) -> (String -> [String]) -> String -> Int
forall b c a. (b -> c) -> (a -> b) -> a -> c
. [[String]] -> [String]
forall a. [a] -> a
head ([[String]] -> [String])
-> (String -> [[String]]) -> String -> [String]
forall b c a. (b -> c) -> (a -> b) -> a -> c
. ([String] -> Bool) -> [[String]] -> [[String]]
forall a. (a -> Bool) -> [a] -> [a]
dropWhile [String] -> Bool
forall (t :: * -> *) a. Foldable t => t a -> Bool
null ([[String]] -> [[String]])
-> (String -> [[String]]) -> String -> [[String]]
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (String -> [String]) -> [String] -> [[String]]
forall a b. (a -> b) -> [a] -> [b]
map String -> [String]
words ([String] -> [[String]])
-> (String -> [String]) -> String -> [[String]]
forall b c a. (b -> c) -> (a -> b) -> a -> c
. String -> [String]
lines (String -> Int) -> String -> Int
forall a b. (a -> b) -> a -> b
$ String
contents
if Int
tot Int -> Int -> Bool
forall a. Ord a => a -> a -> Bool
> Int
0
then (Int, Int) -> IO (Int, Int)
forall (m :: * -> *) a. Monad m => a -> m a
return (Int
tot Int -> Int -> Int
forall a. Integral a => a -> a -> a
`div` Int
c, Int
c)
else (Int, Int) -> IO (Int, Int)
forall (m :: * -> *) a. Monad m => a -> m a
return (Int
0,Int
0)
loadMatrix :: FilePath -> IO (Matrix Double)
loadMatrix :: String -> IO (Matrix Double)
loadMatrix String
file = String -> (Int, Int) -> IO (Matrix Double)
fromFile String
file ((Int, Int) -> IO (Matrix Double))
-> IO (Int, Int) -> IO (Matrix Double)
forall (m :: * -> *) a b. Monad m => (a -> m b) -> m a -> m b
=<< String -> IO (Int, Int)
fileDimensions String
file
fromFile :: FilePath -> (Int,Int) -> IO (Matrix Double)
fromFile :: String -> (Int, Int) -> IO (Matrix Double)
fromFile String
filename (Int
r,Int
c) = Int -> Vector Double -> Matrix Double
forall t. Storable t => Int -> Vector t -> Matrix t
reshape Int
c (Vector Double -> Matrix Double)
-> IO (Vector Double) -> IO (Matrix Double)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
`fmap` String -> Int -> IO (Vector Double)
fscanfVector String
filename (Int
rInt -> Int -> Int
forall a. Num a => a -> a -> a
*Int
c)