Пример #1
0
        private void InitRCGModel()
        {
            SubModel.ClearModel();
            h = SubModel.NumVarArray(Data.DS.Count, 0, double.MaxValue);
            r = SubModel.NumVarArray(Data.RS.Count, 0, double.MaxValue);
            constraint_sub2 = new IRange[Data.RS.Count];
            subObject[0]    = new INumExpr[Data.TimeHorizon];
            subObject[1]    = new INumExpr[Data.TimeHorizon];

            #region 生成约束
            //第一、四种约束
            INumExpr expr1 = SubModel.NumExpr();
            foreach (IMDPDecision d in Data.DS)
            {
                expr1 = SubModel.Sum(expr1, h[Data.DS.IndexOf(d)]);//SubModel.AddGe(h[aff.DS.IndexOf(d)], 0);
            }
            SubModel.AddEq(expr1, 1);

            //第二、三种约束
            foreach (IALPResource re in Data.RS)
            {
                constraint_sub2[Data.RS.IndexOf(re)] = SubModel.AddLe(r[Data.RS.IndexOf(re)], (Data.InitialState as IALPState)[re]);
                INumExpr expr2 = SubModel.NumExpr();
                foreach (IALPDecision a in Data.DS)
                {
                    if (a.UseResource(re))
                    {
                        expr2 = SubModel.Sum(expr2, h[Data.DS.IndexOf(a)]);
                    }
                }
                expr2 = SubModel.Sum(expr2, SubModel.Prod(-1, r[Data.RS.IndexOf(re)]));
                SubModel.AddLe(expr2, 0);
            }
            #endregion

            #region 初始化目标函数第一部分
            //Parallel.For(0, Data.TimeHorizon, t =>
            for (int t = 0; t < Data.TimeHorizon; t++)
            {
                int  iteration = t;
                Task ta        = factory.StartNew(() =>
                {
                    subObject[0][iteration] = SubModel.NumExpr();
                    foreach (IMDPDecision a in Data.DS)
                    {
                        subObject[0][iteration] = SubModel.Sum(subObject[0][iteration],
                                                               SubModel.Prod(Data.Rt(iteration, a), h[Data.DS.IndexOf(a)]));
                    }
                }, cts.Token);
                tasks.Add(ta);
            }
            #endregion
            Task.WaitAll(tasks.ToArray());
            tasks.Clear();

            SubModel.SetOut(null);
        }
Пример #2
0
        private void btn_cutStep_Click(object sender, RoutedEventArgs e)
        {
            mainCanvas.ClearCanvas();

            int[] La = new int[node_cnt * node_cnt];
            for (int i = 0; i < node_cnt; i++)
            {
                int deg = 0;
                for (int j = 0; j < node_cnt; j++)
                {
                    La[i * node_cnt + j] = graph[i, j] ? -1 : 0;
                    deg += graph[i, j] ? 1 : 0;
                }
                La[i * node_cnt + i] = deg;
            }

            Cplex model = new Cplex();

            INumVar[] x   = model.BoolVarArray(node_cnt);
            INumVar[] eij = model.BoolVarArray(node_cnt * node_cnt);
            for (int i = 0; i < node_cnt; i++)
            {
                for (int j = i; j < node_cnt; j++)
                {
                    if (i != j)
                    {
                        model.AddEq(eij[i * node_cnt + j], eij[j * node_cnt + i]);
                    }
                    model.AddLe(eij[i * node_cnt + j], x[i]);
                    model.AddLe(eij[i * node_cnt + j], x[j]);
                    model.AddLe(model.Sum(x[i], x[j]), model.Sum(eij[i * node_cnt + j], eij[i * node_cnt + j], model.Constant(1)));
                }
            }
            model.AddMaximize(model.ScalProd(La, eij));

            if (model.Solve())
            {
                double[] vals = model.GetValues(x);
                int      val  = (int)Math.Round(model.GetObjValue());
                dc_Utility.WriteLine("");
                dc_Utility.WriteLine(dc_Utility.c_stars);
                dc_Utility.WriteLine("Group A size: " + vals.Count(p => p > 0.5));
                dc_Utility.WriteLine("Group B size: " + vals.Count(p => p < 0.5));
                dc_Utility.WriteLine("Max Cut: " + val);
                dc_Utility.WriteLine(dc_Utility.c_stars);
                dc_Utility.WriteLine("");

                for (int i = 0; i < node_cnt; i++)
                {
                    classes[i] = vals[i] > 0.5;
                }
                DrawGraph(true);
            }

            model.Dispose();
        }
Пример #3
0
    // This function creates the following model:
    //   Minimize
    //    obj: x1 + x2 + x3 + x4 + x5 + x6
    //   Subject To
    //    c1: x1 + x2      + x5      = 8
    //    c2:           x3 + x5 + x6 = 10
    //    q1: [ -x1^2 + x2^2 + x3^2 ] <= 0
    //    q2: [ -x4^2 + x5^2 ] <= 0
    //   Bounds
    //    x2 Free
    //    x3 Free
    //    x5 Free
    //   End
    // which is a second order cone program in standard form.
    private static IObjective Createmodel(Cplex cplex,
                                          ICollection <INumVar> vars,
                                          ICollection <IRange> rngs,
                                          IDictionary <INumVar, IRange> cone)
    {
        System.Double pinf = System.Double.PositiveInfinity;
        System.Double ninf = System.Double.NegativeInfinity;
        INumVar       x1   = cplex.NumVar(0, pinf, "x1");
        INumVar       x2   = cplex.NumVar(ninf, pinf, "x2");
        INumVar       x3   = cplex.NumVar(ninf, pinf, "x3");
        INumVar       x4   = cplex.NumVar(0, pinf, "x4");
        INumVar       x5   = cplex.NumVar(ninf, pinf, "x5");
        INumVar       x6   = cplex.NumVar(0, pinf, "x6");

        IObjective obj = cplex.AddMinimize(cplex.Sum(cplex.Sum(cplex.Sum(x1, x2),
                                                               cplex.Sum(x3, x4)),
                                                     cplex.Sum(x5, x6)),
                                           "obj");

        IRange c1 = cplex.AddEq(cplex.Sum(x1, cplex.Sum(x2, x5)), 8, "c1");
        IRange c2 = cplex.AddEq(cplex.Sum(x3, cplex.Sum(x5, x6)), 10, "c2");

        IRange q1 = cplex.AddLe(cplex.Sum(cplex.Prod(-1, cplex.Prod(x1, x1)),
                                          cplex.Sum(cplex.Prod(x2, x2),
                                                    cplex.Prod(x3, x3))), 0, "q1");

        cone[x1] = q1;
        cone[x2] = NOT_CONE_HEAD;
        cone[x3] = NOT_CONE_HEAD;
        IRange q2 = cplex.AddLe(cplex.Sum(cplex.Prod(-1, cplex.Prod(x4, x4)),
                                          cplex.Prod(x5, x5)), 0, "q2");

        cone[x4] = q2;
        cone[x5] = NOT_CONE_HEAD;

        cone[x6] = NOT_IN_CONE;

        vars.Add(x1);
        vars.Add(x2);
        vars.Add(x3);
        vars.Add(x4);
        vars.Add(x5);
        vars.Add(x6);

        rngs.Add(c1);
        rngs.Add(c2);
        rngs.Add(q1);
        rngs.Add(q2);

        return(obj);
    }
Пример #4
0
        private void InitRCGModel()
        {
            SubModel.ClearModel();
            h = SubModel.NumVarArray(Data.DS.Count, 0, double.MaxValue);
            r = SubModel.NumVarArray(Data.RS.Count, 0, double.MaxValue);
            constraint_sub2 = new IRange[Data.RS.Count];
            subObject[0]    = new INumExpr[Data.TimeHorizon];
            subObject[1]    = new INumExpr[Data.TimeHorizon];

            #region 生成约束
            //第一、四种约束
            INumExpr expr1 = SubModel.NumExpr();
            foreach (IMDPDecision d in Data.DS)
            {
                expr1 = SubModel.Sum(expr1, h[Data.DS.IndexOf(d)]);//SubModel.AddGe(h[aff.DS.IndexOf(d)], 0);
            }
            SubModel.AddEq(expr1, 1);

            //第二、三种约束
            foreach (IALPResource re in Data.RS)
            {
                constraint_sub2[Data.RS.IndexOf(re)] = SubModel.AddLe(r[Data.RS.IndexOf(re)], (Data.InitialState as IALPState)[re]);
                INumExpr expr2 = SubModel.NumExpr();
                foreach (IALPDecision a in Data.DS)
                {
                    if (a.UseResource(re))
                    {
                        expr2 = SubModel.Sum(expr2, h[Data.DS.IndexOf(a)]);
                    }
                }
                expr2 = SubModel.Sum(expr2, SubModel.Prod(-1, r[Data.RS.IndexOf(re)]));
                SubModel.AddLe(expr2, 0);
            }
            #endregion

            #region 初始化目标函数第一部分
            Parallel.For(0, Data.TimeHorizon, t =>
                         //for (int t = 0; t < Data.TimeHorizon; t++)
            {
                subObject[0][t] = SubModel.NumExpr();
                foreach (IMDPDecision a in Data.DS)
                {
                    subObject[0][t] = SubModel.Sum(subObject[0][t],
                                                   SubModel.Prod(Data.Rt(t, a), h[Data.DS.IndexOf(a)]));
                }
            });
            #endregion

            SubModel.SetOut(null);
        }
Пример #5
0
    public static void Main(string[] args)
    {
        try {
            Cplex cplex = new Cplex();

            INumVar[] fused = cplex.BoolVarArray(_nbMachines);
            INumVar[] x     = cplex.NumVarArray(_nbMachines, 0.0, System.Double.MaxValue);

            // Objective: minimize the sum of fixed and variable costs
            cplex.AddMinimize(cplex.Sum(cplex.ScalProd(_cost, x),
                                        cplex.ScalProd(fused, _fixedCost)));

            for (int i = 0; i < _nbMachines; i++)
            {
                // Constraint: respect capacity constraint on machine 'i'
                cplex.AddLe(x[i], _capacity[i]);

                // Constraint: only produce product on machine 'i' if it is 'used'
                //             (to capture fixed cost of using machine 'i')
                cplex.AddLe(x[i], cplex.Prod(10000, fused[i]));
            }

            // Constraint: meet demand
            cplex.AddEq(cplex.Sum(x), _demand);

            if (cplex.Solve())
            {
                System.Console.WriteLine("Solution status = " + cplex.GetStatus());
                System.Console.WriteLine("Obj " + cplex.ObjValue);
                double eps = cplex.GetParam(Cplex.Param.MIP.Tolerances.Integrality);
                for (int i = 0; i < _nbMachines; i++)
                {
                    if (cplex.GetValue(fused[i]) > eps)
                    {
                        System.Console.WriteLine("E" + i + " is used for " +
                                                 cplex.GetValue(x[i]));
                    }
                }

                System.Console.WriteLine();
                System.Console.WriteLine("----------------------------------------");
            }
            cplex.End();
        }
        catch (ILOG.Concert.Exception exc) {
            System.Console.WriteLine("Concert exception '" + exc + "' caught");
        }
    }
Пример #6
0
        private void AddCplexLEqual(Cplex model, dc_FGPair fg, INumVar slack)
        {
            INumExpr fi = fg.f.AddExpression(model);
            INumExpr gi = fg.g.Minorize(model);

            model.AddLe(fi, model.Sum(gi, slack));
        }
Пример #7
0
 static bool HasTourElimination(Cplex cplex, Data data, IIntVar[][] x)
 {
     double[][] sol_x = new double[data.n][];
     for (int i = 0; i < data.n; i++)
     {
         sol_x[i] = cplex.GetValues(x[i]);
     }
     //int shortestLenght = ShortestCicleInSelectedPaths(sol_x);
     int[] tour = FindSubTour(sol_x);
     if (tour.Length < data.n)
     {
         ILinearNumExpr sumx = cplex.LinearNumExpr();
         for (int i = 0; i < tour.Length; i++)
         {
             for (int j = i + 1; j < tour.Length; j++)
             {
                 sumx.AddTerm(1, x[tour[i]][tour[j]]);
             }
         }
         cplex.AddLazyConstraint(cplex.AddLe(cplex.Diff(sumx, (tour.Length + 1)), 0));
         return(true);
     }
     else
     {
         return(false);
     }
 }
Пример #8
0
        private void AddIndependentSetsConstraints()
        {
            var independentSets = GetIndependentSets(new List <GraphNode>(graph.Nodes));
            var sets            = independentSets.Values.Where(x => x.Count > 1);

            foreach (var set in sets)
            {
                var numExpr = cplex.NumExpr();
                foreach (var node in set)
                {
                    var curVar = numVars[node.Index - 1];
                    numExpr = cplex.Sum(numExpr, curVar);
                }

                cplex.AddLe(numExpr, 1);
            }
        }
Пример #9
0
    public static void Main( string[] args )
    {
        try {
         string filename  = "../../../../examples/data/facility.dat";
         if (args.Length > 0)
            filename = args[0];
         ReadData(filename);

         Cplex cplex = new Cplex();
         INumVar[] open = cplex.BoolVarArray(_nbLocations);

         INumVar[][] supply = new INumVar[_nbClients][];
         for(int i = 0; i < _nbClients; i++)
            supply[i] = cplex.BoolVarArray(_nbLocations);

         for(int i = 0; i < _nbClients; i++)
            cplex.AddEq(cplex.Sum(supply[i]), 1);

         for(int j = 0; j < _nbLocations; j++) {
            ILinearNumExpr v = cplex.LinearNumExpr();
            for(int i = 0; i < _nbClients; i++)
               v.AddTerm(1.0, supply[i][j]);
            cplex.AddLe(v, cplex.Prod(_capacity[j], open[j]));
         }

         ILinearNumExpr obj = cplex.ScalProd(_fixedCost, open);
         for(int i = 0; i < _nbClients; i++)
            obj.Add(cplex.ScalProd(_cost[i], supply[i]));

         cplex.AddMinimize(obj);

         if (cplex.Solve()) {
            System.Console.WriteLine("Solution status = " + cplex.GetStatus());
            double tolerance = cplex.GetParam(Cplex.Param.MIP.Tolerances.Integrality);
            System.Console.WriteLine("Optimal value: " + cplex.ObjValue);
            for(int j = 0; j < _nbLocations; j++) {
               if (cplex.GetValue(open[j]) >= 1 - tolerance) {
                  System.Console.Write("Facility " + j +" is open, it serves clients ");
                  for(int i = 0; i < _nbClients; i++)
                     if (cplex.GetValue(supply[i][j]) >= 1 - tolerance)
                        System.Console.Write(" " + i);
                  System.Console.WriteLine();
               }
            }
         }
         cplex.End();
          }
          catch(ILOG.Concert.Exception exc) {
         System.Console.WriteLine("Concert exception '" + exc + "' caught");
          }
          catch (System.IO.IOException exc) {
         System.Console.WriteLine("Error reading file " + args[0] + ": " + exc);
          }
          catch (InputDataReader.InputDataReaderException exc) {
         System.Console.WriteLine(exc);
          }
    }
Пример #10
0
    public static void Main(string[] args)
    {
        try {
            Cplex cplex = new Cplex();

            INumVar[] inside  = cplex.NumVarArray(_nbProds, 10.0, Double.MaxValue);
            INumVar[] outside = cplex.NumVarArray(_nbProds, 0.0, Double.MaxValue);
            INumVar   costVar = cplex.NumVar(0.0, Double.MaxValue);

            cplex.AddEq(costVar, cplex.Sum(cplex.ScalProd(inside, _insideCost),
                                           cplex.ScalProd(outside, _outsideCost)));

            IObjective obj = cplex.AddMinimize(costVar);

            // Must meet demand for each product

            for (int p = 0; p < _nbProds; p++)
            {
                cplex.AddEq(cplex.Sum(inside[p], outside[p]), _demand[p]);
            }

            // Must respect capacity constraint for each resource

            for (int r = 0; r < _nbResources; r++)
            {
                cplex.AddLe(cplex.ScalProd(_consumption[r], inside), _capacity[r]);
            }

            cplex.Solve();

            if (cplex.GetStatus() != Cplex.Status.Optimal)
            {
                System.Console.WriteLine("No optimal solution found");
                return;
            }

            // New constraint: cost must be no more than 10% over minimum

            double cost = cplex.ObjValue;
            costVar.UB = 1.1 * cost;

            // New objective: minimize outside production

            obj.Expr = cplex.Sum(outside);

            cplex.Solve();
            System.Console.WriteLine("Solution status = " + cplex.GetStatus());
            DisplayResults(cplex, costVar, inside, outside);
            System.Console.WriteLine("----------------------------------------");
            cplex.End();
        }
        catch (ILOG.Concert.Exception exc) {
            System.Console.WriteLine("Concert exception '" + exc + "' caught");
        }
    }
Пример #11
0
    public static void Main( string[] args )
    {
        try {
         Cplex cplex = new Cplex();

         INumVar[] fused = cplex.BoolVarArray(_nbMachines);
         INumVar[] x     = cplex.NumVarArray(_nbMachines, 0.0, System.Double.MaxValue);

         // Objective: minimize the sum of fixed and variable costs
         cplex.AddMinimize(cplex.Sum(cplex.ScalProd(_cost, x),
                                     cplex.ScalProd(fused, _fixedCost)));

         for (int i =  0; i < _nbMachines; i++) {
            // Constraint: respect capacity constraint on machine 'i'
            cplex.AddLe(x[i], _capacity[i]);

            // Constraint: only produce product on machine 'i' if it is 'used'
            //             (to capture fixed cost of using machine 'i')
            cplex.AddLe(x[i], cplex.Prod(10000, fused[i]));
         }

         // Constraint: meet demand
         cplex.AddEq(cplex.Sum(x), _demand);

         if ( cplex.Solve() ) {
            System.Console.WriteLine("Solution status = " + cplex.GetStatus());
            System.Console.WriteLine("Obj " + cplex.ObjValue);
            double eps = cplex.GetParam(Cplex.Param.MIP.Tolerances.Integrality);
            for(int i = 0; i < _nbMachines; i++)
               if (cplex.GetValue(fused[i]) > eps)
                  System.Console.WriteLine("E" + i + " is used for " +
                                     cplex.GetValue(x[i]));

            System.Console.WriteLine();
            System.Console.WriteLine("----------------------------------------");
         }
         cplex.End();
          }
          catch (ILOG.Concert.Exception exc) {
         System.Console.WriteLine("Concert exception '" + exc + "' caught");
          }
    }
Пример #12
0
        /// <summary>
        /// Constraints for cargo - location coverage considerations. For example, TEX
        /// can have at most %55 of the cargo from a location
        /// </summary>
        private void Coverage()
        {
            for (int i = 0; i < N; i++)
            {
                var cargo = _cargoList[i];
                for (int j = 0; j < M; j++)
                {
                    var location = _locationList[j];
                    if (location.ContainsCargo(cargo))
                    {
                        var rate     = cargo.GetCoverageRate();
                        var forecast = location.GetForecast();

                        var constraint = _solver.LinearNumExpr();
                        constraint.AddTerm(x[i][j], 1);
                        constraint.AddTerm(e[i][j], 1);
                        var rhs = forecast * rate;

                        _solver.AddLe(constraint, rhs);
                    }
                }
            }
        }
