<?xml version="1.0" encoding="UTF-8" ?>
<?xml-stylesheet type="text/xsl" href="http://blogs.msdn.com/utility/FeedStylesheets/rss.xsl" media="screen"?><rss version="2.0" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:slash="http://purl.org/rss/1.0/modules/slash/" xmlns:wfw="http://wellformedweb.org/CommentAPI/"><channel><title>Nathan Brixius : LINQ</title><link>http://blogs.msdn.com/natbr/archive/tags/LINQ/default.aspx</link><description>Tags: LINQ</description><dc:language>en-US</dc:language><generator>CommunityServer 2.1 SP1 (Build: 61025.2)</generator><item><title>Solver Foundation LINQ to SQL example</title><link>http://blogs.msdn.com/natbr/archive/2009/06/02/solver-foundation-linq-to-sql-example.aspx</link><pubDate>Tue, 02 Jun 2009 17:45:00 GMT</pubDate><guid isPermaLink="false">91d46819-8472-40ad-a661-2c78acb4018c:9685593</guid><dc:creator>Nathan Brixius</dc:creator><slash:comments>1</slash:comments><comments>http://blogs.msdn.com/natbr/comments/9685593.aspx</comments><wfw:commentRss>http://blogs.msdn.com/natbr/commentrss.aspx?PostID=9685593</wfw:commentRss><wfw:comment>http://blogs.msdn.com/natbr/rsscomments.aspx?PostID=9685593</wfw:comment><description>&lt;P&gt;Erwin, a modeling consultant and top Solver Foundation user, &lt;A href="http://yetanothermathprogrammingconsultant.blogspot.com/2009/05/ms-solver-foundation-data-binding.html" target=_blank mce_href="http://yetanothermathprogrammingconsultant.blogspot.com/2009/05/ms-solver-foundation-data-binding.html"&gt;encountered some problems trying to do two-way data binding&lt;/A&gt; using DataTable objects.&amp;nbsp; There are more details on &lt;A href="http://code.msdn.microsoft.com/solverfoundation/Thread/View.aspx?ThreadId=1812" target=_blank mce_href="http://code.msdn.microsoft.com/solverfoundation/Thread/View.aspx?ThreadId=1812"&gt;this discussion thread&lt;/A&gt;.&amp;nbsp; Ross, a member of the Solver Foundation team, was kind enough to code up a workaround for Erwin's example.&amp;nbsp; In addition to this CS file, you will need to create a new DBML file called SampleDataContext, &lt;A href="http://blogs.msdn.com/natbr/archive/2009/05/05/creating-parameterized-solver-foundation-models-using-linq-to-sql.aspx" mce_href="http://blogs.msdn.com/natbr/archive/2009/05/05/creating-parameterized-solver-foundation-models-using-linq-to-sql.aspx"&gt;as I described in a previous post&lt;/A&gt;.&lt;/P&gt;&lt;PRE&gt;using System;
using System.Collections.Generic;
using System.Linq;
using System.Data;
using System.Data.OleDb;
using System.Data.Linq;
using System.Text;
using Microsoft.SolverFoundation.Services;
using System.IO;
 
namespace OML1
{
    class Test
    {
        static void Main(string[] args)
        {
            Test t = new Test();
            t.Solve();
        }
 
        // Holds the OML model
        string strModel = @"Model[
              Parameters[Sets,I],
              Parameters[Reals,p[I]],
 
              Decisions[Reals[0,Infinity],x[I]],
 
