tools/dimacs-to-lgf.cc
author Peter Kovacs <kpeter@inf.elte.hu>
Thu, 12 Nov 2009 23:26:13 +0100
changeset 872 fa6f37d7a25b
parent 608 6e0525ec5355
child 1397 d7e25df22e88
permissions -rw-r--r--
Entirely rework CapacityScaling (#180)

- Use the new interface similarly to NetworkSimplex.
- Rework the implementation using an efficient internal structure
for handling the residual network. This improvement made the
code much faster (up to 2-5 times faster on large graphs).
- Handle GEQ supply type (LEQ is not supported).
- Handle negative costs for arcs of finite capacity.
(Note that this algorithm cannot handle arcs of negative cost
and infinite upper bound, thus it returns UNBOUNDED if such
an arc exists.)
- Extend the documentation.
alpar@400
     1
/* -*- mode: C++; indent-tabs-mode: nil; -*-
alpar@400
     2
 *
alpar@400
     3
 * This file is a part of LEMON, a generic C++ optimization library.
alpar@400
     4
 *
alpar@463
     5
 * Copyright (C) 2003-2009
alpar@400
     6
 * Egervary Jeno Kombinatorikus Optimalizalasi Kutatocsoport
alpar@400
     7
 * (Egervary Research Group on Combinatorial Optimization, EGRES).
alpar@400
     8
 *
alpar@400
     9
 * Permission to use, modify and distribute this software is granted
alpar@400
    10
 * provided that this copyright notice appears in all copies. For
alpar@400
    11
 * precise terms see the accompanying LICENSE file.
alpar@400
    12
 *
alpar@400
    13
 * This software is provided "AS IS" with no warranty of any kind,
alpar@400
    14
 * express or implied, and with no claim as to its suitability for any
alpar@400
    15
 * purpose.
alpar@400
    16
 *
alpar@400
    17
 */
alpar@400
    18
alpar@400
    19
///\ingroup tools
alpar@400
    20
///\file
alpar@400
    21
///\brief DIMACS to LGF converter.
alpar@400
    22
///
alpar@400
    23
/// This program converts various DIMACS formats to the LEMON Digraph Format
alpar@400
    24
/// (LGF).
alpar@400
    25
///
alpar@400
    26
/// See
kpeter@631
    27
/// \code
kpeter@631
    28
///   dimacs-to-lgf --help
kpeter@631
    29
/// \endcode
kpeter@631
    30
/// for more info on the usage.
alpar@400
    31
alpar@400
    32
#include <iostream>
alpar@400
    33
#include <fstream>
alpar@400
    34
#include <cstring>
alpar@400
    35
alpar@400
    36
#include <lemon/smart_graph.h>
alpar@400
    37
#include <lemon/dimacs.h>
alpar@400
    38
#include <lemon/lgf_writer.h>
alpar@400
    39
alpar@400
    40
#include <lemon/arg_parser.h>
alpar@402
    41
#include <lemon/error.h>
alpar@400
    42
alpar@400
    43
using namespace std;
alpar@400
    44
using namespace lemon;
alpar@400
    45
alpar@400
    46
alpar@400
    47
int main(int argc, const char *argv[]) {
alpar@400
    48
  typedef SmartDigraph Digraph;
alpar@400
    49
alpar@400
    50
  typedef Digraph::Arc Arc;
alpar@400
    51
  typedef Digraph::Node Node;
alpar@400
    52
  typedef Digraph::ArcIt ArcIt;
alpar@400
    53
  typedef Digraph::NodeIt NodeIt;
alpar@400
    54
  typedef Digraph::ArcMap<double> DoubleArcMap;
alpar@400
    55
  typedef Digraph::NodeMap<double> DoubleNodeMap;
alpar@400
    56
alpar@400
    57
  std::string inputName;
alpar@400
    58
  std::string outputName;
alpar@400
    59
alpar@400
    60
  ArgParser ap(argc, argv);
alpar@402
    61
  ap.other("[INFILE [OUTFILE]]",
alpar@402
    62
           "If either the INFILE or OUTFILE file is missing the standard\n"
alpar@402
    63
           "     input/output will be used instead.")
alpar@400
    64
    .run();
alpar@400
    65
alpar@400
    66
  ifstream input;
alpar@402
    67
  ofstream output;
alpar@402
    68
alpar@402
    69
  switch(ap.files().size())
alpar@402
    70
    {
alpar@402
    71
    case 2:
alpar@402
    72
      output.open(ap.files()[1].c_str());
alpar@402
    73
      if (!output) {
alpar@402
    74
        throw IoError("Cannot open the file for writing", ap.files()[1]);
alpar@402
    75
      }
alpar@402
    76
    case 1:
alpar@402
    77
      input.open(ap.files()[0].c_str());
alpar@402
    78
      if (!input) {
alpar@402
    79
        throw IoError("File cannot be found", ap.files()[0]);
alpar@402
    80
      }
alpar@402
    81
    case 0:
alpar@402
    82
      break;
alpar@402
    83
    default:
alpar@402
    84
      cerr << ap.commandName() << ": too many arguments\n";
alpar@402
    85
      return 1;
alpar@402
    86
  }
alpar@402
    87
  istream& is = (ap.files().size()<1 ? cin : input);
alpar@402
    88
  ostream& os = (ap.files().size()<2 ? cout : output);
alpar@402
    89
alpar@402
    90
  DimacsDescriptor desc = dimacsType(is);
alpar@402
    91
  switch(desc.type)
alpar@402
    92
    {
alpar@402
    93
    case DimacsDescriptor::MIN:
alpar@402
    94
      {
alpar@402
    95
        Digraph digraph;
alpar@402
    96
        DoubleArcMap lower(digraph), capacity(digraph), cost(digraph);
alpar@402
    97
        DoubleNodeMap supply(digraph);
alpar@608
    98
        readDimacsMin(is, digraph, lower, capacity, cost, supply, 0, desc);
alpar@402
    99
        DigraphWriter<Digraph>(digraph, os).
alpar@402
   100
          nodeMap("supply", supply).
alpar@402
   101
          arcMap("lower", lower).
alpar@402
   102
          arcMap("capacity", capacity).
alpar@402
   103
          arcMap("cost", cost).
alpar@402
   104
          attribute("problem","min").
alpar@402
   105
          run();
alpar@402
   106
      }
alpar@402
   107
      break;
alpar@402
   108
    case DimacsDescriptor::MAX:
alpar@402
   109
      {
alpar@402
   110
        Digraph digraph;
alpar@402
   111
        Node s, t;
alpar@402
   112
        DoubleArcMap capacity(digraph);
alpar@608
   113
        readDimacsMax(is, digraph, capacity, s, t, 0, desc);
alpar@402
   114
        DigraphWriter<Digraph>(digraph, os).
alpar@402
   115
          arcMap("capacity", capacity).
alpar@402
   116
          node("source", s).
alpar@402
   117
          node("target", t).
alpar@402
   118
          attribute("problem","max").
alpar@402
   119
          run();
alpar@402
   120
      }
alpar@402
   121
      break;
alpar@402
   122
    case DimacsDescriptor::SP:
alpar@402
   123
      {
alpar@402
   124
        Digraph digraph;
alpar@402
   125
        Node s;
alpar@402
   126
        DoubleArcMap capacity(digraph);
alpar@402
   127
        readDimacsSp(is, digraph, capacity, s, desc);
alpar@402
   128
        DigraphWriter<Digraph>(digraph, os).
alpar@402
   129
          arcMap("capacity", capacity).
alpar@402
   130
          node("source", s).
alpar@402
   131
          attribute("problem","sp").
alpar@402
   132
          run();
alpar@402
   133
      }
alpar@402
   134
      break;
alpar@402
   135
    case DimacsDescriptor::MAT:
alpar@402
   136
      {
alpar@402
   137
        Digraph digraph;
alpar@402
   138
        readDimacsMat(is, digraph,desc);
alpar@402
   139
        DigraphWriter<Digraph>(digraph, os).
alpar@402
   140
          attribute("problem","mat").
alpar@402
   141
          run();
alpar@402
   142
      }
alpar@402
   143
      break;
alpar@402
   144
    default:
alpar@402
   145
      break;
alpar@400
   146
    }
alpar@400
   147
  return 0;
alpar@400
   148
}