Пример #13
0
 public static void Main( string[] args ) {
    try {
       Cplex cplex = new Cplex();
     
       INumVar[]  inside = cplex.NumVarArray(_nbProds, 10.0, Double.MaxValue);
       INumVar[] outside = cplex.NumVarArray(_nbProds, 0.0, Double.MaxValue);
       INumVar   costVar = cplex.NumVar(0.0, Double.MaxValue);
     
       cplex.AddEq(costVar, cplex.Sum(cplex.ScalProd(inside, _insideCost),
                                      cplex.ScalProd(outside, _outsideCost)));
       
       IObjective obj = cplex.AddMinimize(costVar);
     
       // Must meet demand for each product
     
       for(int p = 0; p < _nbProds; p++)
          cplex.AddEq(cplex.Sum(inside[p], outside[p]), _demand[p]);
     
       // Must respect capacity constraint for each resource
     
       for(int r = 0; r < _nbResources; r++)
          cplex.AddLe(cplex.ScalProd(_consumption[r], inside), _capacity[r]);
     
       cplex.Solve();
     
       if ( cplex.GetStatus() != Cplex.Status.Optimal ) {
          System.Console.WriteLine("No optimal solution found");
          return;
       }
     
       // New constraint: cost must be no more than 10% over minimum
     
       double cost = cplex.ObjValue;
       costVar.UB = 1.1 * cost;
     
       // New objective: minimize outside production
     
       obj.Expr = cplex.Sum(outside);
     
       cplex.Solve();
       System.Console.WriteLine("Solution status = " + cplex.GetStatus());       
       DisplayResults(cplex, costVar, inside, outside);
       System.Console.WriteLine("----------------------------------------");
       cplex.End();
    }
    catch (ILOG.Concert.Exception exc) {
       System.Console.WriteLine("Concert exception '" + exc + "' caught");
    }
 }
Пример #14
0
    public static void Main(string[] args)
    {
        try {
            Cplex cplex = new Cplex();

            INumVar[] inside  = new INumVar[_nbProds];
            INumVar[] outside = new INumVar[_nbProds];

            IObjective obj = cplex.AddMinimize();

            // Must meet demand for each product

            for (int p = 0; p < _nbProds; p++)
            {
                IRange demRange = cplex.AddRange(_demand[p], _demand[p]);
                inside[p] = cplex.NumVar(cplex.Column(obj, _insideCost[p]).And(
                                             cplex.Column(demRange, 1.0)),
                                         0.0, System.Double.MaxValue);

                outside[p] = cplex.NumVar(cplex.Column(obj, _outsideCost[p]).And(
                                              cplex.Column(demRange, 1.0)),
                                          0.0, System.Double.MaxValue);
            }

            // Must respect capacity constraint for each resource

            for (int r = 0; r < _nbResources; r++)
            {
                cplex.AddLe(cplex.ScalProd(_consumption[r], inside), _capacity[r]);
            }

            cplex.Solve();

            if (!cplex.GetStatus().Equals(Cplex.Status.Optimal))
            {
                System.Console.WriteLine("No optimal solution found");
                return;
            }

            System.Console.WriteLine("Solution status = " + cplex.GetStatus());
            DisplayResults(cplex, inside, outside);
            System.Console.WriteLine("----------------------------------------");
            cplex.End();
        }
        catch (ILOG.Concert.Exception exc) {
            System.Console.WriteLine("Concert exception '" + exc + "' caught");
        }
    }
Пример #15
0
   public static void Main( string[] args ) {
      try {
         Cplex cplex = new Cplex();
       
         INumVar[]  inside = new INumVar[_nbProds];
         INumVar[] outside = new INumVar[_nbProds];
       
         IObjective obj = cplex.AddMinimize();
       
         // Must meet demand for each product
       
         for(int p = 0; p < _nbProds; p++) {
            IRange demRange = cplex.AddRange(_demand[p], _demand[p]);
            inside[p] = cplex.NumVar(cplex.Column(obj, _insideCost[p]).And(
                                     cplex.Column(demRange, 1.0)),
                                     0.0, System.Double.MaxValue);
            
            outside[p] = cplex.NumVar(cplex.Column(obj, _outsideCost[p]).And(
                                      cplex.Column(demRange, 1.0)),
                                      0.0, System.Double.MaxValue);
         }
       
         // Must respect capacity constraint for each resource
       
         for(int r = 0; r < _nbResources; r++)
            cplex.AddLe(cplex.ScalProd(_consumption[r], inside), _capacity[r]);
       
         cplex.Solve();
       
         if ( !cplex.GetStatus().Equals(Cplex.Status.Optimal) ) {
            System.Console.WriteLine("No optimal solution found");
            return;
         }

         System.Console.WriteLine("Solution status = " + cplex.GetStatus());       
         DisplayResults(cplex, inside, outside);
         System.Console.WriteLine("----------------------------------------");
         cplex.End();
      }
      catch (ILOG.Concert.Exception exc) {
         System.Console.WriteLine("Concert exception '" + exc + "' caught");
      }
   }
Пример #16
0
    public static void Main(string[] args)
    {
        try {
            string filename = "../../../../examples/data/facility.dat";
            if (args.Length > 0)
            {
                filename = args[0];
            }
            ReadData(filename);

            Cplex     cplex = new Cplex();
            INumVar[] open  = cplex.BoolVarArray(_nbLocations);

            INumVar[][] supply = new INumVar[_nbClients][];
            for (int i = 0; i < _nbClients; i++)
            {
                supply[i] = cplex.BoolVarArray(_nbLocations);
            }

            for (int i = 0; i < _nbClients; i++)
            {
                cplex.AddEq(cplex.Sum(supply[i]), 1);
            }

            for (int j = 0; j < _nbLocations; j++)
            {
                ILinearNumExpr v = cplex.LinearNumExpr();
                for (int i = 0; i < _nbClients; i++)
                {
                    v.AddTerm(1.0, supply[i][j]);
                }
                cplex.AddLe(v, cplex.Prod(_capacity[j], open[j]));
            }

            ILinearNumExpr obj = cplex.ScalProd(_fixedCost, open);
            for (int i = 0; i < _nbClients; i++)
            {
                obj.Add(cplex.ScalProd(_cost[i], supply[i]));
            }

            cplex.AddMinimize(obj);

            if (cplex.Solve())
            {
                System.Console.WriteLine("Solution status = " + cplex.GetStatus());
                double tolerance = cplex.GetParam(Cplex.Param.MIP.Tolerances.Integrality);
                System.Console.WriteLine("Optimal value: " + cplex.ObjValue);
                for (int j = 0; j < _nbLocations; j++)
                {
                    if (cplex.GetValue(open[j]) >= 1 - tolerance)
                    {
                        System.Console.Write("Facility " + j + " is open, it serves clients ");
                        for (int i = 0; i < _nbClients; i++)
                        {
                            if (cplex.GetValue(supply[i][j]) >= 1 - tolerance)
                            {
                                System.Console.Write(" " + i);
                            }
                        }
                        System.Console.WriteLine();
                    }
                }
            }
            cplex.End();
        }
        catch (ILOG.Concert.Exception exc) {
            System.Console.WriteLine("Concert exception '" + exc + "' caught");
        }
        catch (System.IO.IOException exc) {
            System.Console.WriteLine("Error reading file " + args[0] + ": " + exc);
        }
        catch (InputDataReader.InputDataReaderException exc) {
            System.Console.WriteLine(exc);
        }
    }
Пример #17
0
    public static void Main(string[] args)
    {
        try {
            string filename = "../../../../examples/data/steel.dat";
            if (args.Length > 0)
            {
                filename = args[0];
            }
            ReadData(filename);

            Cplex cplex = new Cplex();

            // VARIABLES
            INumVar[][] Make = new INumVar[_nProd][];
            for (int p = 0; p < _nProd; p++)
            {
                Make[p] = cplex.NumVarArray(_nTime, 0.0, System.Double.MaxValue);
            }

            INumVar[][] Inv = new INumVar[_nProd][];
            for (int p = 0; p < _nProd; p++)
            {
                Inv[p] = cplex.NumVarArray(_nTime, 0.0, System.Double.MaxValue);
            }

            INumVar[][] Sell = new INumVar[_nProd][];
            for (int p = 0; p < _nProd; p++)
            {
                Sell[p] = new INumVar[_nTime];
                for (int t = 0; t < _nTime; t++)
                {
                    Sell[p][t] = cplex.NumVar(0.0, _market[p][t]);
                }
            }

            // OBJECTIVE
            ILinearNumExpr TotalRevenue  = cplex.LinearNumExpr();
            ILinearNumExpr TotalProdCost = cplex.LinearNumExpr();
            ILinearNumExpr TotalInvCost  = cplex.LinearNumExpr();

            for (int p = 0; p < _nProd; p++)
            {
                for (int t = 1; t < _nTime; t++)
                {
                    TotalRevenue.AddTerm(_revenue[p][t], Sell[p][t]);
                    TotalProdCost.AddTerm(_prodCost[p], Make[p][t]);
                    TotalInvCost.AddTerm(_invCost[p], Inv[p][t]);
                }
            }

            cplex.AddMaximize(cplex.Diff(TotalRevenue,
                                         cplex.Sum(TotalProdCost, TotalInvCost)));

            // TIME AVAILABILITY CONSTRAINTS

            for (int t = 0; t < _nTime; t++)
            {
                ILinearNumExpr availExpr = cplex.LinearNumExpr();
                for (int p = 0; p < _nProd; p++)
                {
                    availExpr.AddTerm(1.0 / _rate[p], Make[p][t]);
                }
                cplex.AddLe(availExpr, _avail[t]);
            }

            // MATERIAL BALANCE CONSTRAINTS

            for (int p = 0; p < _nProd; p++)
            {
                cplex.AddEq(cplex.Sum(Make[p][0], _inv0[p]),
                            cplex.Sum(Sell[p][0], Inv[p][0]));
                for (int t = 1; t < _nTime; t++)
                {
                    cplex.AddEq(cplex.Sum(Make[p][t], Inv[p][t - 1]),
                                cplex.Sum(Sell[p][t], Inv[p][t]));
                }
            }

            cplex.ExportModel("steel.lp");

            if (cplex.Solve())
            {
                System.Console.WriteLine("Solution status = " + cplex.GetStatus());
                System.Console.WriteLine();
                System.Console.WriteLine("Total Profit = " + cplex.ObjValue);

                System.Console.WriteLine();
                System.Console.WriteLine("\tp\tt\tMake\tInv\tSell");

                for (int p = 0; p < _nProd; p++)
                {
                    for (int t = 0; t < _nTime; t++)
                    {
                        System.Console.WriteLine("\t" + p + "\t" + t + "\t" + cplex.GetValue(Make[p][t]) +
                                                 "\t" + cplex.GetValue(Inv[p][t]) + "\t" + cplex.GetValue(Sell[p][t]));
                    }
                }
            }
            cplex.End();
        }
        catch (ILOG.Concert.Exception exc) {
            System.Console.WriteLine("Concert exception '" + exc + "' caught");
        }
        catch (System.IO.IOException exc) {
            System.Console.WriteLine("Error reading file " + args[0] + ": " + exc);
        }
        catch (InputDataReader.InputDataReaderException exc) {
            System.Console.WriteLine(exc);
        }
    }
Пример #18
0
    public static void Main(string[] args)
    {
        try {
         string filename = "../../../../examples/data/steel.dat";
         if ( args.Length > 0 )
            filename = args[0];
         ReadData(filename);

         Cplex cplex = new Cplex();

         // VARIABLES
         INumVar[][] Make = new INumVar[_nProd][];
         for (int p = 0; p < _nProd; p++) {
            Make[p] = cplex.NumVarArray(_nTime, 0.0, System.Double.MaxValue);
         }

         INumVar[][] Inv = new INumVar[_nProd][];
         for (int p = 0; p < _nProd; p++) {
            Inv[p] = cplex.NumVarArray(_nTime, 0.0, System.Double.MaxValue);
         }

         INumVar[][] Sell = new INumVar[_nProd][];
         for (int p = 0; p < _nProd; p++) {
             Sell[p] = new INumVar[_nTime];
            for (int t = 0; t < _nTime; t++) {
               Sell[p][t] = cplex.NumVar(0.0, _market[p][t]);
            }
         }

         // OBJECTIVE
         ILinearNumExpr TotalRevenue  = cplex.LinearNumExpr();
         ILinearNumExpr TotalProdCost = cplex.LinearNumExpr();
         ILinearNumExpr TotalInvCost  = cplex.LinearNumExpr();

         for (int p = 0; p < _nProd; p++) {
            for (int t = 1; t < _nTime; t++) {
               TotalRevenue.AddTerm (_revenue[p][t], Sell[p][t]);
               TotalProdCost.AddTerm(_prodCost[p], Make[p][t]);
               TotalInvCost.AddTerm (_invCost[p], Inv[p][t]);
            }
         }

         cplex.AddMaximize(cplex.Diff(TotalRevenue,
                                      cplex.Sum(TotalProdCost, TotalInvCost)));

         // TIME AVAILABILITY CONSTRAINTS

         for (int t = 0; t < _nTime; t++) {
            ILinearNumExpr availExpr = cplex.LinearNumExpr();
            for (int p = 0; p < _nProd; p++) {
               availExpr.AddTerm(1.0/_rate[p], Make[p][t]);
            }
            cplex.AddLe(availExpr, _avail[t]);
         }

         // MATERIAL BALANCE CONSTRAINTS

         for (int p = 0; p < _nProd; p++) {
            cplex.AddEq(cplex.Sum(Make[p][0], _inv0[p]),
                        cplex.Sum(Sell[p][0], Inv[p][0]));
            for (int t = 1; t < _nTime; t++) {
               cplex.AddEq(cplex.Sum(Make[p][t], Inv[p][t-1]),
                           cplex.Sum(Sell[p][t], Inv[p][t]));
            }
         }

         cplex.ExportModel("steel.lp");

         if ( cplex.Solve() ) {
            System.Console.WriteLine("Solution status = " + cplex.GetStatus());
            System.Console.WriteLine();
            System.Console.WriteLine("Total Profit = " + cplex.ObjValue);

            System.Console.WriteLine();
            System.Console.WriteLine("\tp\tt\tMake\tInv\tSell");

            for (int p = 0; p < _nProd; p++) {
               for (int t = 0; t < _nTime; t++) {
                  System.Console.WriteLine("\t" + p +"\t" + t +"\t" + cplex.GetValue(Make[p][t]) +
                                           "\t" + cplex.GetValue(Inv[p][t]) +"\t" + cplex.GetValue(Sell[p][t]));
               }
            }
         }
         cplex.End();
          }
          catch (ILOG.Concert.Exception exc) {
         System.Console.WriteLine("Concert exception '" + exc + "' caught");
          }
          catch (System.IO.IOException exc) {
         System.Console.WriteLine("Error reading file " + args[0] + ": " + exc);
          }
          catch (InputDataReader.InputDataReaderException exc) {
         System.Console.WriteLine(exc);
          }
    }
Пример #19
0
        //A quadratic interger program for graph matching,
        //When tuned with the right similarity function it can represent the GED problem.
        // See Pattern Reocgnition Paper paper On the unification of graph matching and graph edit distance paper.
        //The directed version has not been tested yet
        public override void QAPGMGED()
        {
            //some important variables
            int nbNode1       = graph1.ListNodes.Count;
            int nbNode2       = graph2.ListNodes.Count;
            int nbvar         = nbNode1 * nbNode2; // number of variables
            int nbcontraintes = nbNode1 + nbNode2; // number of constraints

            Graphs.Label nodeepslabel;

            //Adjacency matrices
            MatrixLibrary.Matrix adj1 = graph1.calculateAdjacencyMatrix();
            MatrixLibrary.Matrix adj2 = graph2.calculateAdjacencyMatrix();
            //Similarity matrix
            Double[,] S = new Double[nbvar, nbvar];

            //Creation of the Similarity matrix
            //4 for loops integrated
            int countrow = -1;

            for (int i = 0; i < nbNode1; i++)
            {
                Node nodei = graph1.ListNodes[i];
                for (int k = 0; k < nbNode2; k++)
                {
                    Node nodek = graph2.ListNodes[k];
                    countrow = countrow + 1;
                    int countcol = -1;
                    for (int j = 0; j < nbNode1; j++)
                    {
                        Node nodej = graph1.ListNodes[j];
                        for (int l = 0; l < nbNode2; l++)
                        {
                            Node nodel = graph2.ListNodes[l];
                            countcol = countcol + 1;
                            if (i == j && k == l) // Similarity between nodes
                            {
                                Type   typeLabel = nodei.Label.GetType();
                                object obj       = Activator.CreateInstance(typeLabel);
                                nodeepslabel    = (Graphs.Label)obj;
                                nodeepslabel.Id = ConstantsAC.EPS_ID;

                                double costsub = nodei.Label.dissimilarity(nodek.Label);
                                double costdel = nodei.Label.dissimilarity(nodeepslabel);
                                double costins = nodeepslabel.dissimilarity(nodek.Label);
                                double cost    = costsub - costdel - costins;
                                cost *= -1;

                                S[countrow, countcol] = cost;
                            }
                            else // Similarity between edges
                            {
                                int connect1 = (int)adj1[i, j];
                                int connect2 = (int)adj2[k, l];
                                if (connect1 == 1 && connect2 == 1) // Two edges are connected
                                {
                                    Edge ij = findedge(nodei, nodej);
                                    Edge kl = findedge(nodek, nodel);


                                    Type   typeLabel = ij.Label.GetType();
                                    object obj       = Activator.CreateInstance(typeLabel);
                                    nodeepslabel    = (Graphs.Label)obj;
                                    nodeepslabel.Id = ConstantsAC.EPS_ID;

                                    double costsub = ij.Label.dissimilarity(kl.Label);
                                    double costdel = ij.Label.dissimilarity(nodeepslabel);
                                    double costins = nodeepslabel.dissimilarity(kl.Label);
                                    double cost    = costsub - costdel - costins;
                                    cost *= -1;
                                    //cost *= 0.5;
                                    S[countrow, countcol] = cost;
                                }
                            }
                        }
                    }
                }
            }


            //We compute the constant that represents the
            //deletion and insertion of the nodes and edges

            //deletions of the nodes of g1
            double constante = 0;

            for (int i = 1; i <= nbNode1; i++)
            {
                Type   typeLabel = graph1.ListNodes[i - 1].Label.GetType();
                object obj       = Activator.CreateInstance(typeLabel);
                nodeepslabel    = (Graphs.Label)obj;
                nodeepslabel.Id = ConstantsAC.EPS_ID;
                constante      += (graph1.ListNodes[i - 1].Label).dissimilarity(nodeepslabel);
            }

            //deletions of the edges of g1
            for (int ij = 1; ij <= nbEdge1; ij++)
            {
                Type   typeLabel = graph1.ListEdges[ij - 1].Label.GetType();
                object obj       = Activator.CreateInstance(typeLabel);
                nodeepslabel    = (Graphs.Label)obj;
                nodeepslabel.Id = ConstantsAC.EPS_ID;
                double costEdge = (graph1.ListEdges[ij - 1].Label).dissimilarity(nodeepslabel);
                constante += costEdge;
            }

            //insertions of the nodes of g2
            for (int k = 1; k <= nbNode2; k++)
            {
                Type   typeLabel = graph2.ListNodes[k - 1].Label.GetType();
                object obj       = Activator.CreateInstance(typeLabel);
                nodeepslabel    = (Graphs.Label)obj;
                nodeepslabel.Id = ConstantsAC.EPS_ID;
                constante      += (graph2.ListNodes[k - 1].Label).dissimilarity(nodeepslabel);
            }

            //insertions of the edges of g2
            for (int kl = 1; kl <= nbEdge2; kl++)
            {
                Type   typeLabel = graph2.ListEdges[kl - 1].Label.GetType();
                object obj       = Activator.CreateInstance(typeLabel);
                nodeepslabel    = (Graphs.Label)obj;
                nodeepslabel.Id = ConstantsAC.EPS_ID;
                double costEdge = (graph2.ListEdges[kl - 1].Label).dissimilarity(nodeepslabel);
                constante += costEdge;
            }

            // the number of variables is the number of columns
            int nbCols = nbvar;
            // the number of constraints is the number of rows
            int           nbRows      = nbcontraintes;
            List <string> colNameList = new List <string>();


            //We create the name of the vrariables for all couples of nodes in g1 and g2
            for (int i = 0; i < nbNode1; i++)
            {
                for (int k = 0; k < nbNode2; k++)
                {
                    colNameList.Add("x_" + graph1.ListNodes[i].Id + "," + graph2.ListNodes[k].Id + "");
                }
            }
            try
            {
                cplex = new Cplex();                                         // creation du modèle CPLEX

                this.ilpMatrix = cplex.AddLPMatrix();                        // matrice du pb (initialisée à 0 colonnes et 0 lignes)

                ColumnArray colonnes = cplex.ColumnArray(ilpMatrix, nbCols); // définition des variables-colonnes du pb

                // ajout des variables-colonnes dans la matrice du pb
                // y is a vector
                INumVar[] y = cplex.NumVarArray(colonnes, 0, 1, NumVarType.Bool, colNameList.ToArray());


                #region création fonction objectif

                // CALCUL DES COEFFICIENTS
                // We create the ojective function
                INumExpr[] coeffs_expr = new INumExpr[nbvar * nbvar]; // vecteur des coeffs des coûts des arrêtes

                int count = 0;
                for (int ik = 0; ik < nbvar; ik++)
                {
                    for (int jl = 0; jl < nbvar; jl++)
                    {
                        coeffs_expr[count] = cplex.Prod(y[ik], y[jl]);
                        coeffs_expr[count] = cplex.Prod(S[ik, jl], coeffs_expr[count]);
                        count = count + 1;
                    }
                }
                INumExpr ff = cplex.Sum(coeffs_expr);
                INumExpr gg = cplex.Sum(ff, cplex.Constant(-constante));
                cplex.AddMaximize(gg);
                #endregion


                #region définition des contraintes du pb

                // We create the constraints

                // The sum of x variables by rows

                for (int i = 0; i < nbNode1; i++)
                {
                    INumVar[] sommeLignes = new INumVar[nbNode2];
                    for (int k = 0; k < nbNode2; k++)
                    {
                        string nameVarik = "x_" + i + "," + k;
                        int    indexik   = SolverCPLEX.GetIndexByName(y, nameVarik);
                        sommeLignes[k] = y[indexik];
                    }
                    cplex.AddLe(cplex.Sum(sommeLignes), 1);
                }

                // The sum of x variables by columns
                for (int k = 0; k < nbNode2; k++)
                {
                    INumVar[] sommeLignes = new INumVar[nbNode1];
                    for (int i = 0; i < nbNode1; i++)
                    {
                        string nameVarik = "x_" + i + "," + k;
                        int    indexik   = SolverCPLEX.GetIndexByName(y, nameVarik);
                        sommeLignes[i] = y[indexik];
                    }
                    cplex.AddLe(cplex.Sum(sommeLignes), 1);
                }



                #endregion
            }
            catch (ILOG.Concert.Exception e)
            {
                System.Console.WriteLine("Concert exception `" + e + "` caught");
            }
        }