              Constraints[
                 Foreach[{i,I}, x[i]==p[i]]
              ]
           ]";
 
 
        //  SFS
        SolverContext context;
        SampleDataContext data;
 
 
        //  Constructor
        public Test()
        {
            context = SolverContext.GetContext();
            data = new SampleDataContext("Data Source=Sql_server_name;Initial Catalog=DataPartitionAllocation20_5;Integrated Security=True");
            context.DataSource = data;
        }
 
 
        // Solve the problem
        public void Solve()
        {
            context.LoadModel(FileFormat.OML, new StringReader(strModel));
 
            Parameter p = context.CurrentModel.Parameters.First(q =&amp;gt; q.Name == "p");
            p.SetBinding(data.P, "value", new string[] { "index" });
 
            Decision x = context.CurrentModel.Decisions.First(d =&amp;gt; d.Name == "x");
            x.SetBinding(data.X, "value", new string[] { "index" }); 
 
            Solution solution = context.Solve();
            Console.Write("{0}", solution.GetReport());
 
            context.PropagateDecisions();
 
        }
 
    }
 
}
&lt;/PRE&gt;&lt;img src="http://blogs.msdn.com/aggbug.aspx?PostID=9685593" width="1" height="1"&gt;</description><category domain="http://blogs.msdn.com/natbr/archive/tags/C_2300_/default.aspx">C#</category><category domain="http://blogs.msdn.com/natbr/archive/tags/Solver+Foundation/default.aspx">Solver Foundation</category><category domain="http://blogs.msdn.com/natbr/archive/tags/optimization/default.aspx">optimization</category><category domain="http://blogs.msdn.com/natbr/archive/tags/LINQ/default.aspx">LINQ</category><category domain="http://blogs.msdn.com/natbr/archive/tags/OML/default.aspx">OML</category><category domain="http://blogs.msdn.com/natbr/archive/tags/SQL/default.aspx">SQL</category></item><item><title>Creating parameterized Solver Foundation models using LINQ to SQL</title><link>http://blogs.msdn.com/natbr/archive/2009/05/05/creating-parameterized-solver-foundation-models-using-linq-to-sql.aspx</link><pubDate>Tue, 05 May 2009 23:29:00 GMT</pubDate><guid isPermaLink="false">91d46819-8472-40ad-a661-2c78acb4018c:9589626</guid><dc:creator>Nathan Brixius</dc:creator><slash:comments>9</slash:comments><comments>http://blogs.msdn.com/natbr/comments/9589626.aspx</comments><wfw:commentRss>http://blogs.msdn.com/natbr/commentrss.aspx?PostID=9589626</wfw:commentRss><wfw:comment>http://blogs.msdn.com/natbr/rsscomments.aspx?PostID=9589626</wfw:comment><description>&lt;P&gt;&lt;A href="http://code.msdn.microsoft.com/solverfoundation/Thread/View.aspx?ThreadId=1665" mce_href="http://code.msdn.microsoft.com/solverfoundation/Thread/View.aspx?ThreadId=1665"&gt;On the Solver Foundation MSDN forum&lt;/A&gt; there was a question about how to read model data from a DB and use it within a Solver Foundation model.&amp;nbsp; In this post I will extend my production planning sample to use LINQ to SQL.&amp;nbsp; To follow along at home you will need to have a recent version of SQL Server installed locally, and some basic knowledge of how to create SQL tables.&amp;nbsp; You should also have compiled and run the code from my &lt;A href="http://blogs.msdn.com/natbr/archive/2009/04/24/modeling-a-production-planning-problem-using-solver-foundation.aspx" mce_href="http://blogs.msdn.com/natbr/archive/2009/04/24/modeling-a-production-planning-problem-using-solver-foundation.aspx"&gt;previous post&lt;/A&gt;.&lt;/P&gt;
&lt;P&gt;&lt;STRONG&gt;Step 1: Create and populate the DB&lt;/STRONG&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;The first step is to create tables corresponding to the entities in my model.&amp;nbsp; I created a very simple DB with three tables: Countries, Products, and Yields.&amp;nbsp; The Yields table has foreign key constraints to the Countries and Products tables.&amp;nbsp; Here is a diagram:&lt;/P&gt;
&lt;P&gt;&lt;IMG title="Petrochem Entities" alt="Petrochem Entities" src="http://blogs.msdn.com/photos/nathan_brixius/images/9589627/original.aspx" mce_src="http://blogs.msdn.com/photos/nathan_brixius/images/9589627/original.aspx"&gt;&lt;/P&gt;
&lt;P&gt;To populate the DB I just wrote a script that inserts my problem data, and ran itin SQL Management Studio.&amp;nbsp; Here's the script (and forgive my SQL):&lt;/P&gt;&lt;PRE&gt;GO 

DELETE FROM Yields
DELETE FROM Products
DELETE FROM Countries
GO

INSERT INTO Countries (Id, Name, Limit, Cost)
VALUES (0, 'SA', 9000, 20)

INSERT INTO Countries (Id, Name, Limit, Cost)
VALUES (1, 'VZ', 6000, 15)

GO

INSERT INTO Products (Id, Name, Demand)
VALUES (0, 'Gas', 1900)

INSERT INTO Products (Id, Name, Demand)
VALUES (1, 'Jet Fuel', 1500)

INSERT INTO Products (Id, Name, Demand)
VALUES (2, 'Lubricant', 500)

GO

INSERT INTO Yields (CountryId, ProductId, Value)
VALUES (0, 0, 0.3)
INSERT INTO Yields (CountryId, ProductId, Value)
VALUES (1, 0, 0.4)

INSERT INTO Yields (CountryId, ProductId, Value)
VALUES (0, 1, 0.4)
INSERT INTO Yields (CountryId, ProductId, Value)
VALUES (1, 1, 0.2)

