module AI.Instinct.Train.Delta
(
TrainPat,
train,
trainAtomic,
trainPat,
learnPat,
totalError,
tpList
)
where
import qualified Data.Vector as V
import qualified Data.Vector.Unboxed as U
import AI.Instinct.Activation
import AI.Instinct.Brain
import AI.Instinct.ConnMatrix
import Control.Arrow
import Data.List
type TrainPat = (Pattern, Pattern)
learnPat :: Brain -> Double -> TrainPat -> ConnMatrix
learnPat b@(Brain actF cm _ ol) rate (inP, expP) =
cmMap (\sk dk _ -> rate * (delta V.! dk) * (av V.! sk)) cm
where
av = activation b inP
iv = netInputFrom b av inP
outP = U.convert (V.drop outk av)
outk = size ol
size = cmSize cm
dact :: Double -> Double
dact = actDeriv actF
delta :: V.Vector Double
delta = V.generate size f
where
f k | k >= outk = let ok = k outk in del * ((expP U.! ok) (outP U.! ok))
| otherwise = del * cmDests k (\s' dk w -> s' + (delta V.! dk) * w) 0 cm
where
del = dact (iv V.! k)
totalError :: Brain -> [TrainPat] -> Double
totalError b = foldl' (\e' (inP, expP) -> e' + patError (runNet b inP) expP) 0
tpList :: [Double] -> [Double] -> (Pattern, Pattern)
tpList = curry (U.fromList *** U.fromList)
train :: Brain -> Double -> [TrainPat] -> Brain
train b' rate = foldl' (\b' -> trainPat b' rate) b'
trainAtomic :: Brain -> Double -> [TrainPat] -> Brain
trainAtomic b'@(Brain _ cm' _ _) rate ps =
b' { brainConns = foldl' (\m' -> cmAdd m' . learnPat b' rate) cm' ps }
trainPat :: Brain -> Double -> TrainPat -> Brain
trainPat b@(Brain _ cm _ _) rate inP =
b { brainConns = cmAdd cm (learnPat b rate inP) }