Пример #20
0
        private double one_tsp(int dim, int [][] matrix, int [] path)
        {
            int[] lo = new int[dim];

            for (int i = 0; i < dim; i++)
            {
                lo[i] = 1;
            }

            Cplex      cplex   = new Cplex();
            NumVarType varType = NumVarType.Bool;

            INumVar[][] x = new INumVar[dim][];
            for (int i = 0; i < dim; i++)
            {
                x[i] = cplex.NumVarArray(dim, 0, 1);
            }

            for (int i = 0; i < dim; i++)
            {
                for (int j = 0; j < dim; j++)
                {
                    x[i][j] = cplex.BoolVar();
                }
            }

            for (int j = 0; j < dim; j++)
            {
                INumExpr xcolSum = cplex.NumExpr();
                for (int i = 0; i < dim; i++)
                {
                    xcolSum = cplex.Sum(xcolSum, x[i][j]);
                }
                cplex.AddEq(lo[j], xcolSum);
            }

            varType = NumVarType.Float;
            INumVar[] u = new INumVar[dim];
            for (int j = 0; j < dim; j++)
            {
                u[j] = cplex.NumVar(0, 100000);
            }

            for (int j = 1; j < dim; j++)
            {
                cplex.AddGe(u[j], 0);
            }

            for (int i = 1; i < dim; i++)
            {
                for (int j = 1; j < dim; j++)
                {
                    if (i != j)
                    {
                        cplex.AddLe(cplex.Sum(cplex.Diff(u[i], u[j]), cplex.Prod(dim, x[i][j])), dim - 1);
                    }
                }
            }

            for (int i = 0; i < dim; i++)
            {
                INumExpr xrowSum = cplex.NumExpr();
                for (int j = 0; j < dim; j++)
                {
                    xrowSum = cplex.Sum(xrowSum, x[i][j]);
                }
                cplex.AddEq(lo[i], xrowSum);
            }

            INumExpr costSum = cplex.NumExpr();

            for (int i = 0; i < dim; i++)
            {
                for (int j = 0; j < dim; j++)
                {
                    costSum = cplex.Sum(costSum, cplex.Prod(x[i][j], matrix[i][j]));
                }
            }
            cplex.AddMinimize(costSum);

            try
            {
                if (cplex.Solve())
                {
                    //MessageBox.Show("Solution status = " + cplex.GetStatus());
                    //MessageBox.Show("cost = " + cplex.ObjValue);
                    int ipath = 0;
                    int depo  = -1;
                    for (int i = dim - 1; i >= 0; i--)
                    {
                        for (int j = 0; j < dim; j++)
                        {
                            if (Convert.ToInt16(cplex.GetValue(x[i][j])) == 1)
                            {
                                depo = i;
                            }
                        }
                    }
                    path[ipath] = depo;
                    ipath++;
                    while (depo > -1)
                    {
                        for (int j = 0; j < dim; j++)
                        {
                            if (Convert.ToInt16(cplex.GetValue(x[path[ipath - 1]][j])) == 1)
                            {
                                path[ipath] = j;
                                ipath++;
                                if (j == depo)
                                {
                                    depo = -1;
                                }
                                break;
                            }
                        }
                    }
                    return(cplex.ObjValue);
                }
                cplex.End();
            }
            catch (ILOG.Concert.Exception ex)
            {
                System.Console.WriteLine("Concert Error: " + ex);
            }
            return(-1);
        }
Пример #21
0
        static void Main(string[] args)
        {
            try
            {
                graphFile = args[0];
                int   timeLimit = Convert.ToInt32(args[1]);
                Timer myTimer   = new Timer();
                myTimer.Start();
                myTimer.Interval = timeLimit * 1000;
                startTime        = DateTime.Now;
                myTimer.Elapsed += MyTimer_Elapsed;
                MyGraph graph            = new MyGraph(graphFile, "DIMACS");
                int     maxTime          = 100;
                int     targetCliqueSize = graph.NumberNodes;
                //Эвристически найдем хотя бы что-то похожее на максимальную клику (в пределах 5% ошибки - чтобы вернуть, если не успеет обсчитаться основной обход)
                maxClique = FindMaxClique(graph, maxTime, targetCliqueSize);
                int ub = maxClique.Count;
                Bound = ub;
                List <List <int> > clique = new List <List <int> >();
                //Сортируем вершины по числу соседей, будем вызывать алгоритм для тех вершин, у которых количество соседей наибольшее
                Dictionary <int, int> nodeAndNeighbors = new Dictionary <int, int>();
                for (int i = 0; i < graph.NumberNodes; ++i)
                {
                    int numberNeighbors = graph.NumberNeighbors(i);
                    nodeAndNeighbors.Add(i, numberNeighbors);
                }
                //Сортируем вершины по уменьшению количества соседей
                nodeAndNeighbors = nodeAndNeighbors.OrderByDescending(pair => pair.Value).ToDictionary(pair => pair.Key, pair => pair.Value);
                List <int> colors = new List <int>()
                {
                    1
                };
                //Раскраска графа
                int top = (from v in nodeAndNeighbors.Keys.ToList() select v).ToList <int>()[0];
                Dictionary <int, int> colorizedGraph = new Dictionary <int, int>();
                //Раскрасим граф
                colorizedGraph = colorize(nodeAndNeighbors.Keys.ToList <int>(), graph);
                int cntr = 0;
                //Зададим базовую модель
                Cplex       cplex = new Cplex();
                IRange[][]  rng   = new IRange[1][];
                INumVar[][] var   = new INumVar[1][];
                rng[0] = new IRange[graph.NumberNodes * graph.NumberNodes];
                // add the objective function
                double[] objvals = new double[graph.NumberNodes];
                string[] varname = new string[graph.NumberNodes];
                for (int i = 0; i < graph.NumberNodes; i++)
                {
                    objvals[i] = 1.0;
                    varname[i] = "x" + (i + 1);
                }
                INumVar[] x = cplex.NumVarArray(graph.NumberNodes, 0.0, 1.0, varname);
                var[0] = x;
                //Ограничение, что х лежит от нуля до единицы задали при инициализации
                cplex.AddMaximize(cplex.ScalProd(x, objvals));
                //Получим номер максимального цвета = это количество цветов, в которые окрашен граф
                //Будем иметь в виду, что количество цветов - это верхняя оценка на размер клики, а найденная эвристически клика на первом этапе - нижняя оценка.
                int        colorCount     = colorizedGraph.Values.Max();
                List <int> colorizedNodes = new List <int>();
                int        pointer        = 1;
                //Добавим ограничение, что вершины, входящие в один цветовой класс, не связаны между собой
                for (int i = 1; i <= colorCount; ++i)
                {
                    colorizedNodes = (from t in colorizedGraph where t.Value == i select t.Key).ToList <int>();
                    if (colorizedNodes.Count() != 1)
                    {
                        INumExpr[] constraint = new INumExpr[colorizedNodes.Count()];
                        int        counter    = 0;
                        colorizedNodes.ForEach(node =>
                        {
                            constraint[counter] = cplex.Prod(1.0, x[node]);
                            counter++;
                        });
                        rng[0][pointer] = cplex.AddLe(cplex.Sum(constraint), 1.0, "c" + (pointer));
                        pointer++;
                    }
                }
                for (int i = 0; i < graph.NumberNodes; i++)
                {
                    for (int j = i + 1; j < graph.NumberNodes; j++)
                    {
                        if (!graph.AreAdjacent(i, j))
                        {
                            rng[0][pointer] = cplex.AddLe(cplex.Sum(cplex.Prod(1.0, x[i]), cplex.Prod(1.0, x[j])), 1.0, "c" + (pointer));
                            pointer++;
                        }
                    }
                }

                //------------------------------------------------------------------------
                //-----Пробуем решать задачу ровно до тех пор, пока не получим клику------
                //-----Помним про ограничения на размер клики-----------------------------
                int countOfConstraint = colorCount;
                globalClick = maxClique;
                Branching(cplex, x);
                cplex.End();
                ////Максимальная клика, которую можно найти для вершины - это количество различных цветов, в которые окрашены все ее соседи плюс она  сама
                //foreach (KeyValuePair<int,int> pair in nodeAndNeighbors)
                //{
                //        List<int> neighbors = graph.GetNeighbors(pair.Key);
                //        neighbors.Add(pair.Key);
                //        var cols = (from n in colorizedGraph where neighbors.Exists(t => t == n.Key) select n.Value).Distinct().ToList<int>();
                //        if (cols.Count() >= Bound && cols.Count() >= globalClick.Count())
                //        {
                //            clique.Add(new List<int>());
                //            List<int> cur = new List<int>();
                //            RecursiveSearch(pair.Key, ref cur, ref neighbors, graph);
                //            clique[cntr] = cur;
                //            cntr++;
                //        }
                //}
                TimeSpan time = (DateTime.Now - startTime);
                Console.WriteLine("Time to find " + time);
                Console.WriteLine(globalClick.Count());
                Console.WriteLine(String.Join(" ", globalClick));
                WriteResults(time, globalClick, false);
            }
            catch (System.Exception ex)
            {
                Console.WriteLine("Fatal: " + ex.Message);
                Console.WriteLine(ex.StackTrace);
                Console.ReadKey();
            }
        }
Пример #22
0
        /// <summary>
        /// return a list of words that can be played, left over letters are the last word
        /// </summary>
        /// <param name="chips">All of the chips to conisder, first ones are on the board</param>
        /// <param name="numberOnBoard">The number of leading chips are on the board already</param>
        /// <returns></returns>
        public static List <Chip[]> Solve(List <Chip> chips, int numberOnBoard, bool suppress = true)
        {
            if (chips == null || chips.Count == 0)
            {
                Utility.Warning("Chips is null or empty!");
                return(null);
            }

            int chip_count = chips.Count;
            int word_count = chip_count / 3 + 1;

            Cplex model = new Cplex();

            IIntVar[]   X  = model.BoolVarArray(chip_count);    // should we place the ith chip
            IIntVar[][] Y  = new IIntVar[chip_count][];         // which word do we place the ith chip on
            IIntVar[]   WO = model.BoolVarArray(word_count);    // flag for if the jth word is an order word or not
            IIntVar[]   WC = model.BoolVarArray(word_count);    // flag for if the jth word is a color word or not
            IIntVar[]   WN = model.BoolVarArray(word_count);    // flag for if the jth word is not used or is used
            IIntVar[][] UO = new IIntVar[word_count][];         // what is the number associated with this word (used only if a color word)
            IIntVar[][] UC = new IIntVar[word_count][];         // what is the color associated with this word (used only if a order word)
            IIntVar[][] PC = new IIntVar[word_count][];         // if i maps to word j and j is a color word, this will be 1 at [j][i]
            IIntVar[][] PO = new IIntVar[word_count][];         // if i maps to word j and j is a order word, this will be 1 at [j][i] (if and only if)

            // Initialize
            for (int i = 0; i < chip_count; i++)
            {
                Y[i] = model.BoolVarArray(word_count);
            }

            for (int i = 0; i < word_count; i++)
            {
                UC[i] = model.BoolVarArray(Chip.COLORCOUNT);
            }

            for (int i = 0; i < word_count; i++)
            {
                UO[i] = model.BoolVarArray(Chip.NUMBERCOUNT);
            }

            for (int i = 0; i < word_count; i++)
            {
                PC[i] = model.BoolVarArray(chip_count);
            }

            for (int i = 0; i < word_count; i++)
            {
                PO[i] = model.BoolVarArray(chip_count);
            }

            // for each word which chips map to it
            IIntVar[][] Yt = new IIntVar[word_count][];
            for (int i = 0; i < word_count; i++)
            {
                Yt[i] = new IIntVar[chip_count];
                for (int j = 0; j < chip_count; j++)
                {
                    Yt[i][j] = Y[j][i];
                }
            }

            // maximize the number of placed chips
            model.AddMaximize(model.Sum(X));

            // if we place i, we need to map it to some word
            for (int i = 0; i < chip_count; i++)
            {
                model.AddLe(X[i], model.Sum(Y[i]));
            }

            // we can map to at most 1 value
            for (int i = 0; i < chip_count; i++)
            {
                model.AddLe(model.Sum(Y[i]), 1);
            }

            // if any chip maps to word j, turn the not used flag off
            for (int j = 0; j < word_count; j++)
            {
                for (int i = 0; i < chip_count; i++)
                {
                    model.AddLe(Y[i][j], model.Diff(1, WN[j]));
                }
            }

            // if a word is used, make sure it has at least 3 chips
            for (int j = 0; j < word_count; j++)
            {
                model.AddLe(model.Prod(3, model.Diff(1, WN[j])), model.Sum(Yt[j]));
            }

            // first 'numberOnBoard' chips are on the board and thus must be placed
            for (int i = 0; i < numberOnBoard; i++)
            {
                model.AddEq(X[i], 1);
            }

            // each word is either an order word or a color word
            for (int i = 0; i < word_count; i++)
            {
                model.AddEq(model.Sum(WO[i], WC[i], WN[i]), 1);
            }

            // if i maps to word j and j is a color word make sure PC[j][i] is 1
            for (int j = 0; j < word_count; j++)
            {
                for (int i = 0; i < chip_count; i++)
                {
                    model.AddGe(model.Sum(1, PC[j][i]), model.Sum(WC[j], Y[i][j]));
                }
            }

            // if i maps to word j and j is a order word, PO will be 1 at [j][i] (if and only if)
            for (int j = 0; j < word_count; j++)
            {
                for (int i = 0; i < chip_count; i++)
                {
                    model.AddGe(model.Sum(1, PO[j][i]), model.Sum(WO[j], Y[i][j]));
                    model.AddLe(PO[j][i], WO[j]);
                    model.AddLe(PO[j][i], Y[i][j]);
                }
            }

            // ************************************************
            // ************ TYPE CONSTRAINTS ******************
            // ************************************************

            for (int i = 0; i < chip_count; i++)
            {
                for (int j = 0; j < word_count; j++)
                {
                    // if this is a color word and a chip maps to it then the numbers of each chip on this word must match
                    for (int k = 0; k < Chip.NUMBERCOUNT; k++)
                    {
                        var bnd = model.Sum(WO[j], model.Diff(1, Y[i][j]));
                        model.AddLe(model.Diff(UO[j][k], chips[i].number[k] ? 1 : 0), bnd);
                        model.AddLe(model.Diff(chips[i].number[k] ? 1 : 0, UO[j][k]), bnd);
                    }

                    // if this is a order word and a chip maps to it then the colors of each chip on this word must match
                    for (int k = 0; k < Chip.COLORCOUNT; k++)
                    {
                        var bnd = model.Sum(WC[j], model.Diff(1, Y[i][j]));
                        model.AddLe(model.Diff(UC[j][k], chips[i].color[k] ? 1 : 0), bnd);
                        model.AddLe(model.Diff(chips[i].color[k] ? 1 : 0, UC[j][k]), bnd);
                    }
                }
            }

            // if this is a color word, ensure that at most one of each color is allowed
            for (int j = 0; j < word_count; j++)
            {
                for (int k = 0; k < Chip.COLORCOUNT; k++)
                {
                    int[] colstack = new int[chip_count];
                    for (int i = 0; i < chip_count; i++)
                    {
                        colstack[i] = chips[i].color[k] ? 1 : 0;
                    }

                    model.Add(model.IfThen(model.Eq(WC[j], 1), model.Le(model.ScalProd(colstack, PC[j]), 1)));
                }
            }

            // ensure that the numbers in an order word are sequential
            for (int j = 0; j < word_count; j++)
            {
                IIntVar[] V = model.BoolVarArray(Chip.NUMBERCOUNT);
                for (int k = 0; k < Chip.NUMBERCOUNT; k++)
                {
                    int[] numstack = new int[chip_count];
                    for (int i = 0; i < chip_count; i++)
                    {
                        numstack[i] = chips[i].number[k] ? 1 : 0;
                    }

                    // if this is an order word put the binary numbers into a vector of flags for those numbers
                    model.Add(model.IfThen(model.Eq(WO[j], 1), model.Eq(model.ScalProd(numstack, PO[j]), V[k])));
                }

                // for each number either the next flag is strictly larger, meaning the start of the sequence
                // or every flag after a decrease is 0, the end of a sequence
                for (int i = 0; i < Chip.NUMBERCOUNT - 1; i++)
                {
                    IIntVar Z = model.BoolVar();
                    model.AddLe(model.Diff(V[i], V[i + 1]), Z);

                    for (int k = i + 1; k < Chip.NUMBERCOUNT; k++)
                    {
                        model.AddLe(V[k], model.Diff(1, Z));
                    }
                }
            }

            List <Chip[]> words = new List <Chip[]>();

            if (suppress)
            {
                model.SetOut(null);
            }

            Utility.Log("Thinking...");

            if (model.Solve())
            {
                for (int j = 0; j < word_count; j++)
                {
                    if (model.GetValue(WN[j]) > 0.5)
                    {
                        continue;
                    }

                    List <Chip> word  = new List <Chip>();
                    double[]    flags = model.GetValues(Yt[j]);
                    for (int i = 0; i < chip_count; i++)
                    {
                        if (flags[i] > 0.5)
                        {
                            word.Add(chips[i]);
                        }
                    }

                    // if this is a color word else it is an order word
                    if (model.GetValue(WC[j]) > 0.5)
                    {
                        words.Add(word.OrderBy(p => Array.IndexOf(p.color, true)).ToArray());
                    }
                    else
                    {
                        words.Add(word.OrderBy(p => Array.IndexOf(p.number, true)).ToArray());
                    }
                }
            }
            else
            {
                Utility.Warning("No possible moves found!");
            }

            model.Dispose();

            Chip[] notplayed = chips.Where(p => !words.Any(q => q.Contains(p))).ToArray();
            words.Add(notplayed);

            return(words);
        }