INSERT INTO Yields (CountryId, ProductId, Value)
VALUES (0, 2, 0.2)
INSERT INTO Yields (CountryId, ProductId, Value)
VALUES (1, 2, 0.3)
&lt;/PRE&gt;
&lt;P&gt;&lt;STRONG&gt;&lt;/STRONG&gt;&amp;nbsp;&lt;/P&gt;
&lt;P&gt;&lt;STRONG&gt;Step 2: Create Entity and DataContext classes in Visual Studio&lt;/STRONG&gt; &lt;/P&gt;
&lt;P&gt;&lt;A href="http://weblogs.asp.net/scottgu/archive/2007/05/19/using-linq-to-sql-part-1.aspx" mce_href="http://weblogs.asp.net/scottgu/archive/2007/05/19/using-linq-to-sql-part-1.aspx"&gt;Scott Guthrie's blog&lt;/A&gt; (and the MSDN docs) show you exactly how to do this:&amp;nbsp; &lt;/P&gt;
&lt;OL&gt;
&lt;LI&gt;Add a new "Linq to SQL file" to your project called Petrochem.dbml.&lt;/LI&gt;
&lt;LI&gt;Bring up the Server Explorer window, connect to your database and drag the tables into the dbml window.&amp;nbsp; Visual Studio will automatically create a Datacontext class (mine is called PetrochemDataContext) and an entity class for each table that you include.&lt;/LI&gt;&lt;/OL&gt;
&lt;P&gt;&lt;IMG style="WIDTH: 257px; HEIGHT: 180px" title="Petrochem DB" alt="Petrochem DB" src="http://blogs.msdn.com/photos/nathan_brixius/images/9589628/original.aspx" width=257 height=180 mce_src="http://blogs.msdn.com/photos/nathan_brixius/images/9589628/original.aspx"&gt;&lt;/P&gt;
&lt;P&gt;&lt;STRONG&gt;Step 3: Modify Solver Foundation Services data binding code&lt;/STRONG&gt;&lt;/P&gt;
&lt;P&gt;This is in fact very easy because Solver Foundation Services was designed to work well with LINQ.&amp;nbsp; Take the PetrochemDataBinding sample from last time, and change the SetBinding statements to work with the PetrochemDataContext class instead of a hardcoded DataSet.&amp;nbsp; The code is almost identical:&lt;/P&gt;&lt;PRE&gt;  private static void PetrochemLinqDataBinding() {
      SolverContext context = SolverContext.GetContext();
      context.ClearModel();
      Model model = context.CreateModel();

      PetrochemDataContext db = new PetrochemDataContext();

      Set products = new Set(Domain.Any, "products");
      Set countries = new Set(Domain.Any, "countries");

      Parameter demand = new Parameter(Domain.Real, "demand", products);
      demand.SetBinding(db.Products, "Demand", "Id");

      Parameter yield = new Parameter(Domain.Real, "yield", products, countries);
      yield.SetBinding(db.Yields, "Value", "ProductId", "CountryId");

      Parameter limit = new Parameter(Domain.Real, "limit", countries);
      limit.SetBinding(db.Countries, "Limit", "Id");

      Parameter cost = new Parameter(Domain.Real, "cost", countries);
      cost.SetBinding(db.Countries, "Cost", "Id");

      model.AddParameters(demand, yield, limit, cost);

      Decision produce = new Decision(Domain.RealNonnegative, "produce", countries);
      model.AddDecision(produce);

      model.AddGoal("goal", GoalKind.Minimize, Model.Sum(Model.ForEach(countries, c =&amp;gt; cost[c] * produce[c])));

      model.AddConstraint("Demand",
        Model.ForEach(products, p =&amp;gt; Model.Sum(Model.ForEach(countries, c =&amp;gt; yield[p, c] * produce[c])) &amp;gt;= demand[p])
        );

      model.AddConstraint("Production limit",
        Model.ForEach(countries, c =&amp;gt; produce[c] &amp;lt;= limit[c])
        );

      Solution solution = context.Solve(new SimplexDirective());
      Report report = solution.GetReport();
      Console.WriteLine(report);
    }
