-- Hoogle documentation, generated by Haddock -- See Hoogle, http://www.haskell.org/hoogle/ -- | Implementation of the two-phase simplex method in exact rational arithmetic -- -- Please see the README on GitHub at -- https://github.com/rasheedja/simplex-method#readme @package simplex-method @version 0.2.0.0 module Linear.Simplex.Types type Var = Int type SimplexNum = Rational type SystemRow = PolyConstraint type System = [SystemRow] data SystemWithSlackVarRow SystemInStandardFormRow :: Maybe Var -> TableauRow -> SystemWithSlackVarRow -- | This is Nothing iff the row does not have a slack variable [$sel:mSlackVar:SystemInStandardFormRow] :: SystemWithSlackVarRow -> Maybe Var [$sel:row:SystemInStandardFormRow] :: SystemWithSlackVarRow -> TableauRow type SystemWithSlackVars = [SystemWithSlackVarRow] data FeasibleSystem FeasibleSystem :: Dict -> [Var] -> [Var] -> Var -> FeasibleSystem [$sel:dict:FeasibleSystem] :: FeasibleSystem -> Dict [$sel:slackVars:FeasibleSystem] :: FeasibleSystem -> [Var] [$sel:artificialVars:FeasibleSystem] :: FeasibleSystem -> [Var] [$sel:objectiveVar:FeasibleSystem] :: FeasibleSystem -> Var data Result Result :: Var -> VarLitMap -> Result [$sel:objectiveVar:Result] :: Result -> Var [$sel:varValMap:Result] :: Result -> VarLitMap data SimplexMeta SimplexMeta :: ObjectiveFunction -> Maybe FeasibleSystem -> Maybe Result -> SimplexMeta [$sel:objective:SimplexMeta] :: SimplexMeta -> ObjectiveFunction [$sel:feasibleSystem:SimplexMeta] :: SimplexMeta -> Maybe FeasibleSystem [$sel:optimisedResult:SimplexMeta] :: SimplexMeta -> Maybe Result type VarLitMap = Map Var SimplexNum -- | List of variables with their SimplexNum coefficients. There is -- an implicit addition between elements in this list. -- -- Example: [Var "x" 3, Var "y" -1, Var "z" 1] is equivalent to 3x + (-y) -- + z. type VarLitMapSum = VarLitMap -- | For specifying constraints in a system. The LHS is a Vars, -- and the RHS, is a SimplexNum number. LEQ [(1, 2), (2, 1)] 3.5 -- is equivalent to 2x1 + x2 <= 3.5. Users must only provide positive -- integer variables. -- -- Example: LEQ [Var "x" 3, Var "y" -1, Var "x" 1] 12.3 is equivalent to -- 3x + (-y) + x <= 12.3. data PolyConstraint LEQ :: VarLitMapSum -> SimplexNum -> PolyConstraint [$sel:lhs:LEQ] :: PolyConstraint -> VarLitMapSum [$sel:rhs:LEQ] :: PolyConstraint -> SimplexNum GEQ :: VarLitMapSum -> SimplexNum -> PolyConstraint [$sel:lhs:LEQ] :: PolyConstraint -> VarLitMapSum [$sel:rhs:LEQ] :: PolyConstraint -> SimplexNum EQ :: VarLitMapSum -> SimplexNum -> PolyConstraint [$sel:lhs:LEQ] :: PolyConstraint -> VarLitMapSum [$sel:rhs:LEQ] :: PolyConstraint -> SimplexNum -- | Create an objective function. We can either Maximize or -- Minimize a VarTermSum. data ObjectiveFunction Max :: VarLitMapSum -> ObjectiveFunction [$sel:objective:Max] :: ObjectiveFunction -> VarLitMapSum Min :: VarLitMapSum -> ObjectiveFunction [$sel:objective:Max] :: ObjectiveFunction -> VarLitMapSum -- | TODO: Maybe we want this type TODO: A better/alternative name data Equation Equation :: VarLitMapSum -> SimplexNum -> Equation [$sel:lhs:Equation] :: Equation -> VarLitMapSum [$sel:rhs:Equation] :: Equation -> SimplexNum -- | Value for Tableau. lhs = rhs. data TableauRow TableauRow :: VarLitMapSum -> SimplexNum -> TableauRow [$sel:lhs:TableauRow] :: TableauRow -> VarLitMapSum [$sel:rhs:TableauRow] :: TableauRow -> SimplexNum -- | A simplex Tableu of equations. Each entry in the map is a -- row. type Tableau = Map Var TableauRow -- | Values for a Dict. data DictValue DictValue :: VarLitMapSum -> SimplexNum -> DictValue [$sel:varMapSum:DictValue] :: DictValue -> VarLitMapSum [$sel:constant:DictValue] :: DictValue -> SimplexNum -- | A simplex Dict One quation represents the objective function. -- Each pair in the list is one equation in the system we're working -- with. data Dict = Dict { objective :: DictObjective , entries :: -- DictEntries } deriving (Show, Read, Eq, Generic) type Dict = Map Var DictValue data PivotObjective PivotObjective :: Var -> VarLitMapSum -> SimplexNum -> PivotObjective [$sel:variable:PivotObjective] :: PivotObjective -> Var [$sel:function:PivotObjective] :: PivotObjective -> VarLitMapSum [$sel:constant:PivotObjective] :: PivotObjective -> SimplexNum instance GHC.Generics.Generic Linear.Simplex.Types.Result instance GHC.Classes.Eq Linear.Simplex.Types.Result instance GHC.Read.Read Linear.Simplex.Types.Result instance GHC.Show.Show Linear.Simplex.Types.Result instance GHC.Generics.Generic Linear.Simplex.Types.PolyConstraint instance GHC.Classes.Eq Linear.Simplex.Types.PolyConstraint instance GHC.Read.Read Linear.Simplex.Types.PolyConstraint instance GHC.Show.Show Linear.Simplex.Types.PolyConstraint instance GHC.Generics.Generic Linear.Simplex.Types.ObjectiveFunction instance GHC.Classes.Eq Linear.Simplex.Types.ObjectiveFunction instance GHC.Read.Read Linear.Simplex.Types.ObjectiveFunction instance GHC.Show.Show Linear.Simplex.Types.ObjectiveFunction instance GHC.Generics.Generic Linear.Simplex.Types.TableauRow instance GHC.Classes.Eq Linear.Simplex.Types.TableauRow instance GHC.Read.Read Linear.Simplex.Types.TableauRow instance GHC.Show.Show Linear.Simplex.Types.TableauRow instance GHC.Generics.Generic Linear.Simplex.Types.DictValue instance GHC.Classes.Eq Linear.Simplex.Types.DictValue instance GHC.Read.Read Linear.Simplex.Types.DictValue instance GHC.Show.Show Linear.Simplex.Types.DictValue instance GHC.Generics.Generic Linear.Simplex.Types.FeasibleSystem instance GHC.Classes.Eq Linear.Simplex.Types.FeasibleSystem instance GHC.Read.Read Linear.Simplex.Types.FeasibleSystem instance GHC.Show.Show Linear.Simplex.Types.FeasibleSystem instance GHC.Generics.Generic Linear.Simplex.Types.PivotObjective instance GHC.Classes.Eq Linear.Simplex.Types.PivotObjective instance GHC.Read.Read Linear.Simplex.Types.PivotObjective instance GHC.Show.Show Linear.Simplex.Types.PivotObjective -- | Converts Linear.Simplex.Types types into human-readable -- Strings module Linear.Simplex.Prettify -- | Convert a VarConstMap into a human-readable String prettyShowVarConstMap :: VarLitMapSum -> String -- | Convert a PolyConstraint into a human-readable String prettyShowPolyConstraint :: PolyConstraint -> String -- | Convert an ObjectiveFunction into a human-readable -- String prettyShowObjectiveFunction :: ObjectiveFunction -> String -- | Helper functions for performing the two-phase simplex method. module Linear.Simplex.Util -- | Is the given ObjectiveFunction to be Maximized? isMax :: ObjectiveFunction -> Bool -- | Simplifies a system of PolyConstraints by first calling -- simplifyPolyConstraint, then reducing LEQ and -- GEQ with same LHS and RHS (and other similar situations) into -- EQ, and finally removing duplicate elements using nub. simplifySystem :: [PolyConstraint] -> [PolyConstraint] -- | Converts a Dict to a Tableau using -- dictEntryToTableauEntry. FIXME: maybe remove this line. The -- basic variables will have a coefficient of 1 in the Tableau. dictionaryFormToTableau :: Dict -> Tableau -- | Converts a Tableau to a Dict. We do this by isolating -- the basic variable on the LHS, ending up with all non basic variables -- and a SimplexNum constant on the RHS. tableauInDictionaryForm :: Tableau -> Dict -- | If this function is given Nothing, return Nothing. -- Otherwise, we lookup the Integer given in the first item -- of the pair in the map given in the second item of the pair. This is -- typically used to extract the value of the ObjectiveFunction -- after calling twoPhaseSimplex. extractObjectiveValue :: Maybe Result -> Maybe SimplexNum -- | Combines two 'VarLitMapSums together by summing values with matching -- keys combineVarLitMapSums :: VarLitMapSum -> VarLitMapSum -> VarLitMapSum foldDictValue :: [DictValue] -> DictValue foldVarLitMap :: [VarLitMap] -> VarLitMap insertPivotObjectiveToDict :: PivotObjective -> Dict -> Dict showT :: Show a => a -> Text logMsg :: (MonadIO m, MonadLogger m) => LogLevel -> Text -> m () extractTableauValues :: Tableau -> Map Var SimplexNum extractDictValues :: Dict -> Map Var SimplexNum -- | Module implementing the two-phase simplex method. -- findFeasibleSolution performs phase one of the two-phase -- simplex method. optimizeFeasibleSystem performs phase two of -- the two-phase simplex method. twoPhaseSimplex performs both -- phases of the two-phase simplex method. module Linear.Simplex.Solver.TwoPhase -- | Find a feasible solution for the given system of -- PolyConstraints by performing the first phase of the two-phase -- simplex method All variables in the PolyConstraint must be -- positive. If the system is infeasible, return Nothing -- Otherwise, return the feasible system in Dict as well as a list -- of slack variables, a list artificial variables, and the objective -- variable. findFeasibleSolution :: (MonadIO m, MonadLogger m) => [PolyConstraint] -> m (Maybe FeasibleSystem) -- | Optimize a feasible system by performing the second phase of the -- two-phase simplex method. We first pass an ObjectiveFunction. -- Then, the feasible system in DictionaryForm as well as a list -- of slack variables, a list artificial variables, and the objective -- variable. Returns a pair with the first item being the Integer -- variable equal to the ObjectiveFunction and the second item -- being a map of the values of all Integer variables appearing in -- the system, including the ObjectiveFunction. optimizeFeasibleSystem :: (MonadIO m, MonadLogger m) => ObjectiveFunction -> FeasibleSystem -> m (Maybe Result) -- | Perform the two phase simplex method with a given -- ObjectiveFunction a system of PolyConstraints. Assumes -- the ObjectiveFunction and PolyConstraint is not empty. -- Returns a pair with the first item being the Integer variable -- equal to the ObjectiveFunction and the second item being a map -- of the values of all Integer variables appearing in the system, -- including the ObjectiveFunction. twoPhaseSimplex :: (MonadIO m, MonadLogger m) => ObjectiveFunction -> [PolyConstraint] -> m (Maybe Result)