Пример #23
0
   public static void Main (string[] args) {
      int nMonths   = cost.Length;
      int nProducts = cost[0].Length;

      try {
         Cplex cplex = new Cplex();

         INumVar[]   produce = cplex.NumVarArray(nMonths, 0, System.Double.MaxValue);
         INumVar[][] use   = new INumVar[nMonths][];
         INumVar[][] buy   = new INumVar[nMonths][];
         INumVar[][] store = new INumVar[nMonths][];

         for (int i = 0; i < nMonths; i++) {
            use[i]   = cplex.NumVarArray(nProducts, 0.0, System.Double.MaxValue);
            buy[i]   = cplex.NumVarArray(nProducts, 0.0, System.Double.MaxValue);
            store[i] = cplex.NumVarArray(nProducts, 0.0, 1000.0);
         }

         for (int p = 0; p < nProducts; p++) {
           store[nMonths-1][p].LB = 500.0;
           store[nMonths-1][p].UB = 500.0;
         }

         INumExpr profit = cplex.NumExpr();
         for (int i = 0; i < nMonths; i++) {
            // Not more than 200 tons of vegetable oil can be refined
            cplex.AddLe(cplex.Sum(use[i][v1], use[i][v2]), 200.0);

            // Not more than 250 tons of non-vegetable oil can be refined
            cplex.AddLe(cplex.Sum(use[i][o1], use[i][o2], use[i][o3]), 250.0);

            // Constraints on food composition
            cplex.AddLe(cplex.Prod(3.0,produce[i]),
                        cplex.Sum(cplex.Prod(8.8, use[i][v1]),
                                  cplex.Prod(6.1, use[i][v2]),
                                  cplex.Prod(2.0, use[i][o1]),
                                  cplex.Prod(4.2, use[i][o2]),
                                  cplex.Prod(5.0, use[i][o3])));
            cplex.AddGe(cplex.Prod(6.0, produce[i]),
                        cplex.Sum(cplex.Prod(8.8, use[i][v1]),
                                  cplex.Prod(6.1, use[i][v2]),
                                  cplex.Prod(2.0, use[i][o1]),
                                  cplex.Prod(4.2, use[i][o2]),
                                  cplex.Prod(5.0, use[i][o3])));
            cplex.AddEq(produce[i], cplex.Sum(use[i]));

            // Raw oil can be stored for later use
            if (i == 0) {
               for (int p = 0; p < nProducts; p++)
                  cplex.AddEq(cplex.Sum(500.0, buy[i][p]),
                              cplex.Sum(use[i][p], store[i][p]));
            }
            else {
               for (int p = 0; p < nProducts; p++)
                 cplex.AddEq(cplex.Sum(store[i-1][p], buy[i][p]),
                             cplex.Sum(use[i][p], store[i][p]));
            }

            // Logical constraints:
            // The food cannot use more than 3 oils
            // (or at least two oils must not be used)
            cplex.AddGe(cplex.Sum(cplex.Eq(use[i][v1], 0),
                                  cplex.Eq(use[i][v2], 0),
                                  cplex.Eq(use[i][o1], 0),
                                  cplex.Eq(use[i][o2], 0),
                                  cplex.Eq(use[i][o3], 0)), 2);

            // When an oil is used, the quantity must be at least 20 tons
            for (int p = 0; p < nProducts; p++)
               cplex.Add(cplex.Or(cplex.Eq(use[i][p],  0),
                                  cplex.Ge(use[i][p], 20)));

            // If products v1 or v2 are used, then product o3 is also used
            cplex.Add(cplex.IfThen(cplex.Or(cplex.Ge(use[i][v1], 20),
                                            cplex.Ge(use[i][v2], 20)),
                                   cplex.Ge(use[i][o3], 20)));

            // Objective function
            profit = cplex.Sum (profit, cplex.Prod(150, produce[i]));
            profit = cplex.Diff(profit, cplex.ScalProd(cost[i], buy[i]));
            profit = cplex.Diff(profit, cplex.Prod(5, cplex.Sum(store[i])));
         }

         cplex.AddMaximize(profit);

         if ( cplex.Solve() ) {
            System.Console.WriteLine("Solution status = " + cplex.GetStatus());
            System.Console.WriteLine(" Maximum profit = " + cplex.ObjValue);
            for (int i = 0; i < nMonths; i++) {
               System.Console.WriteLine(" Month {0}", i);

               System.Console.Write("  . buy   ");
               for (int p = 0; p < nProducts; p++)
                  System.Console.Write("{0,8:F2} ", cplex.GetValue(buy[i][p]));
               System.Console.WriteLine();

               System.Console.Write("  . use   ");
               for (int p = 0; p < nProducts; p++)
                  System.Console.Write("{0,8:F2} ", cplex.GetValue(use[i][p]));
               System.Console.WriteLine();

               System.Console.Write("  . store ");
               for (int p = 0; p < nProducts; p++)
                  System.Console.Write("{0,8:F2} ", cplex.GetValue(store[i][p]));
               System.Console.WriteLine();
            }
         }
         cplex.End();
      }
      catch (ILOG.Concert.Exception e) {
         System.Console.WriteLine("Concert exception caught: " + e);
      }
   }
Пример #24
0
    /// <summary>
    /// The example's main function.
    /// </summary>
    public static void Main(string[] args)
    {
        int retval = 0;
        Cplex cplex = null;
        try
        {
            cplex = new Cplex();

            /* ***************************************************************** *
             *                                                                   *
             *    S E T U P   P R O B L E M                                      *
             *                                                                   *
             *  We create the following problem:                                 *
             * Minimize                                                          *
             *  obj: 3x1 - x2 + 3x3 + 2x4 + x5 + 2x6 + 4x7                       *
             * Subject To                                                        *
             *  c1: x1 + x2 = 4                                                  *
             *  c2: x1 + x3 >= 3                                                 *
             *  c3: x6 + x7 <= 5                                                 *
             *  c4: -x1 + x7 >= -2                                               *
             *  q1: [ -x1^2 + x2^2 ] <= 0                                        *
             *  q2: [ 4.25x3^2 -2x3*x4 + 4.25x4^2 - 2x4*x5 + 4x5^2  ] + 2 x1 <= 9.0
             *  q3: [ x6^2 - x7^2 ] >= 4                                         *
             * Bounds                                                            *
             *  0 <= x1 <= 3                                                     *
             *  x2 Free                                                          *
             *  0 <= x3 <= 0.5                                                   *
             *  x4 Free                                                          *
             *  x5 Free                                                          *
             *  x7 Free                                                          *
             * End                                                               *
             *                                                                   *
             * ***************************************************************** */

            INumVar[] x = new INumVar[7];
            x[0] = cplex.NumVar(0, 3, "x1");
            x[1] = cplex.NumVar(System.Double.NegativeInfinity, System.Double.PositiveInfinity, "x2");
            x[2] = cplex.NumVar(0, 0.5, "x3");
            x[3] = cplex.NumVar(System.Double.NegativeInfinity, System.Double.PositiveInfinity, "x4");
            x[4] = cplex.NumVar(System.Double.NegativeInfinity, System.Double.PositiveInfinity, "x5");
            x[5] = cplex.NumVar(0, System.Double.PositiveInfinity, "x6");
            x[6] = cplex.NumVar(System.Double.NegativeInfinity, System.Double.PositiveInfinity, "x7");

            IRange[] linear = new IRange[4];
            linear[0] = cplex.AddEq(cplex.Sum(x[0], x[1]), 4.0, "c1");
            linear[1] = cplex.AddGe(cplex.Sum(x[0], x[2]), 3.0, "c2");
            linear[2] = cplex.AddLe(cplex.Sum(x[5], x[6]), 5.0, "c3");
            linear[3] = cplex.AddGe(cplex.Diff(x[6], x[0]), -2.0, "c4");

            IRange[] quad = new IRange[3];
            quad[0] = cplex.AddLe(cplex.Sum(cplex.Prod(-1, x[0], x[0]),
                                            cplex.Prod(x[1], x[1])), 0.0, "q1");
            quad[1] = cplex.AddLe(cplex.Sum(cplex.Prod(4.25, x[2], x[2]),
                cplex.Prod(-2,x[2],x[3]),
                cplex.Prod(4.25,x[3],x[3]),
                cplex.Prod(-2,x[3],x[4]),
                cplex.Prod(4,x[4],x[4]),
                cplex.Prod(2,x[0])), 9.0, "q2");
            quad[2] = cplex.AddGe(cplex.Sum(cplex.Prod(x[5], x[5]),
                                            cplex.Prod(-1, x[6], x[6])), 4.0, "q3");

            cplex.AddMinimize(cplex.Sum(cplex.Prod(3.0, x[0]),
                                        cplex.Prod(-1.0, x[1]),
                                        cplex.Prod(3.0, x[2]),
                                        cplex.Prod(2.0, x[3]),
                                        cplex.Prod(1.0, x[4]),
                                        cplex.Prod(2.0, x[5]),
                                        cplex.Prod(4.0, x[6])), "obj");

            /* ***************************************************************** *
             *                                                                   *
             *    O P T I M I Z E   P R O B L E M                                *
             *                                                                   *
             * ***************************************************************** */
            cplex.SetParam(Cplex.Param.Barrier.QCPConvergeTol, 1e-10);
            cplex.Solve();

            /* ***************************************************************** *
             *                                                                   *
             *    Q U E R Y   S O L U T I O N                                    *
             *                                                                   *
             * ***************************************************************** */
            double[] xval = cplex.GetValues(x);
            double[] slack = cplex.GetSlacks(linear);
            double[] qslack = cplex.GetSlacks(quad);
            double[] cpi = cplex.GetReducedCosts(x);
            double[] rpi = cplex.GetDuals(linear);
            double[] qpi = getqconstrmultipliers(cplex, xval, ZEROTOL, x, quad);
            // Also store solution in a dictionary so that we can look up
            // values by variable and not only by index.
            IDictionary<INumVar, System.Double> xmap = new Dictionary<INumVar, System.Double>();
            for (int j = 0; j < x.Length; ++j)
            {
                xmap.Add(x[j], xval[j]);
            }

            /* ***************************************************************** *
             *                                                                   *
             *    C H E C K   K K T   C O N D I T I O N S                        *
             *                                                                   *
             *    Here we verify that the optimal solution computed by CPLEX     *
             *    (and the qpi[] values computed above) satisfy the KKT          *
             *    conditions.                                                    *
             *                                                                   *
             * ***************************************************************** */

            // Primal feasibility: This example is about duals so we skip this test.

            // Dual feasibility: We must verify
            // - for <= constraints (linear or quadratic) the dual
            //   multiplier is non-positive.
            // - for >= constraints (linear or quadratic) the dual
            //   multiplier is non-negative.
            for (int i = 0; i < linear.Length; ++i)
            {
                if (linear[i].LB <= System.Double.NegativeInfinity)
                {
                    // <= constraint
                    if (rpi[i] > ZEROTOL)
                        throw new System.SystemException("Dual feasibility test failed for row " + linear[i]
                                                   + ": " + rpi[i]);
                }
                else if (linear[i].UB >= System.Double.PositiveInfinity)
                {
                    // >= constraint
                    if (rpi[i] < -ZEROTOL)
                        throw new System.SystemException("Dual feasibility test failed for row " + linear[i]
                                                   + ": " + rpi[i]);
                }
                else
                {
                    // nothing to do for equality constraints
                }
            }
            for (int i = 0; i < quad.Length; ++i)
            {
                if (quad[i].LB <= System.Double.NegativeInfinity)
                {
                    // <= constraint
                    if (qpi[i] > ZEROTOL)
                        throw new System.SystemException("Dual feasibility test failed for quad " + quad[i]
                                                   + ": " + qpi[i]);
                }
                else if (quad[i].UB >= System.Double.PositiveInfinity)
                {
                    // >= constraint
                    if (qpi[i] < -ZEROTOL)
                        throw new System.SystemException("Dual feasibility test failed for quad " + quad[i]
                                                   + ": " + qpi[i]);
                }
                else
                {
                    // nothing to do for equality constraints
                }
            }

            // Complementary slackness.
            // For any constraint the product of primal slack and dual multiplier
            // must be 0.
            for (int i = 0; i < linear.Length; ++i)
            {
                if (System.Math.Abs(linear[i].UB - linear[i].LB) > ZEROTOL &&
                     System.Math.Abs(slack[i] * rpi[i]) > ZEROTOL)
                    throw new System.SystemException("Complementary slackness test failed for row " + linear[i]
                                               + ": " + System.Math.Abs(slack[i] * rpi[i]));
            }
            for (int i = 0; i < quad.Length; ++i)
            {
                if (System.Math.Abs(quad[i].UB - quad[i].LB) > ZEROTOL &&
                     System.Math.Abs(qslack[i] * qpi[i]) > ZEROTOL)
                    throw new System.SystemException("Complementary slackness test failed for quad " + quad[i]
                                               + ": " + System.Math.Abs(qslack[i] * qpi[i]));
            }
            for (int j = 0; j < x.Length; ++j)
            {
                if (x[j].UB < System.Double.PositiveInfinity)
                {
                    double slk = x[j].UB - xval[j];
                    double dual = cpi[j] < -ZEROTOL ? cpi[j] : 0.0;
                    if (System.Math.Abs(slk * dual) > ZEROTOL)
                        throw new System.SystemException("Complementary slackness test failed for column " + x[j]
                                                   + ": " + System.Math.Abs(slk * dual));
                }
                if (x[j].LB > System.Double.NegativeInfinity)
                {
                    double slk = xval[j] - x[j].LB;
                    double dual = cpi[j] > ZEROTOL ? cpi[j] : 0.0;
                    if (System.Math.Abs(slk * dual) > ZEROTOL)
                        throw new System.SystemException("Complementary slackness test failed for column " + x[j]
                                                   + ": " + System.Math.Abs(slk * dual));
                }
            }

            // Stationarity.
            // The difference between objective function and gradient at optimal
            // solution multiplied by dual multipliers must be 0, i.E., for the
            // optimal solution x
            // 0 == c
            //      - sum(r in rows)  r'(x)*rpi[r]
            //      - sum(q in quads) q'(x)*qpi[q]
            //      - sum(c in cols)  b'(x)*cpi[c]
            // where r' and q' are the derivatives of a row or quadratic constraint,
            // x is the optimal solution and rpi[r] and qpi[q] are the dual
            // multipliers for row r and quadratic constraint q.
            // b' is the derivative of a bound constraint and cpi[c] the dual bound
            // multiplier for column c.
            IDictionary<INumVar, System.Double> kktsum = new Dictionary<INumVar, System.Double>();
            for (int j = 0; j < x.Length; ++j)
            {
                kktsum.Add(x[j], 0.0);
            }

            // Objective function.
            for (ILinearNumExprEnumerator it = ((ILinearNumExpr)cplex.GetObjective().Expr).GetLinearEnumerator();
                 it.MoveNext(); /* nothing */)
            {
                kktsum[it.NumVar] = it.Value;
            }

            // Linear constraints.
            // The derivative of a linear constraint ax - b (<)= 0 is just a.
            for (int i = 0; i < linear.Length; ++i)
            {
                for (ILinearNumExprEnumerator it = ((ILinearNumExpr)linear[i].Expr).GetLinearEnumerator();
                     it.MoveNext(); /* nothing */)
                {
                    kktsum[it.NumVar] = kktsum[it.NumVar] - rpi[i] * it.Value;
                }
            }

            // Quadratic constraints.
            // The derivative of a constraint xQx + ax - b <= 0 is
            // Qx + Q'x + a.
            for (int i = 0; i < quad.Length; ++i)
            {
                for (ILinearNumExprEnumerator it = ((ILinearNumExpr)quad[i].Expr).GetLinearEnumerator();
                     it.MoveNext(); /* nothing */)
                {
                    kktsum[it.NumVar] = kktsum[it.NumVar] - qpi[i] * it.Value;
                }
                for (IQuadNumExprEnumerator it = ((IQuadNumExpr)quad[i].Expr).GetQuadEnumerator();
                     it.MoveNext(); /* nothing */)
                {
                    INumVar v1 = it.NumVar1;
                    INumVar v2 = it.NumVar2;
                    kktsum[v1] = kktsum[v1] - qpi[i] * xmap[v2] * it.Value;
                    kktsum[v2] = kktsum[v2] - qpi[i] * xmap[v1] * it.Value;
                }
            }

            // Bounds.
            // The derivative for lower bounds is -1 and that for upper bounds
            // is 1.
            // CPLEX already returns dj with the appropriate sign so there is
            // no need to distinguish between different bound types here.
            for (int j = 0; j < x.Length; ++j)
            {
                kktsum[x[j]] = kktsum[x[j]] - cpi[j];
            }

            foreach (INumVar v in x)
            {
                if (System.Math.Abs(kktsum[v]) > ZEROTOL)
                    throw new System.SystemException("Stationarity test failed at " + v
                        + ": " + System.Math.Abs(kktsum[v]));
            }

            // KKT conditions satisfied. Dump out the optimal solutions and
            // the dual values.
            System.Console.WriteLine("Optimal solution satisfies KKT conditions.");
            System.Console.WriteLine("   x[] = " + arrayToString(xval));
            System.Console.WriteLine(" cpi[] = " + arrayToString(cpi));
            System.Console.WriteLine(" rpi[] = " + arrayToString(rpi));
            System.Console.WriteLine(" qpi[] = " + arrayToString(qpi));
        }
        catch (ILOG.Concert.Exception e)
        {
            System.Console.WriteLine("IloException: " + e.Message);
            System.Console.WriteLine(e.StackTrace);
            retval = -1;
        }
        finally
        {
            if (cplex != null)
                cplex.End();
        }
        System.Environment.Exit(retval);
    }