&lt;/PRE&gt;
&lt;P&gt;That's all there is to it!&amp;nbsp; Note that instead of passing the entire collection (e.g. db.Countries) you could easily use LINQ statements or stored procedures, or whatever you like.&lt;/P&gt;&lt;img src="http://blogs.msdn.com/aggbug.aspx?PostID=9589626" width="1" height="1"&gt;</description><category domain="http://blogs.msdn.com/natbr/archive/tags/C_2300_/default.aspx">C#</category><category domain="http://blogs.msdn.com/natbr/archive/tags/Solver+Foundation/default.aspx">Solver Foundation</category><category domain="http://blogs.msdn.com/natbr/archive/tags/optimization/default.aspx">optimization</category><category domain="http://blogs.msdn.com/natbr/archive/tags/LINQ/default.aspx">LINQ</category><category domain="http://blogs.msdn.com/natbr/archive/tags/OML/default.aspx">OML</category><category domain="http://blogs.msdn.com/natbr/archive/tags/SQL/default.aspx">SQL</category></item><item><title>Solving traveling salesman problems using Solver Foundation</title><link>http://blogs.msdn.com/natbr/archive/2009/04/27/solving-traveling-salesman-problems-using-solver-foundation.aspx</link><pubDate>Mon, 27 Apr 2009 18:18:00 GMT</pubDate><guid isPermaLink="false">91d46819-8472-40ad-a661-2c78acb4018c:9571061</guid><dc:creator>Nathan Brixius</dc:creator><slash:comments>2</slash:comments><comments>http://blogs.msdn.com/natbr/comments/9571061.aspx</comments><wfw:commentRss>http://blogs.msdn.com/natbr/commentrss.aspx?PostID=9571061</wfw:commentRss><wfw:comment>http://blogs.msdn.com/natbr/rsscomments.aspx?PostID=9571061</wfw:comment><description>&lt;P&gt;Here's an example that I walked through during yesterday's INFORMS session.&amp;nbsp; Erwin has &lt;A href="http://yetanothermathprogrammingconsultant.blogspot.com/2009/03/tsp-in-oml-ms-solver-foundation.html" mce_href="http://yetanothermathprogrammingconsultant.blogspot.com/2009/03/tsp-in-oml-ms-solver-foundation.html"&gt;two&lt;/A&gt; &lt;A href="http://yetanothermathprogrammingconsultant.blogspot.com/2009/02/tsp-powerset-formulation.html" mce_href="http://yetanothermathprogrammingconsultant.blogspot.com/2009/02/tsp-powerset-formulation.html"&gt;blog postings&lt;/A&gt; about Solver Foundation and the traveling salesman problem, but I want to throw in my two cents because I want to emphasize a couple of points:&lt;/P&gt;
&lt;OL&gt;
&lt;LI&gt;By combining C# and Solver Foundation Services it is possible to express complex models clearly and succinctly.&lt;/LI&gt;
&lt;LI&gt;It is very easy to build powerful, reusable model libraries using C# and Solver Foundation Services.&lt;/LI&gt;
&lt;LI&gt;Solver Foundation Services code can be used in many different application environments (ASP.Net, silverlight, DB, command line apps, WPF, …) with minimal changes.&lt;/LI&gt;&lt;/OL&gt;
&lt;P&gt;The traveling salesman problem is a classical problem in computer science, and you should bow your head in shame if you don't know about it (and turn in your conference badge if you happen to be in Phoenix).&amp;nbsp; A salesperson needs to make a tour of a number of cities.&amp;nbsp; The restrictions are that she wants to visit each city once and only once, and she wants to minimize the distance travelled.&amp;nbsp; This is perhaps &lt;STRONG&gt;the&lt;/STRONG&gt; definitive example of an NP-hard problem.&lt;/P&gt;
&lt;P&gt;TSP can be solved using mixed integer programming - optimizing a linear goal with linear constraints, where some of the decision variables are integer.&amp;nbsp; In this first post I will show how to formulate and solve a TSP model using Solver Foundation Services.&amp;nbsp; In my second post I will show how to use the Gurobi MIP solver using SFS.&amp;nbsp;&amp;nbsp; There are many different ways to model the TSP - &lt;A href="http://archive.ite.journal.informs.org/Vol7No1/LeeRaffensperger/" mce_href="http://archive.ite.journal.informs.org/Vol7No1/LeeRaffensperger/"&gt;here&lt;/A&gt; is a nice introduction.&amp;nbsp; My goal is to provide a clear, complete example - not build a "production level" TSP model, so I am going to choose a model formulation that dates back to 1960!&amp;nbsp; First, I need to establish a couple of building blocks that will help me construct the data for the model.&amp;nbsp; We need to know the distances between each pair of cities.&amp;nbsp; Typically we are provided the coordinates of the cities and need to derive the distances.&amp;nbsp; So I will introduce a Coordinate class that contains properties for the (x, y) coordinates, and properties to convert to latitude and longitude.&amp;nbsp; Finally, a method that computes the distance between points.&lt;/P&gt;&lt;PRE&gt;using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Microsoft.SolverFoundation.Services;
using SolverFoundation.Plugin.Gurobi;

namespace Microsoft.SolverFoundation.Samples.TravelingSalesman {
  class Program {
    // TSP coordinate.
    public class Coordinate {
      public int Name { get; set; }

      // X-coordinate (from TSPLIB)
      public double X { get; set; }

