{-# LANGUAGE BangPatterns #-}
module Bio.Chain.Alignment.Scoring.Loader where

import           Control.Applicative             ( liftA2 )

class ScoringMatrix a where
    scoring :: a -> Char -> Char -> Int

loadMatrix :: String -> [((Char, Char), Int)]
loadMatrix :: String -> [((Char, Char), Int)]
loadMatrix String
txt = forall (t :: * -> *) a b. Foldable t => (a -> [b]) -> t a -> [b]
concatMap ([String] -> [((Char, Char), Int)]
lineMap forall b c a. (b -> c) -> (a -> b) -> a -> c
. String -> [String]
words) (forall a. [a] -> [a]
tail [String]
txtlns)
    where
    -- Lines of matrix
    txtlns :: [String]
    !txtlns :: [String]
txtlns  = forall a. (a -> Bool) -> [a] -> [a]
filter (forall (f :: * -> *) a b c.
Applicative f =>
(a -> b -> c) -> f a -> f b -> f c
liftA2 Bool -> Bool -> Bool
(||) forall (t :: * -> *) a. Foldable t => t a -> Bool
null ((forall a. Eq a => a -> a -> Bool
/= Char
'#') forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall a. [a] -> a
head)) (String -> String
strip forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> String -> [String]
lines String
txt)

    -- Letters of matrix
    letters :: [Char]
    !letters :: String
letters = (forall a b. (a -> b) -> [a] -> [b]
map forall a. [a] -> a
head forall b c a. (b -> c) -> (a -> b) -> a -> c
. String -> [String]
words forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall a. [a] -> a
head) [String]
txtlns
    
    -- Strip spaces
    strip :: String -> String
    strip :: String -> String
strip = forall a. [a] -> [a]
reverse forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall a. (a -> Bool) -> [a] -> [a]
dropWhile (forall a. Eq a => a -> a -> Bool
== Char
' ') forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall a. [a] -> [a]
reverse forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall a. (a -> Bool) -> [a] -> [a]
dropWhile (forall a. Eq a => a -> a -> Bool
== Char
' ')
    
    -- Map one line to a matrix
    lineMap :: [String] -> [((Char, Char), Int)]
    lineMap :: [String] -> [((Char, Char), Int)]
lineMap []       = []
    lineMap (String
x : [String]
xs) =
        let !hx :: Char
hx = forall a. [a] -> a
head String
x
            g :: (Int, Char) -> ((Char, Char), Int)
g (Int
n, Char
c) = ((Char
hx, Char
c), Int
n)
        in  (Int, Char) -> ((Char, Char), Int)
g forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> (forall a. Read a => String -> a
read forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> [String]
xs) forall a b. [a] -> [b] -> [(a, b)]
`zip` String
letters