Пример #25
0
        void solve()
        {
            Cplex Model = new Cplex();

            // decision variables
            #region
            //x1-tjs (first stage t = 1),length of a collection period (in days) at collection point j during time period t
            //INumVar[][][] X1 = new INumVar[period][][];
            //for (int i = 0; i < period; i++)
            //{
            //    X1[i] = new INumVar[cpoint][];
            //    for (int ii = 0; ii < cpoint; ii++)
            //    {
            //        X1[i][ii] = new INumVar[scenario];
            //        X1[i][ii] = Model.NumVarArray(scenario, 1, 7, NumVarType.Int);
            //    }
            //}

            //x2-tpjks ,volume of products returned from collection point j to recycling center k during time period t
            INumVar[][][][][] X2 = new INumVar[period][][][][];
            for (int a = 0; a < period; a++)
            {
                X2[a] = new INumVar[ptype][][][];
                for (int aa = 0; aa < ptype; aa++)
                {
                    X2[a][aa] = new INumVar[cpoint][][];
                    for (int bb = 0; bb < cpoint; bb++)
                    {
                        X2[a][aa][bb] = new INumVar[rcenter][];
                        for (int cc = 0; cc < rcenter; cc++)
                        {
                            X2[a][aa][bb][cc] = new INumVar[scenario];
                            X2[a][aa][bb][cc] = Model.NumVarArray(scenario, 0, System.Double.MaxValue, NumVarType.Int);
                        }
                    }
                }
            }

            //x3-tij ,Binary decision variable equals ‘1’ if customer i is allocated to collection point j during time period t and ‘0’ otherwise
            INumVar[][][] X3 = new INumVar[period][][];
            for (int aa = 0; aa < period; aa++)
            {
                X3[aa] = new INumVar[customer][];
                for (int bb = 0; bb < customer; bb++)
                {
                    X3[aa][bb] = new INumVar[cpoint];
                    X3[aa][bb] = Model.NumVarArray(cpoint, 0.0, 1.0, NumVarType.Bool);
                }
            }


            //x4-tj ,Binary decision variable equals ‘1’ if collection point j is rented during time period t and ‘0’ otherwise
            INumVar[][] X4 = new INumVar[period][];
            for (int i = 0; i < period; i++)
            {
                X4[i] = new INumVar[cpoint];
                X4[i] = Model.NumVarArray(cpoint, 0.0, 1.0, NumVarType.Bool);
            }

            //x5-k ,Binary decision variable equals ‘1’ if recycling center k is established and ‘0’ otherwise
            INumVar[] X5 = new INumVar[rcenter];
            X5 = Model.NumVarArray(rcenter, 0, 1, NumVarType.Bool);

            //x6 maximum capacity level option for recycling center k
            INumVar[] X6 = new INumVar[rcenter];
            X6 = Model.NumVarArray(rcenter, 1, 3, NumVarType.Int);

            //X7-tjs Auxiliary variable  x7 the frequency of recylce during a period
            //INumVar[][][] X7 = new INumVar[period][][];
            //for (int i = 0; i < period; i++)
            //{
            //    X7[i] = new INumVar[cpoint][];
            //    for (int ii = 0; ii < cpoint; ii++)
            //    {
            //        X7[i][ii] = new INumVar[scenario];
            //        X7[i][ii] = Model.NumVarArray(scenario, 30, wday, NumVarType.Int);
            //    }
            //}

            #endregion

            Double M = 100000;

            // constraints
            #region
            // formulation (4)
            INumExpr[] expr1 = new INumExpr[1];

            for (int aa = 0; aa < period; aa++)
            {
                for (int bb = 0; bb < customer; bb++)
                {
                    expr1[0] = X3[0][0][0];
                    for (int cc = 0; cc < cpoint; cc++)
                    {
                        expr1[0] = Model.Sum(expr1[0], X3[aa][bb][cc]);
                    }
                    expr1[0] = Model.Sum(expr1[0], Model.Prod(-1.0, X3[0][0][0]));
                    Model.AddEq(expr1[0], 1);
                }
            }


            // formulation (5)
            INumExpr[] expr2 = new INumExpr[1];
            INumExpr[] expr3 = new INumExpr[1];
            for (int aa = 0; aa < period; aa++)
            {
                for (int bb = 0; bb < cpoint; bb++)
                {
                    expr2[0] = X3[0][0][0];
                    expr3[0] = X4[0][0];
                    for (int cc = 0; cc < customer; cc++)
                    {
                        Model.Sum(expr2[0], X3[aa][cc][bb]);
                    }
                    expr2[0] = Model.Sum(expr2[0], Model.Prod(-1.0, X3[0][0][0]));
                    expr3[0] = Model.Prod(M, X4[aa][bb]);
                    expr3[0] = Model.Sum(expr3[0], Model.Prod(-1.0, X4[0][0]));
                    Model.AddLe(expr2[0], expr3[0]);
                }
            }

            // formulation (6)
            INumExpr[] expr4 = new INumExpr[1];
            INumExpr[] expr5 = new INumExpr[1];
            INumExpr[] expr6 = new INumExpr[1];
            for (int aa = 0; aa < period; aa++)
            {
                for (int cc = 0; cc < scenario; cc++)
                {
                    for (int bb = 0; bb < cpoint; bb++)
                    {
                        expr5[0] = X3[0][0][0];
                        for (int dd = 0; dd < customer; dd++)
                        {
                            for (int ee = 0; ee < ptype; ee++)
                            {
                                expr5[0] = Model.Sum(expr5[0], Model.Prod(Model.Prod(r[dd, ee, aa, cc], X3[aa][dd][bb]), vlength));
                            }
                        }
                        expr5[0] = Model.Sum(expr5[0], Model.Prod(-1.0, X3[0][0][0]));

                        expr6[0] = X2[0][0][0][0][0];
                        for (int ff = 0; ff < rcenter; ff++)
                        {
                            for (int ee = 0; ee < ptype; ee++)
                            {
                                expr6[0] = Model.Sum(expr6[0], X2[aa][ee][bb][ff][cc]);
                            }
                        }
                        expr6[0] = Model.Sum(expr6[0], Model.Prod(-1.0, X2[0][0][0][0][0]));
                        Model.AddEq(expr5[0], expr6[0]);
                    }
                }
            }

            // formulation (7-1)
            INumExpr[] expr7 = new INumExpr[1];
            for (int aa = 0; aa < period; aa++)
            {
                for (int bb = 0; bb < rcenter; bb++)
                {
                    for (int cc = 0; cc < scenario; cc++)
                    {
                        for (int dd = 0; dd < cpoint; dd++)
                        {
                            expr7[0] = X2[0][0][0][0][0];
                            for (int ee = 0; ee < ptype; ee++)
                            {
                                expr7[0] = Model.Sum(expr7[0], X2[aa][ee][dd][bb][cc]);
                            }
                            expr7[0] = Model.Sum(expr7[0], Model.Prod(-1.0, X2[0][0][0][0][0]));
                            Model.AddLe(expr7[0], Model.Prod(X5[bb], M));
                        }
                    }
                }
            }

            // formulation (7-2)
            INumExpr[] expr71 = new INumExpr[1];
            for (int aa = 0; aa < period; aa++)
            {
                for (int bb = 0; bb < rcenter; bb++)
                {
                    for (int cc = 0; cc < scenario; cc++)
                    {
                        for (int dd = 0; dd < cpoint; dd++)
                        {
                            expr71[0] = X2[0][0][0][0][0];
                            for (int ee = 0; ee < ptype; ee++)
                            {
                                expr71[0] = Model.Sum(expr71[0], X2[aa][ee][dd][bb][cc]);
                            }
                            expr71[0] = Model.Sum(expr71[0], Model.Prod(-1.0, X2[0][0][0][0][0]));
                            Model.AddLe(expr71[0], Model.Sum(Model.Prod(X6[bb], 1000), Model.Prod(Model.Sum(1, Model.Prod(X5[bb], -1)), M)));
                        }
                    }
                }
            }

            // formulation (8)
            INumExpr[] expr8 = new INumExpr[1];
            for (int a = 0; a < period; a++)
            {
                expr8[0] = X4[0][0];
                for (int b = 0; b < cpoint; b++)
                {
                    expr8[0] = Model.Sum(expr8[0], X4[a][b]);
                }
                expr8[0] = Model.Sum(expr8[0], Model.Prod(-1.0, X4[0][0]));
                Model.AddGe(expr8[0], 1);
            }

            // formulation (9)
            INumExpr[] expr9 = new INumExpr[1];
            expr9[0] = X5[0];
            for (int a = 0; a < rcenter; a++)
            {
                expr9[0] = Model.Sum(expr9[0], X5[a]);
            }
            expr9[0] = Model.Sum(expr9[0], Model.Prod(-1.0, X5[0]));
            Model.AddGe(expr9[0], 1);

            // formulation (10)
            INumExpr[] expr10 = new INumExpr[1];
            for (int a = 0; a < period; a++)
            {
                for (int b = 0; b < rcenter; b++)
                {
                    for (int c = 0; c < scenario; c++)
                    {
                        for (int d = 0; d < cpoint; d++)
                        {
                            expr10[0] = X2[0][0][0][0][0];
                            for (int e = 0; e < ptype; e++)
                            {
                                expr10[0] = Model.Sum(expr10[0], X2[a][e][d][b][c]);
                            }
                            expr10[0] = Model.Sum(expr10[0], Model.Prod(-1.0, X2[0][0][0][0][0]));
                            Model.AddGe(expr10[0], X5[b]);
                        }
                    }
                }
            }


            // formulation (11)
            for (int a = 0; a < period; a++)
            {
                for (int c = 0; c < customer; c++)
                {
                    for (int b = 0; b < cpoint; b++)
                    {
                        Model.AddLe(Model.Prod(d1[c, b], X3[a][c][b]), l);
                    }
                }
            }

            // formulation (12)
            for (int a = 0; a < period; a++)
            {
                for (int aa = 0; aa < ptype; aa++)
                {
                    for (int b = 0; b < cpoint; b++)
                    {
                        for (int c = 0; c < rcenter; c++)
                        {
                            for (int d = 0; d < scenario; d++)
                            {
                                Model.AddGe(X2[a][aa][b][c][d], 0);
                            }
                        }
                    }
                }
            }



            // #endregion
            //formulation (15)  //formulation (1)  objective function -1
            // collection points rent cost

            INumExpr[] expr11 = new INumExpr[1];
            for (int a = 0; a < period; a++)
            {
                expr11[0] = X4[0][0];
                for (int b = 0; b < cpoint; b++)
                {
                    expr11[0] = Model.Sum(expr11[0], Model.Prod(X4[a][b], e1[b]));
                }
                expr11[0] = Model.Sum(expr11[0], Model.Prod(-1.0, X4[0][0]));
            }

            INumExpr[] expr12  = new INumExpr[1];
            INumExpr[] expr121 = new INumExpr[1];

            for (int a = 0; a < period; a++)
            {
                for (int b = 0; b < rcenter; b++)
                {
                    expr121[0] = X5[0];
                    for (int c = 0; c < cpoint; c++)
                    {
                        for (int d = 0; d < ptype; d++)
                        {
                            for (int e = 0; e < customer; e++)
                            {
                                expr12[0] = X2[0][0][0][0][0];
                                for (int f = 0; f < scenario; f++)
                                {
                                    expr12[0] = Model.Sum(expr12[0], Model.Prod(Model.Prod(X2[a][d][c][b][f], e2[d, c, b]), wday / vlength));
                                }
                                expr12[0] = Model.Sum(expr12[0], Model.Prod(-1.0, X2[0][0][0][0][0]));
                            }
                        }
                    }
                    expr121[0] = Model.Sum(expr121[0], Model.Prod(expr12[0], X5[b]));
                }
            }

            INumExpr[] expr13 = new INumExpr[1];
            for (int a = 0; a < period; a++)
            {
                for (int b = 0; b < rcenter; b++)
                {
                    expr13[0] = X5[0];
                    for (int bb = 0; bb < elevel; bb++)
                    {
                        expr13[0] = Model.Sum(expr13[0], Model.Prod(X5[b], e3[b, bb]));
                    }
                    expr13[0] = Model.Sum(expr13[0], Model.Prod(-1.0, X5[0]));
                }
            }


            Model.AddLe(Model.Prod(wday, Model.Sum(expr11[0], expr13[0])), e);  //expr12[0],  ,)
            // #endregion

            // //formulation (1)  objective function -1
            // #region
            INumExpr[] expr15 = new INumExpr[1];
            expr15[0] = X4[0][0];
            for (int i = 0; i < period; i++)
            {
                for (int ii = 0; ii < cpoint; ii++)
                {
                    expr15[0] = Model.Sum(expr15[0], Model.Prod(a[ii], X4[i][ii]));
                }
            }
            expr15[0] = Model.Sum(expr15[0], Model.Prod(-1.0, X4[0][0]));
            // ok


            INumExpr[] expr17 = new INumExpr[1];
            for (int a = 0; a < period; a++)
            {
                for (int aaa = 0; aaa < scenario; aaa++)
                {
                    for (int bb = 0; bb < cpoint; bb++)
                    {
                        for (int bbb = 0; bbb < customer; bbb++)
                        {
                            expr17[0] = X3[0][0][0];
                            for (int aa = 0; aa < ptype; aa++)
                            {
                                expr17[0] = Model.Sum(expr17[0], Model.Prod(Model.Prod(r[bbb, aa, a, aaa] * b[aa], X3[a][bbb][bb]), (vlength + 1) * 0.5));
                            }
                            expr17[0] = Model.Sum(expr17[0], Model.Prod(-1.0, X3[0][0][0]));
                        }
                    }
                }
            }

            INumExpr[] expr18 = new INumExpr[1];
            INumExpr[] expr41 = new INumExpr[1];
            expr18[0] = X5[0];
            for (int a = 0; a < period; a++)
            {
                for (int aa = 0; aa < rcenter; aa++)
                {
                    for (int bb = 0; bb < cpoint; bb++)
                    {
                        for (int b = 0; b < ptype; b++)
                        {
                            for (int aaa = 0; aaa < customer; aaa++)
                            {
                                expr41[0] = X2[0][0][0][0][0];
                                for (int bbb = 0; bbb < scenario; bbb++)
                                {
                                    expr41[0] = Model.Sum(expr41[0], Model.Prod(Model.Prod(X2[a][b][bb][aa][bbb], z[bb, aa, b]), vlength));
                                }
                                expr41[0] = Model.Sum(expr17[0], Model.Prod(-1.0, X2[0][0][0][0][0]));
                            }
                        }
                    }
                    expr18[0] = Model.Prod(expr41[0], X5[aa]);
                }
            }
            expr18[0] = Model.Sum(expr18[0], Model.Prod(-1.0, X5[0]));

            INumExpr[] expr19 = new INumExpr[1];
            for (int i = 0; i < period; i++)
            {
                for (int ii = 0; ii < rcenter; ii++)
                {
                    for (int iii = 0; iii < elevel; iii++)
                    {
                        expr19[0] = X5[0];
                        for (int iiii = 0; iiii < capacity; iiii++)
                        {
                            expr19[0] = Model.Sum(expr19[0], Model.Prod(q[ii, iii, iiii], X5[ii]));
                        }
                    }
                }
            }
            expr19[0] = Model.Sum(expr19[0], Model.Prod(-1.0, X5[0]));



            #endregion
            INumExpr[] expr21 = new INumExpr[1];
            expr21[0] = Model.Prod(Model.Sum(expr15[0], Model.Prod(expr17[0], wday), expr18[0], expr19[0]), lambda); //

            INumExpr[] expr22 = new INumExpr[1];
            expr22[0] = Model.Prod(Model.Sum(expr11[0], expr12[0], expr13[0]), delta); // Model.Prod(Model.Prod(wday, Model.Sum(expr11[0], expr12[0], expr13[0])),delta);

            Model.AddMinimize(Model.Sum(expr21[0], expr22[0]));                        //

            Model.ExportModel("RLND.LP");

            if (Model.Solve())
            {
                Console.WriteLine("statue=" + Model.GetStatus());
                Console.WriteLine("obj=" + Model.ObjValue);
                Console.WriteLine("X2的结果");

                for (int aa2 = 0; aa2 < period; aa2++)
                {
                    for (int bb2 = 0; bb2 < ptype; bb2++)
                    {
                        for (int cc = 0; cc < cpoint; cc++)
                        {
                            for (int dd = 0; dd < rcenter; dd++)
                            {
                                for (int ee = 0; ee < scenario; ee++)
                                {
                                    Console.WriteLine(Model.GetValue(X2[aa2][bb2][cc][dd][ee]));
                                    Console.WriteLine();
                                }
                            }
                        }
                    }
                }

                //for (int a = 0; a < X6.Length; a++)
                //{
                //    Console.WriteLine("result[" + a + "] = " + Model.GetValue(X6[a]));
                //}
                //Console.WriteLine();


                Model.End();
            }
            else
            {
                Model.End();
                Console.WriteLine();
                Console.WriteLine("cannot be solved");
            }
        }