      // Y-coordinate (from TSPLIB)
      public double Y { get; set; }

      public Coordinate(int name, double x, double y) {
        Name = name;
        X = x;
        Y = y;
      }

      // Latitude in radians.
      public double Latitude {
        get { return Math.PI * (Math.Truncate(X) + 5 * (X - Math.Truncate(X)) / 3) / 180; }
      }

      // Longitude in radians.
      public double Longitude {
        get { return Math.PI * (Math.Truncate(Y) + 5 * (Y - Math.Truncate(Y)) / 3) / 180; }
      }

      // Geographic distance between two points (as an integer).
      public int Distance(Coordinate p) {
        double q1 = Math.Cos(Longitude - p.Longitude);
        double q2 = Math.Cos(Latitude - p.Latitude);
        double q3 = Math.Cos(Latitude + p.Latitude);
        // There may rounding difficulties her if the points are close together...just sayin'.
        return (int)(6378.388 * Math.Acos(0.5 * ((1 + q1) * q2 - (1 - q1) * q3)) + 1);
      }
    }

    // TSP city-city arc.
    // &lt;/SUMMARY&gt;
    public class Arc {
      public int City1 { get; set; }
      public int City2 { get; set; }
      public double Distance { get; set; }
    }

    // Burma14 from TSPLIB. Optimal tour = 3323.
    private static Coordinate[] data = new Coordinate[] {
      new Coordinate(0, 16.47, 96.10),
      new Coordinate(1, 16.47, 94.44),
      new Coordinate(2, 20.09, 92.54),
      new Coordinate(3, 22.39, 93.37),
      new Coordinate(4, 25.23, 97.24),
      new Coordinate(5, 22.00, 96.05),
      new Coordinate(6, 20.47, 97.02),
      new Coordinate(7, 17.20, 96.29),
      new Coordinate(8, 16.30, 97.38),
      new Coordinate(9, 14.05, 98.12),
      new Coordinate(10, 16.53, 97.38),
      new Coordinate(11, 21.52, 95.59),
      new Coordinate(12, 19.41, 97.13),
      new Coordinate(13, 20.09, 94.55)
    };
&lt;/PRE&gt;
&lt;P&gt;(The data for this 14-city problem comes from the &lt;A href="http://www.iwr.uni-heidelberg.de/groups/comopt/software/TSPLIB95/" mce_href="http://www.iwr.uni-heidelberg.de/groups/comopt/software/TSPLIB95/"&gt;TSPLIB&lt;/A&gt; library). If you've been following my blog you know that the building blocks of a Solver Foundation model are: sets, parameters, decisions, goals, and constraints. I am going to implement a simple formulation that is centered around&amp;nbsp;the following (indexed) decisions:&lt;/P&gt;
&lt;UL&gt;
&lt;LI&gt;Assign[i,j]: this is equal to 1 if the optimal tour contains a trip (or arc) from city i to city j.&lt;/LI&gt;
&lt;LI&gt;Rank[i]: this is equal to the number of cities visited after arriving at city i.&amp;nbsp;&lt;/LI&gt;&lt;/UL&gt;
&lt;P&gt;We have one parameter in our model:&lt;/P&gt;
&lt;UL&gt;
&lt;LI&gt;Distance[I,j]: the distance from city i to city j.&amp;nbsp;&lt;/LI&gt;&lt;/UL&gt;
&lt;P&gt;With that in mind, here's the model.&amp;nbsp; Explanation of the goals and constraints follow.&lt;/P&gt;&lt;PRE&gt;    static void Main(string[] args) {
      SolverContext context = SolverContext.GetContext();
      Model model = context.CreateModel();

      // ------------
      // Parameters
      Set city = new Set(Domain.IntegerNonnegative, "city");
      Parameter dist = new Parameter(Domain.Real, "dist", city, city);
      var arcs = from p1 in data
                 from p2 in data
                 select new Arc { City1 = p1.Name, City2 = p2.Name, Distance = p1.Distance(p2) };
      dist.SetBinding(arcs, "Distance", "City1", "City2");
      model.AddParameters(dist);

      // ------------
      // Decisions
      Decision assign = new Decision(Domain.IntegerRange(0, 1), "assign", city, city);
      Decision rank = new Decision(Domain.RealNonnegative, "rank", city);
      model.AddDecisions(assign, rank);

      // ------------
      // Goal: minimize the length of the tour.
      Goal goal = model.AddGoal("TourLength", GoalKind.Minimize,
        Model.Sum(Model.ForEach(city, i =&amp;gt; Model.ForEachWhere(city, j =&amp;gt; dist[i, j] * assign[i, j], j =&amp;gt; i != j))));

