.. _cpp-flow/LinExp: ********************************************************** flow/LinExp.hpp ********************************************************** .. default-domain:: cpp .. default-role:: cpp:expr .. py:currentmodule:: mod .. cpp:namespace:: mod Linear expressions and constraints can be implicitly created from variable specifiers and operators, meaning one rarely need to instantiate them explicitly. However creating the zero-expression might sometimes be useful (e.g., in a sum expression) and can be done simply with the expression :cpp:expr:`flow::LinExp()`. A variable specifier is a representation of either a single variable or a sum of variables. The addition, multiplication and division operators are overloaded for variable specifiers and linear expressions such that expressions can be written in the natural manner. The operators ``<=``, ``==`` and ``>=`` are overloaded on linear expressions to make the creation of linear constraints easier. However, one argument to the operator must be a linear expression while the other argument must be a number. Variable Specifiers -------------------- The main variables in a flow model are associated with either vertices or hyperedges in the underlying derivation graph. A variable specifier represents either a set of variables or a single variable, Each specifier has an associated ID that must be registered by a flow model module at the time when the specifier is added to the model. See also :ref:`flowCommon` for an overview of the specifiers. Class ``flow::VarSumVertex`` -------------------------------------------------------------------------------------------------------------------------------- .. class:: flow::VarSumVertex Represents the sum of all variables indicated by the given :cpp:expr:`id`. Can be indexed to retrieve a specifier for a single variable in the set. Synopsis ^^^^^^^^ .. code-block:: c++ struct MOD_DECL VarSumVertex { explicit VarSumVertex(std::string id); MOD_DECL friend std::ostream &operator<<(std::ostream &s, const VarSumVertex &v); MOD_DECL friend bool operator==(const VarSumVertex &a, const VarSumVertex &b) { return a.id == b.id; } VarVertex operator[](dg::DG::Vertex v) const; VarVertexGraph operator[](std::shared_ptr g) const; public: std::string id; }; Details ^^^^^^^ .. cpp:namespace-push:: flow::VarSumVertex .. function:: explicit VarSumVertex(std::string id) Construct a variable specifier for a sum of variables associated with vertices in the underlying derivation graph. .. function:: friend std::ostream &operator<<(std::ostream &s, const VarSumVertex &v) .. function:: friend bool operator==(const VarSumVertex &a, const VarSumVertex &b) .. function:: VarVertex operator[](dg::DG::Vertex v) const Select the variable associated with the given derivation graph vertex. When the resulting specifier is given to a flow model the vertex must be from the underlying derivation graph. :returns: a variable specifier for a single variable in the set represented by this object. :throws: `LogicError` if `!v`. .. function:: VarVertexGraph operator[](std::shared_ptr g) const Select the variable associated with the derivation graph vertex which represents the given graph. When the resulting specifier is given to a flow model such a vertex must then exist in the underlying derivation graph. :returns: a variable specifier for a single variable in the set represented by this object. .. var:: std::string id The ID for this specifier. .. cpp:namespace-pop:: Class ``flow::VarVertex`` -------------------------------------------------------------------------------------------------------------------------------- .. class:: flow::VarVertex Represents a variable associated with a single vertex in a derivation graph. Synopsis ^^^^^^^^ .. code-block:: c++ struct MOD_DECL VarVertex { explicit VarVertex(std::string id, dg::DG::Vertex v); MOD_DECL friend std::ostream &operator<<(std::ostream &s, const VarVertex &v); MOD_DECL friend bool operator==(const VarVertex &a, const VarVertex &b) { return a.id == b.id && a.v == b.v; } public: std::string id; dg::DG::Vertex v; }; Details ^^^^^^^ .. cpp:namespace-push:: flow::VarVertex .. function:: explicit VarVertex(std::string id, dg::DG::Vertex v) :throws: `LogicError` if `!v`. .. function:: friend std::ostream &operator<<(std::ostream &s, const VarVertex &v) .. function:: friend bool operator==(const VarVertex &a, const VarVertex &b) .. var:: std::string id .. var:: dg::DG::Vertex v .. cpp:namespace-pop:: Class ``flow::VarVertexGraph`` -------------------------------------------------------------------------------------------------------------------------------- .. class:: flow::VarVertexGraph Represents a variable associated with a single vertex in a derivation graph. This is done implicitly by a graph, and when this specifier is later given to a flow model a vertex with the graph associated must exist in the underlying derivation graph. Synopsis ^^^^^^^^ .. code-block:: c++ struct MOD_DECL VarVertexGraph { explicit VarVertexGraph(std::string id, std::shared_ptr g); MOD_DECL friend std::ostream &operator<<(std::ostream &s, const VarVertexGraph &v); MOD_DECL friend bool operator==(const VarVertexGraph &a, const VarVertexGraph &b) { return a.id == b.id && a.g == b.g; } public: std::string id; std::shared_ptr g; }; Details ^^^^^^^ .. cpp:namespace-push:: flow::VarVertexGraph .. function:: explicit VarVertexGraph(std::string id, std::shared_ptr g) .. function:: friend std::ostream &operator<<(std::ostream &s, const VarVertexGraph &v) .. function:: friend bool operator==(const VarVertexGraph &a, const VarVertexGraph &b) .. var:: std::string id .. var:: std::shared_ptr g .. cpp:namespace-pop:: Class ``flow::VarSumEdge`` -------------------------------------------------------------------------------------------------------------------------------- .. class:: flow::VarSumEdge Represents the sum of all variables indicated by the given :cpp:expr:`id`. Can be indexed to retrieve a specifier for a single variable in the set. Synopsis ^^^^^^^^ .. code-block:: c++ struct MOD_DECL VarSumEdge { explicit VarSumEdge(std::string id); public: MOD_DECL friend std::ostream &operator<<(std::ostream &s, const VarSumEdge &v); MOD_DECL friend bool operator==(const VarSumEdge &a, const VarSumEdge &b) { return a.id == b.id; } VarEdge operator[](dg::DG::HyperEdge e) const; public: std::string id; }; Details ^^^^^^^ .. cpp:namespace-push:: flow::VarSumEdge .. function:: explicit VarSumEdge(std::string id) Construct a variable specifier for a sum of variables associated with hyperedges in the underlying derivation graph. .. function:: friend std::ostream &operator<<(std::ostream &s, const VarSumEdge &v) .. function:: friend bool operator==(const VarSumEdge &a, const VarSumEdge &b) .. function:: VarEdge operator[](dg::DG::HyperEdge e) const Select the variable associated with the given derivation graph hyperedge. When the resulting specifier is given to a flow model its underlying derivation graph must be the same as the derivation graph the given hyperedge belongs to. :returns: a variable specifier for a single variable in the set represented by this object. :throws: :cpp:type:`LogicError` if :cpp:expr:`!e`. .. var:: std::string id .. cpp:namespace-pop:: Class ``flow::VarEdge`` -------------------------------------------------------------------------------------------------------------------------------- .. class:: flow::VarEdge Represents a variable associated with a single hyperedge in a derivation graph. When this specifier is later given to a flow model its underlying derivation graph must be the same as the derivation graph the hyperedge in this object belongs to. Synopsis ^^^^^^^^ .. code-block:: c++ struct MOD_DECL VarEdge { explicit VarEdge(std::string id, dg::DG::HyperEdge e); MOD_DECL friend std::ostream &operator<<(std::ostream &s, const VarEdge &v); MOD_DECL friend bool operator==(const VarEdge &a, const VarEdge &b) { return a.id == b.id && a.edge == b.edge; } public: std::string id; dg::DG::HyperEdge edge; }; Details ^^^^^^^ .. cpp:namespace-push:: flow::VarEdge .. function:: explicit VarEdge(std::string id, dg::DG::HyperEdge e) :throws: :cpp:type:`LogicError` if :cpp:expr:`!e`. .. function:: friend std::ostream &operator<<(std::ostream &s, const VarEdge &v) .. function:: friend bool operator==(const VarEdge &a, const VarEdge &b) .. var:: std::string id .. var:: dg::DG::HyperEdge edge .. cpp:namespace-pop:: Class ``flow::VarSumCustom`` -------------------------------------------------------------------------------------------------------------------------------- .. class:: flow::VarSumCustom Represents the sum of all variables indicated by the given :cpp:expr:`id`. Can be indexed to retrieve a specifier for a single variable in the set. Synopsis ^^^^^^^^ .. code-block:: c++ struct MOD_DECL VarSumCustom { explicit VarSumCustom(std::string id); MOD_DECL friend std::ostream &operator<<(std::ostream &s, const VarSumCustom &v); MOD_DECL friend bool operator==(const VarSumCustom &a, const VarSumCustom &b) { return a.id == b.id; } VarCustom operator[](std::string name) const; public: std::string id; }; Details ^^^^^^^ .. cpp:namespace-push:: flow::VarSumCustom .. function:: explicit VarSumCustom(std::string id) .. function:: friend std::ostream &operator<<(std::ostream &s, const VarSumCustom &v) .. function:: friend bool operator==(const VarSumCustom &a, const VarSumCustom &b) .. function:: VarCustom operator[](std::string name) const Select the variable associated with the given name. When the resulting specifier is given to a flow model that variable must have been created in the specification in some way. :returns: a variable specifier for a single variable in the set represented by this object. .. var:: std::string id .. cpp:namespace-pop:: Class ``flow::VarCustom`` -------------------------------------------------------------------------------------------------------------------------------- .. class:: flow::VarCustom Represents a custom variable. Synopsis ^^^^^^^^ .. code-block:: c++ struct MOD_DECL VarCustom { explicit VarCustom(std::string id, std::string name); MOD_DECL friend std::ostream &operator<<(std::ostream &s, const VarCustom &v); MOD_DECL friend bool operator==(const VarCustom &a, const VarCustom &b) { return a.id == b.id && a.name == b.name; } public: std::string id; std::string name; }; Details ^^^^^^^ .. cpp:namespace-push:: flow::VarCustom .. function:: explicit VarCustom(std::string id, std::string name) .. function:: friend std::ostream &operator<<(std::ostream &s, const VarCustom &v) .. function:: friend bool operator==(const VarCustom &a, const VarCustom &b) .. var:: std::string id .. var:: std::string name .. cpp:namespace-pop:: Class ``flow::Var`` -------------------------------------------------------------------------------------------------------------------------------- .. class:: flow::Var Represents any of the variable specifier types, and can be implicitly converted to from any of them. Synopsis ^^^^^^^^ .. code-block:: c++ struct MOD_DECL Var { using VarImpl = boost::variant; public: template::value>::type> Var(T v) : v(std::move(v)) {} template typename Visitor::result_type applyVisitor(Visitor visitor) { return boost::apply_visitor(visitor, v); } template typename Visitor::result_type applyVisitor(Visitor visitor) const { return boost::apply_visitor(visitor, v); } template const T *get() const { return get(&v); } MOD_DECL friend std::ostream &operator<<(std::ostream &s, const Var &v); MOD_DECL friend bool operator==(const Var &a, const Var &b) { return a.v == b.v; } private: VarImpl v; }; Details ^^^^^^^ .. cpp:namespace-push:: flow::Var .. type:: VarImpl = boost::variant .. function:: template \ Var(T v) Requires `T` being a variable specifier type. .. function:: template \ typename Visitor::result_type applyVisitor(Visitor visitor) template \ typename Visitor::result_type applyVisitor(Visitor visitor) const :returns: `boost::apply_visitor(visitor, v)` .. function:: template \ const T *get() const :returns: `get(&v)` .. function:: friend std::ostream &operator<<(std::ostream &s, const Var &v) .. function:: friend bool operator==(const Var &a, const Var &b) .. var:: private VarImpl v .. cpp:namespace-pop:: Class ``flow::LinExp`` -------------------------------------------------------------------------------------------------------------------------------- .. class:: flow::LinExp Represents a linear expression over variable specifiers. Synopsis ^^^^^^^^ .. code-block:: c++ struct MOD_DECL LinExp { using IntElement = std::pair; using FloatElement = std::pair; public: LinExp() = default; LinExp(Var v); template::value>::type> LinExp(T v) : LinExp(Var(std::move(v))) {} MOD_DECL friend std::ostream &operator<<(std::ostream &s, const LinExp &exp); const std::vector &getIntElements() const; const std::vector &getFloatElements() const; LinExp &operator+=(const LinExp &e); LinExp &operator-=(const LinExp &e); LinExp &operator*=(int c); LinExp &operator*=(double c); private: std::vector intElements; std::vector floatElements; }; Details ^^^^^^^ .. cpp:namespace-push:: flow::LinExp .. type:: IntElement = std::pair .. type:: FloatElement = std::pair .. function:: LinExp() = default .. function:: template LinExp(T v) Requires `T` convertible to `Var`. .. function:: friend std::ostream &operator<<(std::ostream &s, const LinExp &exp) .. function:: const std::vector &getIntElements() const :returns: all elements of the linear expression that have integer coefficients. .. function:: const std::vector &getFloatElements() const :returns: all elements of the linear expression that have floating point coefficients. .. cpp:namespace-pop:: Class ``flow::LinConstraint`` -------------------------------------------------------------------------------------------------------------------------------- .. class:: flow::LinConstraint Represents a linear constraint on the form :cpp:expr:`exp` :cpp:expr:`relation` :cpp:expr:`bound`, Synopsis ^^^^^^^^ .. code-block:: c++ struct MOD_DECL LinConstraint { enum class Relation { Leq, Eq, Geq }; public: explicit LinConstraint(LinExp exp, Relation relation, double bound); MOD_DECL friend std::ostream &operator<<(std::ostream &s, const LinConstraint &c); public: LinExp exp; Relation relation; double bound; }; Details ^^^^^^^ .. cpp:namespace-push:: flow::LinConstraint .. enum-class:: Relation .. enumerator: Leq Eq Geq .. function:: explicit LinConstraint(LinExp exp, Relation relation, double bound) .. function:: friend std::ostream &operator<<(std::ostream &s, const LinConstraint &c) .. var:: LinExp exp .. var:: Relation relation .. var:: double bound .. cpp:namespace-pop::