Пример #26
0
        //Handle the resolution method without callbacks
        static void Loop(Cplex cplex, Instance instance, Stopwatch clock, Process process, double perc, int numb)
        {
            int typeSol = 1;

            //epGap is false when EpGap parameter is at default
            bool epGap = false;

            //allEdges is true when all possible links have their upper bound to 1
            bool allEdges = true;

            //Setting EpGap if a valid percentage is specified
            if (perc >= 0 && perc <= 1)
            {
                cplex.SetParam(Cplex.DoubleParam.EpGap, perc);

                epGap = true;

                typeSol = 0;
            }

            //numb is equal to -1 when all links upper bound are 1
            if (numb != -1)
            {
                allEdges = false;

                typeSol = 0;
            }

            //Building the maximum # of links that involves each node
            INumVar[] x = Utility.BuildModel(cplex, instance, numb);

            //Allocating the correct space to store the optimal solution
            //Only links from node i to i with i < i are considered
            instance.BestSol = new double[(instance.NNodes - 1) * instance.NNodes / 2];

            //Init buffers
            int[] relatedComponents             = new int[instance.NNodes];
            List <ILinearNumExpr> rcExpr        = new List <ILinearNumExpr>();
            List <int>            bufferCoeffRC = new List <int>();

            //Temporary variable
            double[] linksDistances = new double[(instance.NNodes - 1) * instance.NNodes / 2];;

            do
            {
                //When only one related component is found and ehuristics methods are active they are disabled
                if (rcExpr.Count == 1)
                {
                    epGap = false;

                    allEdges = true;

                    cplex.SetParam(Cplex.DoubleParam.EpGap, 1e-06);

                    Utility.ResetVariables(x);

                    typeSol = 1;
                }

                //Cplex solves the current model
                cplex.Solve();

                //Initializing the arrays used to eliminate the subtour
                Utility.InitCC(relatedComponents);

                rcExpr        = new List <ILinearNumExpr>();
                bufferCoeffRC = new List <int>();

                //Init the StreamWriter for the current solution
                StreamWriter file = new StreamWriter(instance.InputFile + ".dat", false);

                //Storing the optimal value of the objective function
                instance.BestLb = cplex.ObjValue;

                //Blank line
                Console.WriteLine();

                //Printing the optimal solution and the GNUPlot input file
                for (int i = 0; i < instance.NNodes; i++)
                {
                    for (int j = i + 1; j < instance.NNodes; j++)
                    {
                        //Retriving the correct index position for the current link inside x
                        int position = Utility.xPos(i, j, instance.NNodes);

                        //Reading the optimal solution for the actual link (i,i)
                        linksDistances[position] = cplex.GetValue(x[position]);


                        //Only links in the optimal solution (coefficient = 1) are printed in the GNUPlot file
                        if (linksDistances[position] >= 0.5)
                        {
                            /*
                             * Current GNUPlot format is:
                             *-- previus link --
                             *<Blank line>
                             * Xi Yi <index(i)>
                             * Xj Yj <index(i)>
                             *<Blank line>
                             *-- next link --
                             */
                            file.WriteLine(instance.Coord[i].X + " " + instance.Coord[i].Y + " " + (i + 1));
                            file.WriteLine(instance.Coord[j].X + " " + instance.Coord[j].Y + " " + (j + 1) + "\n");

                            //Updating the model with the current subtours elimination
                            Utility.UpdateCC(cplex, x, rcExpr, bufferCoeffRC, relatedComponents, i, j);
                        }
                    }
                }

                //Only when more than one related components are found they are added to the model
                if (rcExpr.Count > 1)
                {
                    for (int i = 0; i < rcExpr.Count; i++)
                    {
                        cplex.AddLe(rcExpr[i], bufferCoeffRC[i] - 1);
                    }
                }

                //GNUPlot input file needs to be closed
                file.Close();

                //Accessing GNUPlot to read the file
                if (Program.VERBOSE >= -1)
                {
                    Utility.PrintGNUPlot(process, instance.InputFile, typeSol, instance.BestLb, -1);
                }

                //Blank line
                cplex.Output().WriteLine();

                //Writing the value
                cplex.Output().WriteLine("xOPT = " + instance.BestLb + "\n");
            } while (rcExpr.Count > 1 || epGap || !allEdges); //if there is more then one related components the solution is not optimal

            instance.BestSol = linksDistances;
            instance.XBest   = instance.BestLb;

            //Exporting the updated model
            if (Program.VERBOSE >= -1)
            {
                cplex.ExportModel(instance.InputFile + ".lp");
            }

            //Closing Cplex link
            cplex.End();

            //Accessing GNUPlot to read the file
            if (Program.VERBOSE >= -1)
            {
                Utility.PrintGNUPlot(process, instance.InputFile, typeSol, instance.XBest, -1);
            }
        }
Пример #27
0
        // The constructor sets up the Cplex instance to solve the worker LP,
        // and creates the worker LP (i.e., the dual of flow constraints and
        // capacity constraints of the flow MILP)
        //
        // Modeling variables:
        // forall k in V0, i in V:
        //    u(k,i) = dual variable associated with flow constraint (k,i)
        //
        // forall k in V0, forall (i,j) in A:
        //    v(k,i,j) = dual variable associated with capacity constraint (k,i,j)
        //
        // Objective:
        // minimize sum(k in V0) sum((i,j) in A) x(i,j) * v(k,i,j)
        //          - sum(k in V0) u(k,0) + sum(k in V0) u(k,k)
        //
        // Constraints:
        // forall k in V0, forall (i,j) in A: u(k,i) - u(k,j) <= v(k,i,j)
        //
        // Nonnegativity on variables v(k,i,j)
        // forall k in V0, forall (i,j) in A: v(k,i,j) >= 0
        //
        internal WorkerLP(int numNodes)
        {
            this.numNodes = numNodes;
            int i, j, k;

            // Set up Cplex instance to solve the worker LP

            cplex = new Cplex();
            cplex.SetOut(null);

            // Turn off the presolve reductions and set the CPLEX optimizer
            // to solve the worker LP with primal simplex method.

            cplex.SetParam(Cplex.Param.Preprocessing.Reduce, 0);
            cplex.SetParam(Cplex.Param.RootAlgorithm, Cplex.Algorithm.Primal);

            // Create variables v(k,i,j) forall k in V0, (i,j) in A
            // For simplicity, also dummy variables v(k,i,i) are created.
            // Those variables are fixed to 0 and do not partecipate to
            // the constraints.

            v = new INumVar[numNodes - 1][][];
            for (k = 1; k < numNodes; ++k)
            {
                v[k - 1] = new INumVar[numNodes][];
                for (i = 0; i < numNodes; ++i)
                {
                    v[k - 1][i] = new INumVar[numNodes];
                    for (j = 0; j < numNodes; ++j)
                    {
                        v[k - 1][i][j] = cplex.NumVar(0.0, System.Double.MaxValue, "v." + k + "." + i + "." + j);
                        cplex.Add(v[k - 1][i][j]);
                    }
                    v[k - 1][i][i].UB = 0.0;
                }
            }

            // Create variables u(k,i) forall k in V0, i in V

            u = new INumVar[numNodes - 1][];
            for (k = 1; k < numNodes; ++k)
            {
                u[k - 1] = new INumVar[numNodes];
                for (i = 0; i < numNodes; ++i)
                {
                    u[k - 1][i] = cplex.NumVar(-System.Double.MaxValue, System.Double.MaxValue, "u." + k + "." + i);
                    cplex.Add(u[k - 1][i]);
                }
            }

            // Initial objective function is empty

            cplex.AddMinimize();

            // Add constraints:
            // forall k in V0, forall (i,j) in A: u(k,i) - u(k,j) <= v(k,i,j)

            for (k = 1; k < numNodes; ++k)
            {
                for (i = 0; i < numNodes; ++i)
                {
                    for (j = 0; j < numNodes; ++j)
                    {
                        if (i != j)
                        {
                            ILinearNumExpr expr = cplex.LinearNumExpr();
                            expr.AddTerm(v[k - 1][i][j], -1.0);
                            expr.AddTerm(u[k - 1][i], 1.0);
                            expr.AddTerm(u[k - 1][j], -1.0);
                            cplex.AddLe(expr, 0.0);
                        }
                    }
                }
            }
        } // END WorkerLP
Пример #28
0
    /// <summary>
    /// The example's main function.
    /// </summary>
    public static void Main(string[] args)
    {
        int   retval = 0;
        Cplex cplex  = null;

        try
        {
            cplex = new Cplex();

            /* ***************************************************************** *
            *                                                                   *
            *    S E T U P   P R O B L E M                                      *
            *                                                                   *
            *  We create the following problem:                                 *
            * Minimize                                                          *
            *  obj: 3x1 - x2 + 3x3 + 2x4 + x5 + 2x6 + 4x7                       *
            * Subject To                                                        *
            *  c1: x1 + x2 = 4                                                  *
            *  c2: x1 + x3 >= 3                                                 *
            *  c3: x6 + x7 <= 5                                                 *
            *  c4: -x1 + x7 >= -2                                               *
            *  q1: [ -x1^2 + x2^2 ] <= 0                                        *
            *  q2: [ 4.25x3^2 -2x3*x4 + 4.25x4^2 - 2x4*x5 + 4x5^2  ] + 2 x1 <= 9.0
            *  q3: [ x6^2 - x7^2 ] >= 4                                         *
            * Bounds                                                            *
            *  0 <= x1 <= 3                                                     *
            *  x2 Free                                                          *
            *  0 <= x3 <= 0.5                                                   *
            *  x4 Free                                                          *
            *  x5 Free                                                          *
            *  x7 Free                                                          *
            * End                                                               *
            *                                                                   *
            * ***************************************************************** */

            INumVar[] x = new INumVar[7];
            x[0] = cplex.NumVar(0, 3, "x1");
            x[1] = cplex.NumVar(System.Double.NegativeInfinity, System.Double.PositiveInfinity, "x2");
            x[2] = cplex.NumVar(0, 0.5, "x3");
            x[3] = cplex.NumVar(System.Double.NegativeInfinity, System.Double.PositiveInfinity, "x4");
            x[4] = cplex.NumVar(System.Double.NegativeInfinity, System.Double.PositiveInfinity, "x5");
            x[5] = cplex.NumVar(0, System.Double.PositiveInfinity, "x6");
            x[6] = cplex.NumVar(System.Double.NegativeInfinity, System.Double.PositiveInfinity, "x7");

            IRange[] linear = new IRange[4];
            linear[0] = cplex.AddEq(cplex.Sum(x[0], x[1]), 4.0, "c1");
            linear[1] = cplex.AddGe(cplex.Sum(x[0], x[2]), 3.0, "c2");
            linear[2] = cplex.AddLe(cplex.Sum(x[5], x[6]), 5.0, "c3");
            linear[3] = cplex.AddGe(cplex.Diff(x[6], x[0]), -2.0, "c4");

            IRange[] quad = new IRange[3];
            quad[0] = cplex.AddLe(cplex.Sum(cplex.Prod(-1, x[0], x[0]),
                                            cplex.Prod(x[1], x[1])), 0.0, "q1");
            quad[1] = cplex.AddLe(cplex.Sum(cplex.Prod(4.25, x[2], x[2]),
                                            cplex.Prod(-2, x[2], x[3]),
                                            cplex.Prod(4.25, x[3], x[3]),
                                            cplex.Prod(-2, x[3], x[4]),
                                            cplex.Prod(4, x[4], x[4]),
                                            cplex.Prod(2, x[0])), 9.0, "q2");
            quad[2] = cplex.AddGe(cplex.Sum(cplex.Prod(x[5], x[5]),
                                            cplex.Prod(-1, x[6], x[6])), 4.0, "q3");

            cplex.AddMinimize(cplex.Sum(cplex.Prod(3.0, x[0]),
                                        cplex.Prod(-1.0, x[1]),
                                        cplex.Prod(3.0, x[2]),
                                        cplex.Prod(2.0, x[3]),
                                        cplex.Prod(1.0, x[4]),
                                        cplex.Prod(2.0, x[5]),
                                        cplex.Prod(4.0, x[6])), "obj");

            /* ***************************************************************** *
            *                                                                   *
            *    O P T I M I Z E   P R O B L E M                                *
            *                                                                   *
            * ***************************************************************** */
            cplex.SetParam(Cplex.Param.Barrier.QCPConvergeTol, 1e-10);
            cplex.Solve();

            /* ***************************************************************** *
            *                                                                   *
            *    Q U E R Y   S O L U T I O N                                    *
            *                                                                   *
            * ***************************************************************** */
            double[] xval   = cplex.GetValues(x);
            double[] slack  = cplex.GetSlacks(linear);
            double[] qslack = cplex.GetSlacks(quad);
            double[] cpi    = cplex.GetReducedCosts(x);
            double[] rpi    = cplex.GetDuals(linear);
            double[] qpi    = getqconstrmultipliers(cplex, xval, ZEROTOL, x, quad);
            // Also store solution in a dictionary so that we can look up
            // values by variable and not only by index.
            IDictionary <INumVar, System.Double> xmap = new Dictionary <INumVar, System.Double>();
            for (int j = 0; j < x.Length; ++j)
            {
                xmap.Add(x[j], xval[j]);
            }

            /* ***************************************************************** *
            *                                                                   *
            *    C H E C K   K K T   C O N D I T I O N S                        *
            *                                                                   *
            *    Here we verify that the optimal solution computed by CPLEX     *
            *    (and the qpi[] values computed above) satisfy the KKT          *
            *    conditions.                                                    *
            *                                                                   *
            * ***************************************************************** */

            // Primal feasibility: This example is about duals so we skip this test.

            // Dual feasibility: We must verify
            // - for <= constraints (linear or quadratic) the dual
            //   multiplier is non-positive.
            // - for >= constraints (linear or quadratic) the dual
            //   multiplier is non-negative.
            for (int i = 0; i < linear.Length; ++i)
            {
                if (linear[i].LB <= System.Double.NegativeInfinity)
                {
                    // <= constraint
                    if (rpi[i] > ZEROTOL)
                    {
                        throw new System.SystemException("Dual feasibility test failed for row " + linear[i]
                                                         + ": " + rpi[i]);
                    }
                }
                else if (linear[i].UB >= System.Double.PositiveInfinity)
                {
                    // >= constraint
                    if (rpi[i] < -ZEROTOL)
                    {
                        throw new System.SystemException("Dual feasibility test failed for row " + linear[i]
                                                         + ": " + rpi[i]);
                    }
                }
                else
                {
                    // nothing to do for equality constraints
                }
            }
            for (int i = 0; i < quad.Length; ++i)
            {
                if (quad[i].LB <= System.Double.NegativeInfinity)
                {
                    // <= constraint
                    if (qpi[i] > ZEROTOL)
                    {
                        throw new System.SystemException("Dual feasibility test failed for quad " + quad[i]
                                                         + ": " + qpi[i]);
                    }
                }
                else if (quad[i].UB >= System.Double.PositiveInfinity)
                {
                    // >= constraint
                    if (qpi[i] < -ZEROTOL)
                    {
                        throw new System.SystemException("Dual feasibility test failed for quad " + quad[i]
                                                         + ": " + qpi[i]);
                    }
                }
                else
                {
                    // nothing to do for equality constraints
                }
            }

            // Complementary slackness.
            // For any constraint the product of primal slack and dual multiplier
            // must be 0.
            for (int i = 0; i < linear.Length; ++i)
            {
                if (System.Math.Abs(linear[i].UB - linear[i].LB) > ZEROTOL &&
                    System.Math.Abs(slack[i] * rpi[i]) > ZEROTOL)
                {
                    throw new System.SystemException("Complementary slackness test failed for row " + linear[i]
                                                     + ": " + System.Math.Abs(slack[i] * rpi[i]));
                }
            }
            for (int i = 0; i < quad.Length; ++i)
            {
                if (System.Math.Abs(quad[i].UB - quad[i].LB) > ZEROTOL &&
                    System.Math.Abs(qslack[i] * qpi[i]) > ZEROTOL)
                {
                    throw new System.SystemException("Complementary slackness test failed for quad " + quad[i]
                                                     + ": " + System.Math.Abs(qslack[i] * qpi[i]));
                }
            }
            for (int j = 0; j < x.Length; ++j)
            {
                if (x[j].UB < System.Double.PositiveInfinity)
                {
                    double slk  = x[j].UB - xval[j];
                    double dual = cpi[j] < -ZEROTOL ? cpi[j] : 0.0;
                    if (System.Math.Abs(slk * dual) > ZEROTOL)
                    {
                        throw new System.SystemException("Complementary slackness test failed for column " + x[j]
                                                         + ": " + System.Math.Abs(slk * dual));
                    }
                }
                if (x[j].LB > System.Double.NegativeInfinity)
                {
                    double slk  = xval[j] - x[j].LB;
                    double dual = cpi[j] > ZEROTOL ? cpi[j] : 0.0;
                    if (System.Math.Abs(slk * dual) > ZEROTOL)
                    {
                        throw new System.SystemException("Complementary slackness test failed for column " + x[j]
                                                         + ": " + System.Math.Abs(slk * dual));
                    }
                }
            }

            // Stationarity.
            // The difference between objective function and gradient at optimal
            // solution multiplied by dual multipliers must be 0, i.E., for the
            // optimal solution x
            // 0 == c
            //      - sum(r in rows)  r'(x)*rpi[r]
            //      - sum(q in quads) q'(x)*qpi[q]
            //      - sum(c in cols)  b'(x)*cpi[c]
            // where r' and q' are the derivatives of a row or quadratic constraint,
            // x is the optimal solution and rpi[r] and qpi[q] are the dual
            // multipliers for row r and quadratic constraint q.
            // b' is the derivative of a bound constraint and cpi[c] the dual bound
            // multiplier for column c.
            IDictionary <INumVar, System.Double> kktsum = new Dictionary <INumVar, System.Double>();
            for (int j = 0; j < x.Length; ++j)
            {
                kktsum.Add(x[j], 0.0);
            }

            // Objective function.
            for (ILinearNumExprEnumerator it = ((ILinearNumExpr)cplex.GetObjective().Expr).GetLinearEnumerator();
                 it.MoveNext(); /* nothing */)
            {
                kktsum[it.NumVar] = it.Value;
            }

            // Linear constraints.
            // The derivative of a linear constraint ax - b (<)= 0 is just a.
            for (int i = 0; i < linear.Length; ++i)
            {
                for (ILinearNumExprEnumerator it = ((ILinearNumExpr)linear[i].Expr).GetLinearEnumerator();
                     it.MoveNext(); /* nothing */)
                {
                    kktsum[it.NumVar] = kktsum[it.NumVar] - rpi[i] * it.Value;
                }
            }

            // Quadratic constraints.
            // The derivative of a constraint xQx + ax - b <= 0 is
            // Qx + Q'x + a.
            for (int i = 0; i < quad.Length; ++i)
            {
                for (ILinearNumExprEnumerator it = ((ILinearNumExpr)quad[i].Expr).GetLinearEnumerator();
                     it.MoveNext(); /* nothing */)
                {
                    kktsum[it.NumVar] = kktsum[it.NumVar] - qpi[i] * it.Value;
                }
                for (IQuadNumExprEnumerator it = ((IQuadNumExpr)quad[i].Expr).GetQuadEnumerator();
                     it.MoveNext(); /* nothing */)
                {
                    INumVar v1 = it.NumVar1;
                    INumVar v2 = it.NumVar2;
                    kktsum[v1] = kktsum[v1] - qpi[i] * xmap[v2] * it.Value;
                    kktsum[v2] = kktsum[v2] - qpi[i] * xmap[v1] * it.Value;
                }
            }

            // Bounds.
            // The derivative for lower bounds is -1 and that for upper bounds
            // is 1.
            // CPLEX already returns dj with the appropriate sign so there is
            // no need to distinguish between different bound types here.
            for (int j = 0; j < x.Length; ++j)
            {
                kktsum[x[j]] = kktsum[x[j]] - cpi[j];
            }

            foreach (INumVar v in x)
            {
                if (System.Math.Abs(kktsum[v]) > ZEROTOL)
                {
                    throw new System.SystemException("Stationarity test failed at " + v
                                                     + ": " + System.Math.Abs(kktsum[v]));
                }
            }

            // KKT conditions satisfied. Dump out the optimal solutions and
            // the dual values.
            System.Console.WriteLine("Optimal solution satisfies KKT conditions.");
            System.Console.WriteLine("   x[] = " + arrayToString(xval));
            System.Console.WriteLine(" cpi[] = " + arrayToString(cpi));
            System.Console.WriteLine(" rpi[] = " + arrayToString(rpi));
            System.Console.WriteLine(" qpi[] = " + arrayToString(qpi));
        }
        catch (ILOG.Concert.Exception e)
        {
            System.Console.WriteLine("IloException: " + e.Message);
            System.Console.WriteLine(e.StackTrace);
            retval = -1;
        }
        finally
        {
            if (cplex != null)
            {
                cplex.End();
            }
        }
        System.Environment.Exit(retval);
    }