      // ------------
      // Enter and leave each city only once.
      int N = data.Length;
      model.AddConstraint("assign 1",
        Model.ForEach(city, i =&amp;gt; Model.Sum(Model.ForEachWhere(city, j =&amp;gt; assign[i, j],
          j =&amp;gt; i != j)) == 1));
      model.AddConstraint("assign 2",
        Model.ForEach(city, j =&amp;gt; Model.Sum(Model.ForEachWhere(city, i =&amp;gt; assign[i, j], i =&amp;gt; i != j)) == 1));
      model.AssignmentNoDiag(city, assign);

      // Forbid subtours (Miller, Tucker, Zemlin - 1960...)
      model.AddConstraint("no subtours",
        Model.ForEach(city,
          i =&amp;gt; Model.ForEachWhere(city,
            j =&amp;gt; rank[i] + 1 &amp;lt;= rank[j] + N * (1 - assign[i, j]),
            j =&amp;gt; Model.And(i != j, i &amp;gt;= 1, j &amp;gt;= 1)
          )
        )
      );

      Solution solution = context.Solve();

      // Retrieve solution information.
      Console.WriteLine("Cost = {0}", goal.ToDouble());
      Console.WriteLine("Tour:");
      var tour = from p in assign.GetValues() where (double)p[0] &amp;gt; 0.9 select p[2];
      foreach (var i in tour.ToArray()) {
        Console.Write(i + " -&amp;gt; ");
      }
      Console.WriteLine();
    }
  }
