// -*- c++ -*- #include #include #include #include using std::cout; using std::endl; using namespace lemon; /* On an 1537Mhz PC, the run times with glpk are the following. for n=3,4, some secondes for n=5, 25 hours */ int main(int, char **) { const int n=4; const double row_sum=(1.0+n*n)*n/2; Timer ts; ts.reset(); typedef LpGlpk LPSolver; typedef LPSolver::Col Col; LPSolver lp; typedef std::map, Col> Coords; Coords x; // we create a new variable for each entry // of the magic square for (int i=1; i<=n; ++i) { for (int j=1; j<=n; ++j) { Col col=lp.addCol(); x[std::make_pair(i,j)]=col; lp.setColLowerBound(col, 1.0); lp.setColUpperBound(col, double(n*n)); } } LPSolver::Expression expr3, expr4; for (int i=1; i<=n; ++i) { LPSolver::Expression expr1, expr2; for (int j=1; j<=n; ++j) { expr1+=x[std::make_pair(i, j)]; expr2+=x[std::make_pair(j, i)]; } // sum of rows and columns lp.addRow(expr1==row_sum); lp.addRow(expr2==row_sum); expr3+=x[std::make_pair(i, i)]; expr4+=x[std::make_pair(i, (n+1)-i)]; } // sum of the diagonal entries lp.addRow(expr3==row_sum); lp.addRow(expr4==row_sum); lp.solveSimplex(); cout << "elapsed time: " << ts << endl; for (int i=1; i<=n; ++i) { for (int j=1; j<=n; ++j) { cout << "x("<