Пример #29
0
        static void Main(string[] args)
        {
            double[] Demand = new double[] { 15, 18, 14, 20 };
            double[] Capacity = new double[] { 20, 22, 17, 19, 18 };
            double[,] ShipCosts =
                new double[,] { { 4000, 2500, 1200, 2200 }, 
                { 2000, 2600, 1800, 2600 }, 
                { 3000, 3400, 2600, 3100 }, 
                { 2500, 3000, 4100, 3700 },
                { 4500, 4000, 3000, 3200 } };
            int nWarehouses = Capacity.Length;
            int nCustomers = Demand.Length;

            Cplex m = new Cplex();

            INumVar[,] Ship = new INumVar[nWarehouses, nCustomers];
            for (int i = 0; i < nWarehouses; ++i)
                for (int j = 0; j < nCustomers; ++j)
                    Ship[i, j] = m.NumVar(0, System.Double.MaxValue, NumVarType.Float, "ship." + i + "." + j);

            INumVar[] Shortage = new INumVar[nCustomers];
            for (int j = 0; j < nCustomers; ++j)
                Shortage[j] = m.NumVar(0, System.Double.MaxValue, NumVarType.Float, "shortage." + j);

            INumVar TotalShortage = m.NumVar(0, System.Double.MaxValue, NumVarType.Float, "TotalShortage");
            INumVar TotalShippingCost = m.NumVar(0, System.Double.MaxValue, NumVarType.Float, "TotalShippingCost");
            IObjective obj = m.AddMinimize(TotalShippingCost);

            IConstraint[] DemandCon = new IConstraint[nCustomers];
            for (int j = 0; j < nCustomers; ++j)
            {
                INumExpr lhs = m.LinearNumExpr(0.0);
                INumExpr rhs = m.LinearNumExpr(Demand[j]);
                for (int i = 0; i < nWarehouses; ++i)
                    lhs = m.Sum(lhs, Ship[i, j]);
                lhs = m.Sum(lhs, Shortage[j]);
                DemandCon[j] = m.AddEq(lhs, rhs, "demand." + j);
            }

            IConstraint[] CapacityCon = new IConstraint[nWarehouses];
            for (int i = 0; i < nWarehouses; ++i)
            {
                INumExpr lhs = m.LinearNumExpr(0.0);
                for (int j = 0; j < nCustomers; ++j)
                    lhs = m.Sum(lhs, Ship[i, j]);
                CapacityCon[i] = m.AddLe(lhs, Capacity[i], "capacity." + i);
            }

            INumExpr expr = m.Sum(Shortage);
            IConstraint TotalShortageCon = m.AddEq(expr, TotalShortage, "total_shortage");

            expr = m.LinearNumExpr(0.0);
            for (int i = 0; i < nWarehouses; ++i)
                for (int j = 0; j < nCustomers; ++j)
                    expr = m.Sum(expr, m.Prod(ShipCosts[i, j], Ship[i, j]));
            IConstraint TotalShippingCon = m.AddEq(expr, TotalShippingCost, "total_shipping");
            m.ExportModel("Facility.lp");
            while (true)
            {
                Console.WriteLine("\nSolver Output:");
                m.Solve();
                double OptShortage = m.GetValue(TotalShortage);
                double OptShipping = m.GetValue(TotalShippingCost);
                Console.WriteLine("\nFacility Program Output:");
                Console.WriteLine("\nTotalShortage = {0}", OptShortage);
                Console.WriteLine("TotalShippingCost= {0}\n", OptShipping);
                if (OptShortage < EPS) break;
                INumVar[] varArr = new INumVar[26];
                double[] ubs = new double[26];
                double[] lbs = new double[26];
                varArr[0] = TotalShortage;
                varArr[1] = TotalShippingCost;
                for (int i = 0; i < nWarehouses; ++i)
                    for (int j = 0; j < nCustomers; ++j)
                        varArr[4 * i + j + 2] = Ship[i, j];
                for (int j = 0; j < nCustomers; ++j)
                    varArr[j + 22] = Shortage[j];
                m.GetObjSA(lbs, ubs, varArr);
                double ObjectiveBound = ubs[0];
                m.SetLinearCoef(obj, ((1 + EPS) * ObjectiveBound), TotalShortage);
            } // end while

            for (int i = 0; i < nWarehouses; ++i)
                for (int j = 0; j < nCustomers; ++j)
                    Console.WriteLine("{0} = {1}", Ship[i, j].Name, m.GetValue(Ship[i, j]));
            for (int j = 0; j < nCustomers; ++j)
                Console.WriteLine("{0} = {1}", Shortage[j].Name, m.GetValue(Shortage[j]));
            Console.WriteLine("{0} = {1}", TotalShortage.Name, m.GetValue(TotalShortage));
            Console.WriteLine("{0} = {1}", TotalShippingCost.Name, m.GetValue(TotalShippingCost));
        } // end Main
Пример #30
0
 public void AddCapacityConstraint()
 {
     theModel.AddLe(theModel.Sum(theModel.ScalProd(TrailerTurns, LoadedMoves), theModel.ScalProd(TrailerTurns, EmptyMoves)), (trailerCapacity * 52), "Capacity");
 }
Пример #31
0
        static void Main()
        {
            try
            {
                string resultFilename = "./ResultFiles/MTSP_MTZ.csv";
                string filename       = "./DataFiles/Data.dat";
                Data   data           = new Data(filename);

                double timeFactor     = 0;
                double distanceFactor = 1;
                double step           = 0.1;
                int    routeCounter   = 0;

                File.WriteAllText(resultFilename, "");

                do
                {
                    using (Cplex cplex = new Cplex())
                    {
                        #region [Decision Variables]
                        IIntVar[][] x = new IIntVar[data.n][];
                        IIntVar     Q = cplex.IntVar(1, 250, "Q");

                        for (int i = 0; i < data.n; i++)
                        {
                            x[i] = cplex.BoolVarArray(data.n);
                            cplex.Add(x[i]);
                        }
                        #endregion

                        #region [Objective Function]
                        INumExpr obj = cplex.NumExpr();
                        for (int i = 0; i < data.n; i++)
                        {
                            for (int j = 0; j < data.n; j++)
                            {
                                if (i != j)
                                {
                                    obj = cplex.Sum(obj,
                                                    cplex.Prod(
                                                        (
                                                            (timeFactor * data.timeNormalized[i][j]) +
                                                            (distanceFactor * data.distanceNormalized[i][j])
                                                        ), x[i][j]));
                                }
                            }
                        }
                        cplex.AddMinimize(obj);
                        #endregion

                        #region [Restrictions]
                        for (int j = 0; j < data.n; j++)
                        {
                            ILinearNumExpr sumj = cplex.LinearNumExpr();
                            for (int i = 0; i < data.n; i++)
                            {
                                if (i != j)
                                {
                                    sumj.AddTerm(1, x[i][j]);
                                }
                            }
                            cplex.AddEq(sumj, 1);
                        }

                        for (int i = 0; i < data.n; i++)
                        {
                            ILinearNumExpr sumi = cplex.LinearNumExpr();
                            for (int j = 0; j < data.n; j++)
                            {
                                if (i != j)
                                {
                                    sumi.AddTerm(1, x[i][j]);
                                }
                            }
                            cplex.AddEq(sumi, 1);
                        }
                        #endregion

                        cplex.SetParam(Cplex.DoubleParam.WorkMem, 4000.0);
                        cplex.SetParam(Cplex.Param.MIP.Strategy.File, 2);
                        cplex.SetParam(Cplex.DoubleParam.EpGap, 0.1);
                        cplex.SetParam(Cplex.BooleanParam.MemoryEmphasis, true);
                        cplex.SetParam(Cplex.IntParam.VarSel, 4);

SOLVE:

                        Stopwatch stopWatch = new Stopwatch();
                        stopWatch.Start();
                        if (cplex.Solve())
                        {
                            stopWatch.Stop();
                            double[][] sol_x = new double[data.n][];
                            for (int i = 0; i < data.n; i++)
                            {
                                sol_x[i] = cplex.GetValues(x[i]);
                            }
                            int[] tour = FindSubTour(sol_x);
                            if (tour.Length < data.n)
                            {
                                ILinearNumExpr sumx = cplex.LinearNumExpr();
                                for (int i = 0; i < tour.Length; i++)
                                {
                                    for (int j = 0; j < tour.Length; j++)
                                    {
                                        sumx.AddTerm(1, x[tour[i]][tour[j]]);
                                    }
                                }
                                cplex.AddLazyConstraint(cplex.AddLe(cplex.Diff(sumx, tour.Length), -1));
                                goto SOLVE;
                            }

                            double timeTotal     = 0;
                            double distanceTotal = 0;
                            for (int i = 0; i < data.n; i++)
                            {
                                for (int j = 0; j < data.n; j++)
                                {
                                    timeTotal     += data.time[i][j] * sol_x[i][j];
                                    distanceTotal += data.distance[i][j] * sol_x[i][j];
                                }
                            }

                            StreamWriter file = new StreamWriter(resultFilename, true);
                            file.WriteLine($"{timeFactor},{distanceFactor},{stopWatch.Elapsed.TotalSeconds},{cplex.ObjValue},{timeTotal},{distanceTotal}");
                            file.Close();

                            StreamWriter fileRouteResult = new StreamWriter($"./ResultFiles/Route-{routeCounter}.txt");
                            for (int i = 0; i < data.n; i++)
                            {
                                for (int j = 0; j < data.n; j++)
                                {
                                    if (sol_x[i][j] == 1)
                                    {
                                        fileRouteResult.WriteLine($"From city {i} to city {j}");
                                    }
                                }
                            }
                            fileRouteResult.Close();
                        }
                        cplex.End();
                    }

                    timeFactor     += step;
                    distanceFactor -= step;
                    routeCounter++;
                } while (timeFactor <= 1);
            }
            catch (ILOG.Concert.Exception ex)
            {
                StreamWriter errorfile = new StreamWriter("./ErrorLog.txt");
                errorfile.WriteLine("Exception Kind: ILOG.Concert.Exception (Concert Error)");
                errorfile.WriteLine("Message: " + ex.Message);
                errorfile.WriteLine("StackTrace: " + ex.StackTrace);
                errorfile.Close();
            }
            catch (InputDataReader.InputDataReaderException ex)
            {
                StreamWriter errorfile = new StreamWriter("./ErrorLog.txt");
                errorfile.WriteLine("Exception Kind: InputDataReader.InputDataReaderException (Data Error)");
                errorfile.WriteLine("Message: " + ex.Message);
                errorfile.WriteLine("StackTrace: " + ex.StackTrace);
                errorfile.Close();
            }
            catch (System.IO.IOException ex)
            {
                StreamWriter errorfile = new StreamWriter("./ErrorLog.txt");
                errorfile.WriteLine("Exception Kind: System.IO.IOException (IO Error)");
                errorfile.WriteLine("Message: " + ex.Message);
                errorfile.WriteLine("StackTrace: " + ex.StackTrace);
                errorfile.Close();
            }
        }
Пример #32
0
    private void runModel(List <Employee> employees, List <Shift> shifts)
    {
        StreamWriter writer = File.CreateText(@"C:\Users\user\Desktop\cplex log\result9.txt");

        try
        {
            Cplex model = new Cplex();

            model.SetOut(writer);

            //------------------------------
            //---Variable initialization-----
            //------------------------------
            //Assignment variables
            IDictionary <string, IIntVar> assignVars = new Dictionary <string, IIntVar>();
            employees.ForEach(employee =>
            {
                shifts.ForEach(shift =>
                {
                    string name = getAssignVarName(employee, shift);
                    assignVars.Add(name, model.BoolVar(name));
                });
            });

            //Total assignment hours
            INumVar totalAssignHourVar = model.NumVar(0, Double.MaxValue, getTotalAssignVarName());

            //----------------------------------
            //---Constraints initialization-----
            //-----------------------------------

            //1) Min rest constraint
            //2) Goal total assigned hours constraint
            ILinearNumExpr sumAssignHourExpr = model.LinearNumExpr();
            sumAssignHourExpr.AddTerm(-1.0, totalAssignHourVar);
            employees.ForEach(employee =>
            {
                shifts.ForEach(shift1 =>
                {
                    ILinearNumExpr sumOverlapExpr = model.LinearNumExpr();
                    string name1       = getAssignVarName(employee, shift1);
                    IIntVar assignVar1 = assignVars[name1];
                    sumOverlapExpr.AddTerm(1.0, assignVar1);
                    shifts.ForEach(shift2 =>
                    {
                        if (shift1 != shift2 && this.isDurationOverlap(shift1, shift2))
                        {
                            string name2 = getAssignVarName(employee, shift2);
                            sumOverlapExpr.AddTerm(1.0, assignVars[name2]);
                        }
                    });
                    model.AddLe(sumOverlapExpr, 1.0, "MinRestConst");

                    sumAssignHourExpr.AddTerm((shift1.end - shift1.begin).TotalMinutes, assignVar1);
                });
            });

            //3) No overassignment constraint
            shifts.ForEach(shift =>
            {
                ILinearNumExpr sumAssigsExpr = model.LinearNumExpr();
                employees.ForEach(employee =>
                {
                    string name1       = getAssignVarName(employee, shift);
                    IIntVar assignVar1 = assignVars[name1];
                    sumAssigsExpr.AddTerm(1.0, assignVar1);
                });
                model.AddLe(sumAssigsExpr, shift.shiftNumber, "NoOverAssignConst");
            });
            model.AddEq(sumAssignHourExpr, 0.0, "TotalAssignedHourConst");
            INumVar[] goalVars = { totalAssignHourVar };
            double[]  coeffs   = { 1.0 };
            model.AddMaximize(model.ScalProd(goalVars, coeffs));

            model.ExportModel(@"C:\Users\user\Desktop\cplex log\model1.lp");
            bool feasible = model.Solve();
            if (feasible)
            {
                double objVal = model.ObjValue;
                model.Output().WriteLine("Solution value = " + model.ObjValue);
                shifts.ForEach(shift =>
                {
                    ILinearNumExpr sumAssigsExpr = model.LinearNumExpr();
                    employees.ForEach(employee =>
                    {
                        string name = getAssignVarName(employee, shift);
                    });
                    model.AddLe(sumAssigsExpr, shift.shiftNumber, "NoOverAssignConst");
                });
            }
            else
            {
            }
        }
        catch (System.Exception ex)
        {
            Response.ContentType = "application/json; charset=utf-8";
            Response.Write(ex.Message);
            Response.End();
        }
        writer.Close();
    }
Пример #33
0
    public static void Main(string[] args)
    {
        int nMonths   = cost.Length;
        int nProducts = cost[0].Length;

        try {
            Cplex cplex = new Cplex();

            INumVar[]   produce = cplex.NumVarArray(nMonths, 0, System.Double.MaxValue);
            INumVar[][] use     = new INumVar[nMonths][];
            INumVar[][] buy     = new INumVar[nMonths][];
            INumVar[][] store   = new INumVar[nMonths][];

            for (int i = 0; i < nMonths; i++)
            {
                use[i]   = cplex.NumVarArray(nProducts, 0.0, System.Double.MaxValue);
                buy[i]   = cplex.NumVarArray(nProducts, 0.0, System.Double.MaxValue);
                store[i] = cplex.NumVarArray(nProducts, 0.0, 1000.0);
            }

            for (int p = 0; p < nProducts; p++)
            {
                store[nMonths - 1][p].LB = 500.0;
                store[nMonths - 1][p].UB = 500.0;
            }

            INumExpr profit = cplex.NumExpr();
            for (int i = 0; i < nMonths; i++)
            {
                // Not more than 200 tons of vegetable oil can be refined
                cplex.AddLe(cplex.Sum(use[i][v1], use[i][v2]), 200.0);

                // Not more than 250 tons of non-vegetable oil can be refined
                cplex.AddLe(cplex.Sum(use[i][o1], use[i][o2], use[i][o3]), 250.0);

                // Constraints on food composition
                cplex.AddLe(cplex.Prod(3.0, produce[i]),
                            cplex.Sum(cplex.Prod(8.8, use[i][v1]),
                                      cplex.Prod(6.1, use[i][v2]),
                                      cplex.Prod(2.0, use[i][o1]),
                                      cplex.Prod(4.2, use[i][o2]),
                                      cplex.Prod(5.0, use[i][o3])));
                cplex.AddGe(cplex.Prod(6.0, produce[i]),
                            cplex.Sum(cplex.Prod(8.8, use[i][v1]),
                                      cplex.Prod(6.1, use[i][v2]),
                                      cplex.Prod(2.0, use[i][o1]),
                                      cplex.Prod(4.2, use[i][o2]),
                                      cplex.Prod(5.0, use[i][o3])));
                cplex.AddEq(produce[i], cplex.Sum(use[i]));

                // Raw oil can be stored for later use
                if (i == 0)
                {
                    for (int p = 0; p < nProducts; p++)
                    {
                        cplex.AddEq(cplex.Sum(500.0, buy[i][p]),
                                    cplex.Sum(use[i][p], store[i][p]));
                    }
                }
                else
                {
                    for (int p = 0; p < nProducts; p++)
                    {
                        cplex.AddEq(cplex.Sum(store[i - 1][p], buy[i][p]),
                                    cplex.Sum(use[i][p], store[i][p]));
                    }
                }

                // Logical constraints:
                // The food cannot use more than 3 oils
                // (or at least two oils must not be used)
                cplex.AddGe(cplex.Sum(cplex.Eq(use[i][v1], 0),
                                      cplex.Eq(use[i][v2], 0),
                                      cplex.Eq(use[i][o1], 0),
                                      cplex.Eq(use[i][o2], 0),
                                      cplex.Eq(use[i][o3], 0)), 2);

                // When an oil is used, the quantity must be at least 20 tons
                for (int p = 0; p < nProducts; p++)
                {
                    cplex.Add(cplex.Or(cplex.Eq(use[i][p], 0),
                                       cplex.Ge(use[i][p], 20)));
                }

                // If products v1 or v2 are used, then product o3 is also used
                cplex.Add(cplex.IfThen(cplex.Or(cplex.Ge(use[i][v1], 20),
                                                cplex.Ge(use[i][v2], 20)),
                                       cplex.Ge(use[i][o3], 20)));

                // Objective function
                profit = cplex.Sum(profit, cplex.Prod(150, produce[i]));
                profit = cplex.Diff(profit, cplex.ScalProd(cost[i], buy[i]));
                profit = cplex.Diff(profit, cplex.Prod(5, cplex.Sum(store[i])));
            }

            cplex.AddMaximize(profit);

            if (cplex.Solve())
            {
                System.Console.WriteLine("Solution status = " + cplex.GetStatus());
                System.Console.WriteLine(" Maximum profit = " + cplex.ObjValue);
                for (int i = 0; i < nMonths; i++)
                {
                    System.Console.WriteLine(" Month {0}", i);

                    System.Console.Write("  . buy   ");
                    for (int p = 0; p < nProducts; p++)
                    {
                        System.Console.Write("{0,8:F2} ", cplex.GetValue(buy[i][p]));
                    }
                    System.Console.WriteLine();

                    System.Console.Write("  . use   ");
                    for (int p = 0; p < nProducts; p++)
                    {
                        System.Console.Write("{0,8:F2} ", cplex.GetValue(use[i][p]));
                    }
                    System.Console.WriteLine();

                    System.Console.Write("  . store ");
                    for (int p = 0; p < nProducts; p++)
                    {
                        System.Console.Write("{0,8:F2} ", cplex.GetValue(store[i][p]));
                    }
                    System.Console.WriteLine();
                }
            }
            cplex.End();
        }
        catch (ILOG.Concert.Exception e) {
            System.Console.WriteLine("Concert exception caught: " + e);
        }
    }