&lt;/PRE&gt;&lt;PRE style="MARGIN: 0in; FONT-FAMILY: Calibri; FONT-SIZE: 11pt"&gt;In my humble opinion, the "Parameter data =" line is an awesome example of the power of LINQ data binding in Solver Foundation.&lt;SPAN style="mso-spacerun: yes"&gt;&amp;nbsp; &lt;/SPAN&gt;We generate the 2D matrix of distances using a single LINQ expression.  It would be incredibly easy to change the code to retrieve the coordinate data from a database (perhaps using a LINQ expression once again), a file, or even a user application.&lt;/PRE&gt;&lt;PRE style="MARGIN: 0in; FONT-FAMILY: Calibri; FONT-SIZE: 11pt"&gt;&amp;nbsp;&lt;/PRE&gt;&lt;PRE style="MARGIN: 0in; FONT-FAMILY: Calibri; FONT-SIZE: 11pt"&gt;The goal is straightforward: minimize the distance traveled.&lt;SPAN style="mso-spacerun: yes"&gt;&amp;nbsp; &lt;/SPAN&gt;This is a product of the selected arcs and the distance matrix.&lt;SPAN style="mso-spacerun: yes"&gt;&amp;nbsp;&amp;nbsp; &lt;/SPAN&gt;We have two types of constraints:&lt;/PRE&gt;
&lt;UL&gt;
&lt;LI&gt;&lt;PRE style="MARGIN: 0in; FONT-FAMILY: Calibri; FONT-SIZE: 11pt"&gt;&lt;SPAN style="FONT-FAMILY: Calibri; FONT-SIZE: 11pt"&gt;Assignment constraints: these ensure that we enter and leave each city only once.&lt;/SPAN&gt;&lt;/PRE&gt;&lt;/LI&gt;
&lt;LI&gt;&lt;PRE style="MARGIN: 0in; FONT-FAMILY: Calibri; FONT-SIZE: 11pt"&gt;&lt;SPAN style="FONT-FAMILY: Calibri; FONT-SIZE: 11pt"&gt;&lt;/SPAN&gt;&lt;SPAN style="FONT-FAMILY: Calibri; FONT-SIZE: 11pt"&gt;Subtour constraints: these ensure that we do not have any subtours.&lt;SPAN style="mso-spacerun: yes"&gt;&amp;nbsp; &lt;/SPAN&gt;In a four city problem {A, B, C, D}, for example, we cannot have two cycles (A, B), (C, D).&lt;SPAN style="mso-spacerun: yes"&gt;&amp;nbsp; &lt;/SPAN&gt;We need to have one tour that contains all the cities.&lt;/SPAN&gt;&lt;/PRE&gt;&lt;/LI&gt;&lt;/UL&gt;&lt;PRE style="MARGIN: 0in; FONT-FAMILY: Calibri; FONT-SIZE: 11pt"&gt;The assignment constraints are easy using the ForEach and ForEachWhere operations.&lt;SPAN style="mso-spacerun: yes"&gt;&amp;nbsp; &lt;/SPAN&gt;I use ForEachWhere because I want to disallow arcs that enter and leave the same city - that doesn't make sense.&lt;SPAN style="mso-spacerun: yes"&gt;&amp;nbsp; &lt;/SPAN&gt;The subtour constraint is a little more complicated.   It relates the "assign" and "rank" decisions.  The key fact is that if there is an arc from city i to city j, rank[i] + 1 == j.  Of course, if the (i, j) arc is not part of the optimal tour then all bets are off.   Last note: notice that I can mix parameters, decisions, and C# variables in my expressions. &lt;/PRE&gt;&lt;PRE style="MARGIN: 0in; FONT-FAMILY: Calibri; FONT-SIZE: 11pt"&gt; &lt;P style="MARGIN: 0in; FONT-FAMILY: Calibri; FONT-SIZE: 11pt"&gt;Once we solve the model we want to print out the cost, and the optimal tour.&lt;SPAN style="mso-spacerun: yes"&gt;&amp;nbsp; &lt;/SPAN&gt;Getting the cost is very easy using goal.ToDouble().&lt;SPAN style="mso-spacerun: yes"&gt;&amp;nbsp; &lt;/SPAN&gt;We can get the tour using either Assign or Rank.&lt;SPAN style="mso-spacerun: yes"&gt;&amp;nbsp; &lt;/SPAN&gt;I have chosen to use Assign because it gives me another opportunity to use LINQ.&lt;SPAN style="mso-spacerun: yes"&gt;&amp;nbsp; &lt;/SPAN&gt;When you call GetValues() on a decision, you get arrays that contain the value along with the indexes for each decision.&lt;SPAN style="mso-spacerun: yes"&gt;&amp;nbsp; &lt;/SPAN&gt;In this case, the last entry in the array is the one we are interested in.  There are other ways to conveniently query decsision results, I'll save that for another time.&lt;/P&gt;&lt;P style="MARGIN: 0in; FONT-FAMILY: Calibri; FONT-SIZE: 11pt" mce_keep="true"&gt;&amp;nbsp;&lt;/P&gt;&lt;P style="MARGIN: 0in; FONT-FAMILY: Calibri; FONT-SIZE: 11pt"&gt;The next post will show how we can use Solver Foundation's plug-in model to tune the behavior of the Gurobi MIP solver.&lt;/P&gt; &lt;/PRE&gt;&lt;img src="http://blogs.msdn.com/aggbug.aspx?PostID=9571061" width="1" height="1"&gt;</description><category domain="http://blogs.msdn.com/natbr/archive/tags/C_2300_/default.aspx">C#</category><category domain="http://blogs.msdn.com/natbr/archive/tags/combinatorial+optimization/default.aspx">combinatorial optimization</category><category domain="http://blogs.msdn.com/natbr/archive/tags/Solver+Foundation/default.aspx">Solver Foundation</category><category domain="http://blogs.msdn.com/natbr/archive/tags/optimization/default.aspx">optimization</category><category domain="http://blogs.msdn.com/natbr/archive/tags/LINQ/default.aspx">LINQ</category><category domain="http://blogs.msdn.com/natbr/archive/tags/INFORMS/default.aspx">INFORMS</category></item><item><title>Two way data binding using LINQ and Solver Foundation Services</title><link>http://blogs.msdn.com/natbr/archive/2008/12/19/two-way-data-binding-using-linq-and-solver-foundation-services.aspx</link><pubDate>Sat, 20 Dec 2008 00:22:00 GMT</pubDate><guid isPermaLink="false">91d46819-8472-40ad-a661-2c78acb4018c:9242894</guid><dc:creator>Nathan Brixius</dc:creator><slash:comments>0</slash:comments><comments>http://blogs.msdn.com/natbr/comments/9242894.aspx</comments><wfw:commentRss>http://blogs.msdn.com/natbr/commentrss.aspx?PostID=9242894</wfw:commentRss><wfw:comment>http://blogs.msdn.com/natbr/rsscomments.aspx?PostID=9242894</wfw:comment><description>&lt;P&gt;Recently on the Microsoft Solver Foundation discussion boards there was a question about two-way data binding and Solver Foundation Services.&amp;nbsp;&amp;nbsp;The MSF-SFS Programming Primer has plenty of examples for helping you&amp;nbsp;learn to use Solver Foundation Services in your .Net applications.&amp;nbsp; Sample 5 is about binding output values - &lt;A target=_blank href="http://code.msdn.microsoft.com/solverfoundation/Thread/View.aspx?ThreadId=1099" mce_href="http://code.msdn.microsoft.com/solverfoundation/Thread/View.aspx?ThreadId=1099"&gt;user "detond" from our discussion boards extended the example&lt;/A&gt; to go against a&amp;nbsp;SQL DB, and I have cleaned up the code.&amp;nbsp; A few notes:&lt;/P&gt;
&lt;OL&gt;
&lt;LI&gt;You'll need to create a table named "ProductionCapacity" with nvarchar(max) Country, int MaxProduction, float Output columns.&lt;/LI&gt;
&lt;LI&gt;Create rows for Venezuela and SaudiArabia, with MaxProduction = 9000, 6000 to reproduce sample 5.&lt;/LI&gt;
&lt;LI&gt;The using() statement is necessary to prevent a SQL connection from leaking.&lt;/LI&gt;
&lt;LI&gt;db.SubmitChanges() is necessary to commit the changes back to the DB.&amp;nbsp; Otherwise only your in-memory copy is modified.&lt;/LI&gt;&lt;/OL&gt;&lt;PRE&gt;using System;
using System.Collections.Generic;
using System.Data.Linq;
using System.Data.Linq.Mapping;
using System.Linq;
using System.Text;
using Microsoft.SolverFoundation.Services;

