module Numeric.Limp.Canon.Analyse.Constants where
import Numeric.Limp.Canon.Program
import Numeric.Limp.Rep
import Numeric.Limp.Error
import qualified Data.Map as M
constantsProgram :: (Ord z, Ord r, Rep c) => Program z r c -> Either Infeasible (Assignment z r c)
constantsProgram p
= mkAss $ concatMap eq $ M.toList $ _bounds p
where
eq (var, (Just lo, Just up))
| lo == up
= [(var, lo)]
eq _
= []
mkAss ms
= do zs <- mapM tkLeft ms
rs <- mapM tkRight ms
return $ Assignment (M.fromList $ concat zs)
(M.fromList $ concat rs)
tkLeft (Left z, v)
| v /= (fromZ $ truncate v)
= Left InfeasibleNotIntegral
| otherwise
= return [(z, truncate v)]
tkLeft _
= return []
tkRight (Right r, v)
= return [(r, v)]
tkRight _
= return []