Пример #34
0
        // The constructor sets up the Cplex instance to solve the worker LP,
        // and creates the worker LP (i.e., the dual of flow constraints and
        // capacity constraints of the flow MILP)
        //
        // Modeling variables:
        // forall k in V0, i in V:
        //    u(k,i) = dual variable associated with flow constraint (k,i)
        //
        // forall k in V0, forall (i,j) in A:
        //    v(k,i,j) = dual variable associated with capacity constraint (k,i,j)
        //
        // Objective:
        // minimize sum(k in V0) sum((i,j) in A) x(i,j) * v(k,i,j)
        //          - sum(k in V0) u(k,0) + sum(k in V0) u(k,k)
        //
        // Constraints:
        // forall k in V0, forall (i,j) in A: u(k,i) - u(k,j) <= v(k,i,j)
        //
        // Nonnegativity on variables v(k,i,j)
        // forall k in V0, forall (i,j) in A: v(k,i,j) >= 0
        //
        internal WorkerLP(int numNodes)
        {
            this.numNodes = numNodes;
             int i, j, k;

             // Set up Cplex instance to solve the worker LP

             cplex = new Cplex();
             cplex.SetOut(null);

             // Turn off the presolve reductions and set the CPLEX optimizer
             // to solve the worker LP with primal simplex method.

             cplex.SetParam(Cplex.Param.Preprocessing.Reduce, 0);
             cplex.SetParam(Cplex.Param.RootAlgorithm, Cplex.Algorithm.Primal);

             // Create variables v(k,i,j) forall k in V0, (i,j) in A
             // For simplicity, also dummy variables v(k,i,i) are created.
             // Those variables are fixed to 0 and do not partecipate to
             // the constraints.

             v = new INumVar[numNodes-1][][];
             for (k = 1; k < numNodes; ++k)
             {
            v[k-1] = new INumVar[numNodes][];
            for (i = 0; i < numNodes; ++i)
            {
               v[k-1][i] = new INumVar[numNodes];
               for (j = 0; j < numNodes; ++j)
               {
                  v[k-1][i][j] = cplex.NumVar(0.0, System.Double.MaxValue, "v." + k + "." + i + "." + j);
                  cplex.Add(v[k-1][i][j]);
               }
               v[k-1][i][i].UB = 0.0;
            }
             }

             // Create variables u(k,i) forall k in V0, i in V

             u = new INumVar[numNodes-1][];
             for (k = 1; k < numNodes; ++k)
             {
            u[k-1] = new INumVar[numNodes];
            for (i = 0; i < numNodes; ++i)
            {
               u[k-1][i] = cplex.NumVar(-System.Double.MaxValue, System.Double.MaxValue, "u." + k + "." + i);
               cplex.Add(u[k-1][i]);
            }
             }

             // Initial objective function is empty

             cplex.AddMinimize();

             // Add constraints:
             // forall k in V0, forall (i,j) in A: u(k,i) - u(k,j) <= v(k,i,j)

             for (k = 1; k < numNodes; ++k)
             {
            for (i = 0; i < numNodes; ++i)
            {
               for (j = 0; j < numNodes; ++j)
               {
                  if ( i != j )
                  {
                     ILinearNumExpr expr = cplex.LinearNumExpr();
                     expr.AddTerm(v[k-1][i][j], -1.0);
                     expr.AddTerm(u[k-1][i], 1.0);
                     expr.AddTerm(u[k-1][j], -1.0);
                     cplex.AddLe(expr, 0.0);
                  }
               }
            }
             }
        }
Пример #35
0
        private void decomp(int dim, int kts, int[][] dist, List <int> WorkList)
        {
            int[] lo = new int[dim];
            int   dk = dim * kts;

            for (int i = 0; i < dim; i++)
            {
                lo[i] = 1;
            }

            Cplex      cplex   = new Cplex();
            NumVarType varType = NumVarType.Bool;

            INumVar[][] x = new INumVar[dim][];
            for (int i = 0; i < dim; i++)
            {
                x[i] = cplex.NumVarArray(dk, 0, 1);
            }

            for (int i = 0; i < dim; i++)
            {
                for (int j = 0; j < dk; j++)
                {
                    x[i][j] = cplex.BoolVar();
                }
            }

            //****************************************
            //Что тут происходит?
            for (int j = 0; j < dim; j++)
            {
                INumExpr xcolSum = cplex.NumExpr();
                for (int k = 0; k < kts; k++)
                {
                    for (int i = 0; i < dim; i++)
                    {
                        xcolSum = cplex.Sum(xcolSum, x[i][k * dim + j]);
                    }
                }
                cplex.AddEq(lo[j], xcolSum);
            }

            varType = NumVarType.Float;
            INumVar[] u = new INumVar[dk];
            for (int j = 0; j < dk; j++)
            {
                u[j] = cplex.NumVar(0, 100000);
            }

            for (int j = 1; j < dk; j++)
            {
                cplex.AddGe(u[j], 0);
            }

            for (int k = 0; k < kts; k++)
            {
                for (int i = 1; i < dim; i++)
                {
                    for (int j = 1; j < dim; j++)
                    {
                        if (i != j)
                        {
                            if (kts == 1)
                            {
                                cplex.AddLe(cplex.Sum(cplex.Diff(u[k * dim + i], u[k * dim + j]), cplex.Prod(dim, x[i][k * dim + j])), dim - 1);
                            }
                            else
                            {
                                cplex.AddLe(cplex.Sum(cplex.Diff(u[k * dim + i], u[k * dim + j]), cplex.Prod(dim, x[i][k * dim + j])), dim);
                            }
                        }
                    }
                }
            }

            for (int i = 0; i < dim; i++)
            {
                INumExpr xrowSum = cplex.NumExpr();
                for (int j = 0; j < dk; j++)
                {
                    xrowSum = cplex.Sum(xrowSum, x[i][j]);
                }
                cplex.AddEq(lo[i], xrowSum);
            }

            //Условия независимости кластеров
            if (kts > 1)
            {
                int[] a = new int[kts + 1];
                for (int k = 1; k < kts; k++)
                {
                    if (k > 1 && k < kts - 1)
                    {
                        continue;
                    }
                    int p;
                    for (int i = 1; i <= k; i++)
                    {
                        a[i] = i;
                    }
                    p = k;
                    while (p >= 1)
                    {
                        for (int m = 0; m < dim; m++)
                        {
                            INumExpr xcolrowSum = cplex.NumExpr();
                            for (int j = 1; j <= kts; j++)
                            {
                                bool row = false;
                                for (int i = 1; i <= k; i++)
                                {
                                    if (a[i] == j)
                                    {
                                        row = true;
                                    }
                                }
                                if (row)
                                {
                                    for (int t = 0; t < dim; t++)
                                    {
                                        xcolrowSum = cplex.Sum(xcolrowSum, x[m][(j - 1) * dim + t]);
                                    }
                                }
                                else
                                {
                                    for (int t = 0; t < dim; t++)
                                    {
                                        xcolrowSum = cplex.Sum(xcolrowSum, x[t][(j - 1) * dim + m]);
                                    }
                                }
                            }
                            cplex.AddLe(xcolrowSum, lo[m]);
                        }
                        if (a[k] == kts)
                        {
                            p--;
                        }
                        else
                        {
                            p = k;
                        }
                        if (p >= 1)
                        {
                            for (int i = k; i >= p; i--)
                            {
                                a[i] = a[p] + i - p + 1;
                            }
                        }
                    }
                }
            }

            INumExpr costSum = cplex.NumExpr();

            INumExpr[] costSum1 = new INumExpr[kts];

            if (kts == 1)
            {
                for (int i = 0; i < dim; i++)
                {
                    for (int j = 0; j < dim; j++)
                    {
                        costSum = cplex.Sum(costSum, cplex.Prod(x[i][j], dist[i][j]));
                    }
                }
                cplex.AddMinimize(costSum);
            }
            else
            {
                for (int k = 0; k < kts; k++)
                {
                    costSum1[k] = cplex.NumExpr();
                    for (int i = 0; i < dim; i++)
                    {
                        for (int j = 0; j < dim; j++)
                        {
                            costSum1[k] = cplex.Sum(costSum1[k], cplex.Prod(x[i][k * dim + j], dist[i][j]));
                        }
                    }
                    //cplex.AddLe(costSum1[k], costSum);
                }
                costSum = cplex.Max(costSum1);
                cplex.AddMinimize(costSum);
            }

            try
            {
                if (cplex.Solve())
                {
                    textBox1.Text += "lambda = " + cplex.ObjValue + Environment.NewLine;
                    textBox1.Text += DateTime.Now.ToString() + Environment.NewLine;

                    WorkList.Clear();
                    int num_clust = 0;
                    for (int k = 0; k < kts; k++)
                    {
                        int dim1 = 0;
                        for (int i = 0; i < dim; i++)
                        {
                            for (int j = 0; j < dim; j++)
                            {
                                if (Convert.ToInt16(cplex.GetValue(x[i][k * dim + j])) == 1)
                                {
                                    dim1++;
                                }
                            }
                        }

                        if (dim1 > 0)
                        {
                            num_clust++;
                            for (int i = 0; i < dim; i++)
                            {
                                for (int j = 0; j < dim; j++)
                                {
                                    if (Convert.ToInt16(cplex.GetValue(x[i][k * dim + j])) == 1)
                                    {
                                        WorkList.Add(i);
                                        break;
                                    }
                                }
                            }

                            WorkList.Add(-1);
                        }
                    }
                    textBox1.Text += DateTime.Now.ToString() + Environment.NewLine;
                }
                else
                {
                    textBox1.Text += "Нет решения" + Environment.NewLine;
                    textBox1.Text += DateTime.Now.ToString() + Environment.NewLine;
                }
                cplex.End();
            }
            catch (ILOG.Concert.Exception ex)
            {
                textBox1.Text += "Concert Error: " + ex + Environment.NewLine;
                textBox1.Text += DateTime.Now.ToString() + Environment.NewLine;
            }
        }
Пример #36
0
        static void Main(string[] args)
        {
            double[]   price        = { 170.0, 170.0, 170.0 };
            double[]   priceStorage = { 10.0, 10.0, 10.0 };
            double[]   hardness     = { 8.4, 6.2, 2.0 };
            double[]   hardness3    = { 3, 3, 3 };
            double[]   hardness6    = { 6, 6, 6 };
            double[][] oilCost      = new double[2][];
            oilCost[0] = new double[3] {
                1.159550009798596e+02, 1.018115866059220e+02, 1.128780935294160e+02
            };
            oilCost[1] = new double[3] {
                100, 1.067537671189185e+02, 1.098041326934309e+02
            };

            //oilCost = GenerateRandomVector();

            INumVar[][] oilStore   = new INumVar[3][];
            INumVar[][] oilBuy     = new INumVar[2][];
            INumVar[][] oilProduce = new INumVar[2][]; // [month][A-C]
            Cplex       cplex      = new Cplex();

            for (int i = 0; i < 2; i++) // Initialize oilBuy and oilProduce
            {
                oilBuy[i]     = new INumVar[3];
                oilProduce[i] = new INumVar[3];
            }
            for (int i = 0; i < 3; i++) // Initialize oilStore
            {
                oilStore[i] = new INumVar[3];
                for (int j = 0; j < 3; j++)
                {
                    oilStore[i][j] = cplex.NumVar(0, 800); // Ograniczenia na pojemność magazynu
                }
            }
            for (int i = 0; i < 2; i++)     // Ograniczenia na miesiące
            {
                for (int j = 0; j < 3; j++) // Ograniczenia na możliwości rafinacji
                {
                    if (j != 2)
                    {
                        oilProduce[i][j] = cplex.NumVar(0, 220); // Rafinacja roślinnego
                    }
                    else
                    {
                        oilProduce[i][j] = cplex.NumVar(0, 270); // Rafinacja nie-roślinnego
                    }
                    oilBuy[i][j] = cplex.NumVar(0, 1070);
                }
                cplex.AddRange(0, cplex.Sum(oilProduce[i][0], oilProduce[i][1]), 220);
                cplex.AddGe(cplex.ScalProd(hardness, oilProduce[i]), cplex.ScalProd(hardness3, oilProduce[i]));     // Hardness greater than 3
                cplex.AddLe(cplex.ScalProd(hardness, oilProduce[i]), cplex.ScalProd(hardness6, oilProduce[i]));     // Hardness less than 6
            }
            for (int i = 0; i < 3; i++)                                                                             // Ograniczenia na oleje
            {
                cplex.AddEq(oilStore[0][i], 200.0);                                                                 // Ograniczenie na stan magazynu w grudniu
                cplex.AddEq(oilStore[2][i], 200.0);                                                                 // Ograniczenie na stan magazynu w lutym
                cplex.AddEq(oilStore[1][i], cplex.Sum(cplex.Diff(oilBuy[0][i], oilProduce[0][i]), oilStore[0][i])); // (Kupowane + zmagazynowane - produkowane) w tym miesiacu = zmagazynowane w nastepnym miesiacu
                cplex.AddEq(oilStore[2][i], cplex.Sum(cplex.Diff(oilBuy[1][i], oilProduce[1][i]), oilStore[1][i]));
            }

            // Funkcja Celu: zyski ze sprzedaży - koszta magazynowania - koszta kupowania materiału do produkcji
            cplex.AddMaximize(
                cplex.Diff(
                    cplex.Diff(
                        cplex.Sum(
                            cplex.ScalProd(price, oilProduce[0]),
                            cplex.ScalProd(price, oilProduce[1])),
                        cplex.Sum(
                            cplex.ScalProd(priceStorage, oilStore[1]),
                            cplex.ScalProd(priceStorage, oilStore[2]))),
                    cplex.Sum(
                        cplex.ScalProd(oilCost[0], oilBuy[0]),
                        cplex.ScalProd(oilCost[1], oilBuy[1]))));


            if (cplex.Solve())
            {
                System.Console.WriteLine();
                System.Console.WriteLine("Solution status = " + cplex.GetStatus());
                System.Console.WriteLine();
                System.Console.WriteLine("  = " + cplex.ObjValue);
                Console.WriteLine();
                for (int i = 0; i < 2; i++)
                {
                    for (int j = 0; j < 3; j++)
                    {
                        Console.WriteLine(" oilCost[" + i + "][" + j + "] = " + oilCost[i][j]);
                    }
                }

                Console.WriteLine();
                for (int j = 0; j < 2; j++)
                {
                    double hardnessTotal = 0;
                    double sum           = 0;
                    for (int i = 0; i < 3; i++)
                    {
                        System.Console.WriteLine(" oilProduce[" + j + "][" + i + "] = " + cplex.GetValue(oilProduce[j][i]));
                        hardnessTotal += cplex.GetValue(oilProduce[j][i]) * hardness[i];
                        sum           += cplex.GetValue(oilProduce[j][i]);
                    }
                    System.Console.WriteLine(" hardnessTotal[" + j + "] = " + hardnessTotal / sum);
                    Console.WriteLine();
                }

                for (int j = 0; j < 2; j++)
                {
                    for (int i = 0; i < 3; i++)
                    {
                        System.Console.WriteLine(" oilBuy[" + j + "][" + i + "] = " + cplex.GetValue(oilBuy[j][i]));
                    }
                }
                Console.WriteLine();
                for (int j = 0; j < 3; j++)
                {
                    for (int i = 0; i < 3; i++)
                    {
                        System.Console.WriteLine(" oilStore[" + j + "][" + i + "] = " + cplex.GetValue(oilStore[j][i]));
                    }
                }

                System.Console.WriteLine();
            }
            Console.ReadKey();
        }
Пример #37
0
        private void button1_Click(object sender, EventArgs e)
        {
            int[,] A = new int[, ]
            {
                { 1, 1, 1, 1, 0 },
                { 1, 1, 0, 1, 1 },
                { 0, 1, 1, 1, 1 }
            };

            double[] L = new double[] { 8, 5, 7, 8, 4 };

            double G = 10.7;

            double[] N_Max = new double[] { 2, 2, 2 };

            int nbOfWorkers = A.GetLength(0);
            int nbOfTasks   = A.GetLength(1);

            Cplex cplex = new Cplex();

            INumVar[,] X = new INumVar[nbOfWorkers, nbOfTasks];  // C라는 2차원 인덱스가 0이면, 행의 개수을 받겠다
            // C라는 2차원 인덱스가 1이면 열의 개수를 받겠다.
            for (int i = 0; i < A.GetLength(0); i++)
            {
                for (int j = 0; j < A.GetLength(1); j++)
                {
                    X[i, j] = cplex.BoolVar();
                }
            }

            List <INumVar> D_negative = new List <INumVar>();

            for (int i = 0; i < nbOfWorkers; i++)
            {
                D_negative.Add(cplex.NumVar(0, double.MaxValue));
            }


            List <INumVar> D_positive = new List <INumVar>();

            for (int i = 0; i < nbOfWorkers; i++)
            {
                D_positive.Add(cplex.NumVar(0, double.MaxValue));
            }

            //목적함수
            ILinearNumExpr objectiveFunction = cplex.LinearNumExpr();

            for (int i = 0; i < nbOfWorkers; i++)
            {
                objectiveFunction.AddTerm(1, D_negative[i]);
            }

            for (int i = 0; i < nbOfWorkers; i++)
            {
                objectiveFunction.AddTerm(1, D_positive[i]); // C[i, j], X[i, j] 두개를 곱해서 objectiveFunction 에 넣겠다.
            }
            //과제
            for (int i = 0; i < nbOfWorkers; i++)
            {
                ILinearNumExpr constLeft1 = cplex.LinearNumExpr();
                for (int j = 0; j < nbOfTasks; j++)
                {
                    constLeft1.AddTerm(L[j], X[i, j]);
                }
                constLeft1.AddTerm(1, D_negative[i]);
                constLeft1.AddTerm(-1, D_positive[i]);
                cplex.AddEq(constLeft1, G);
            }


            for (int j = 0; j < nbOfTasks; j++)
            {
                ILinearNumExpr constLeft2 = cplex.LinearNumExpr();
                for (int i = 0; i < X.GetLength(0); i++)
                {
                    constLeft2.AddTerm(1, X[i, j]);
                }
                cplex.AddEq(constLeft2, 1);
            }

            for (int i = 0; i < nbOfWorkers; i++)
            {
                for (int j = 0; j < nbOfTasks; j++)
                {
                    cplex.AddLe(X[i, j], A[i, j]);
                }
            }

            for (int i = 0; i < nbOfWorkers; i++)
            {
                ILinearNumExpr constLeft4 = cplex.LinearNumExpr();
                for (int j = 0; j < nbOfTasks; j++)
                {
                    constLeft4.AddTerm(1, X[i, j]);
                }
                cplex.AddLe(constLeft4, N_Max[i]);
            }

            cplex.AddMinimize(objectiveFunction);
            cplex.Solve();

            string solution  = "";
            double tolerance = cplex.GetParam(Cplex.Param.MIP.Tolerances.Integrality); //tolerance를 정의함

            for (int i = 0; i < A.GetLength(0); i++)
            {
                for (int j = 0; j < A.GetLength(1); j++)
                {
                    if (cplex.GetValue(X[i, j]) >= 1 - tolerance)
                    {
                        solution += "(" + (i + 1).ToString() + " ," + (j + 1).ToString() + ")";
                    }
                }
            }

            MessageBox.Show("목적함수 값은 =" + cplex.GetObjValue() + "\r\n" + "선택된 변수는 =" + solution);
        }