namespace OutputBindings {

  [Table(Name = "ProductionCapacity")]
  public class Production {
    [Column(IsPrimaryKey = true)]
    public string Country;

    private int _MaxProduction;

    [Column(Storage = "_MaxProduction")]
    public int MaxProduction {
      get { return this._MaxProduction; }
      set { this._MaxProduction = value; }
    }

    private double _Output;

    [Column(Storage = "_Output")]
    public double Output {
      get { return this._Output; }
      set { this._Output = value; }
    }
  }

  class Program {
    static void Main(string[] args) {

      Decision vz, sa;
      Solution solution = null;
      using (DataContext db = new DataContext(@"Data Source=xxx\yyy; Initial Catalog=MSF; Integrated Security=True")) {
        db.Log = Console.Out; // Let's see what's happening.

        // Get a typed table to run queries
        Table&amp;lt;Production&amp;gt; Productions = db.GetTable&amp;lt;Production&amp;gt;();

        // Get the context and creating a new model.
        SolverContext context = SolverContext.GetContext();
        Model model = context.CreateModel();

        // Create two decision variables representing the number of barrels to
        // purchase from two countries.
        // AddDecisions tells the model about the two variables.
        vz = new Decision(Domain.RealNonnegative, "barrels_venezuela");
        sa = new Decision(Domain.RealNonnegative, "barrels_saudiarabia");

        vz.SetBinding(from row in Productions where row.Country == "Venezuela"
           select row, "Output");
        sa.SetBinding(from row in Productions where row.Country == "SaudiArabia"
           select row, "Output");
        model.AddDecisions(vz, sa);

        Parameter maxvz = new Parameter(Domain.RealNonnegative, 
           "maxproduction_venezuela");
        Parameter maxsa = new Parameter(Domain.RealNonnegative,   
           "maxproduction_saudiarabia");

        // To get the same results as in the sample, set MaxProduction=9000 for  
        // Venezuela, MaxProduction=6000 for SaudiArabia in your DB table.
        maxvz.SetBinding(from row in Productions where row.Country == "Venezuela" 
            select row, "MaxProduction");
        maxsa.SetBinding(from row in Productions where row.Country == "SaudiArabia" 
            select row, "MaxProduction");
        model.AddParameters(maxvz, maxsa);

        // Adding five contraints. The first line is two contraints giving the
        // allowable range for the two decision varibles. The other contraints put
        // minimums on the total yield of three products.
        model.AddConstraints("limits",
        0 &amp;lt;= vz &amp;lt;= maxvz,
        0 &amp;lt;= sa &amp;lt;= maxsa);
        model.AddConstraints("production",
        0.3 * sa + 0.4 * vz &amp;gt;= 2000,
        0.4 * sa + 0.2 * vz &amp;gt;= 1500,
        0.2 * sa + 0.3 * vz &amp;gt;= 500);

        model.AddGoal("cost", GoalKind.Minimize, 20 * sa + 15 * vz);
        solution = context.Solve(new SimplexDirective());

        context.PropagateDecisions(); // Propagate values to the in-memory rep.
        db.SubmitChanges(); // Commit to DB.
      }

      if (solution != null) {
        Report report = solution.GetReport();
        Console.WriteLine("vz: {0}, sa: {1}", vz, sa);
        Console.Write("{0}", report);
      }
    }
  }
}
&lt;/PRE&gt;&lt;img src="http://blogs.msdn.com/aggbug.aspx?PostID=9242894" width="1" height="1"&gt;</description><category domain="http://blogs.msdn.com/natbr/archive/tags/C_2300_/default.aspx">C#</category><category domain="http://blogs.msdn.com/natbr/archive/tags/Solver+Foundation/default.aspx">Solver Foundation</category><category domain="http://blogs.msdn.com/natbr/archive/tags/LINQ/default.aspx">LINQ</category></item></channel></rss>