Merge
authorAlpar Juttner <alpar@cs.elte.hu>
Wed, 01 Oct 2008 13:56:40 +0200
changeset 294cbe3ec2d59d2
parent 293 47fbc814aa31
parent 292 e7af73f1805e
child 295 7c796c1cf1b0
child 296 9768e60aa4e1
Merge
demo/lgf_demo.cc
lemon/lgf_reader.h
lemon/lgf_writer.h
     1.1 --- a/demo/lgf_demo.cc	Wed Oct 01 12:44:16 2008 +0200
     1.2 +++ b/demo/lgf_demo.cc	Wed Oct 01 13:56:40 2008 +0200
     1.3 @@ -49,7 +49,7 @@
     1.4        node("source", s).             // read 'source' node to s
     1.5        node("target", t).             // read 'target' node to t
     1.6        run();
     1.7 -  } catch (DataFormatError& error) { // check if there was any error
     1.8 +  } catch (Exception& error) { // check if there was any error
     1.9      std::cerr << "Error: " << error.what() << std::endl;
    1.10      return -1;
    1.11    }
     2.1 --- a/lemon/arg_parser.h	Wed Oct 01 12:44:16 2008 +0200
     2.2 +++ b/lemon/arg_parser.h	Wed Oct 01 13:56:40 2008 +0200
     2.3 @@ -310,8 +310,9 @@
     2.4  
     2.5      ///This is the type of the return value of ArgParser::operator[]().
     2.6      ///It automatically converts to \c int, \c double, \c bool or
     2.7 -    ///\c std::string if the type of the option matches, otherwise it
     2.8 -    ///throws an exception (i.e. it performs runtime type checking).
     2.9 +    ///\c std::string if the type of the option matches, which is checked
    2.10 +    ///with an \ref LEMON_ASSERT "assertion" (i.e. it performs runtime
    2.11 +    ///type checking).
    2.12      class RefType
    2.13      {
    2.14        const ArgParser &_parser;
     3.1 --- a/lemon/assert.h	Wed Oct 01 12:44:16 2008 +0200
     3.2 +++ b/lemon/assert.h	Wed Oct 01 13:56:40 2008 +0200
     3.3 @@ -108,7 +108,7 @@
     3.4  ///
     3.5  /// \brief Macro for assertion with customizable message
     3.6  ///
     3.7 -/// Macro for assertion with customizable message.  
     3.8 +/// Macro for assertion with customizable message.
     3.9  /// \param exp An expression that must be convertible to \c bool.  If it is \c
    3.10  /// false, then an assertion is raised. The concrete behaviour depends on the
    3.11  /// settings of the assertion system.
     4.1 --- a/lemon/bfs.h	Wed Oct 01 12:44:16 2008 +0200
     4.2 +++ b/lemon/bfs.h	Wed Oct 01 13:56:40 2008 +0200
     4.3 @@ -135,16 +135,6 @@
     4.4  #endif
     4.5    class Bfs {
     4.6    public:
     4.7 -    ///\ref Exception for uninitialized parameters.
     4.8 -
     4.9 -    ///This error represents problems in the initialization of the
    4.10 -    ///parameters of the algorithm.
    4.11 -    class UninitializedParameter : public lemon::UninitializedParameter {
    4.12 -    public:
    4.13 -      virtual const char* what() const throw() {
    4.14 -        return "lemon::Bfs::UninitializedParameter";
    4.15 -      }
    4.16 -    };
    4.17  
    4.18      ///The type of the digraph the algorithm runs on.
    4.19      typedef typename TR::Digraph Digraph;
    4.20 @@ -232,7 +222,8 @@
    4.21        typedef T PredMap;
    4.22        static PredMap *createPredMap(const Digraph &)
    4.23        {
    4.24 -        throw UninitializedParameter();
    4.25 +        LEMON_ASSERT(false, "PredMap is not initialized");
    4.26 +        return 0; // ignore warnings
    4.27        }
    4.28      };
    4.29      ///\brief \ref named-templ-param "Named parameter" for setting
    4.30 @@ -250,7 +241,8 @@
    4.31        typedef T DistMap;
    4.32        static DistMap *createDistMap(const Digraph &)
    4.33        {
    4.34 -        throw UninitializedParameter();
    4.35 +        LEMON_ASSERT(false, "DistMap is not initialized");
    4.36 +        return 0; // ignore warnings
    4.37        }
    4.38      };
    4.39      ///\brief \ref named-templ-param "Named parameter" for setting
    4.40 @@ -268,7 +260,8 @@
    4.41        typedef T ReachedMap;
    4.42        static ReachedMap *createReachedMap(const Digraph &)
    4.43        {
    4.44 -        throw UninitializedParameter();
    4.45 +        LEMON_ASSERT(false, "ReachedMap is not initialized");
    4.46 +        return 0; // ignore warnings
    4.47        }
    4.48      };
    4.49      ///\brief \ref named-templ-param "Named parameter" for setting
    4.50 @@ -286,7 +279,8 @@
    4.51        typedef T ProcessedMap;
    4.52        static ProcessedMap *createProcessedMap(const Digraph &)
    4.53        {
    4.54 -        throw UninitializedParameter();
    4.55 +        LEMON_ASSERT(false, "ProcessedMap is not initialized");
    4.56 +        return 0; // ignore warnings
    4.57        }
    4.58      };
    4.59      ///\brief \ref named-templ-param "Named parameter" for setting
    4.60 @@ -304,6 +298,7 @@
    4.61        static ProcessedMap *createProcessedMap(const Digraph &g)
    4.62        {
    4.63          return new ProcessedMap(g);
    4.64 +        return 0; // ignore warnings
    4.65        }
    4.66      };
    4.67      ///\brief \ref named-templ-param "Named parameter" for setting
    4.68 @@ -1040,7 +1035,6 @@
    4.69      ///\return \c true if \c t is reachable form \c s.
    4.70      bool run(Node s, Node t)
    4.71      {
    4.72 -      if (s==INVALID || t==INVALID) throw UninitializedParameter();
    4.73        Bfs<Digraph,TR> alg(*reinterpret_cast<const Digraph*>(Base::_g));
    4.74        if (Base::_pred)
    4.75          alg.predMap(*reinterpret_cast<PredMap*>(Base::_pred));
    4.76 @@ -1323,18 +1317,6 @@
    4.77    class BfsVisit {
    4.78    public:
    4.79  
    4.80 -    /// \brief \ref Exception for uninitialized parameters.
    4.81 -    ///
    4.82 -    /// This error represents problems in the initialization
    4.83 -    /// of the parameters of the algorithm.
    4.84 -    class UninitializedParameter : public lemon::UninitializedParameter {
    4.85 -    public:
    4.86 -      virtual const char* what() const throw()
    4.87 -      {
    4.88 -        return "lemon::BfsVisit::UninitializedParameter";
    4.89 -      }
    4.90 -    };
    4.91 -
    4.92      ///The traits class.
    4.93      typedef _Traits Traits;
    4.94  
    4.95 @@ -1389,7 +1371,8 @@
    4.96      struct SetReachedMapTraits : public Traits {
    4.97        typedef T ReachedMap;
    4.98        static ReachedMap *createReachedMap(const Digraph &digraph) {
    4.99 -        throw UninitializedParameter();
   4.100 +        LEMON_ASSERT(false, "ReachedMap is not initialized");
   4.101 +        return 0; // ignore warnings
   4.102        }
   4.103      };
   4.104      /// \brief \ref named-templ-param "Named parameter" for setting
     5.1 --- a/lemon/concepts/heap.h	Wed Oct 01 12:44:16 2008 +0200
     5.2 +++ b/lemon/concepts/heap.h	Wed Oct 01 13:56:40 2008 +0200
     5.3 @@ -129,7 +129,6 @@
     5.4        /// already stored in the heap.
     5.5        /// Otherwise it inserts the given item with the given priority.
     5.6        ///
     5.7 -      /// It may throw an \ref UnderflowPriorityException.
     5.8        /// \param i The item.
     5.9        /// \param p The priority.
    5.10        void set(const Item &i, const Prio &p) {}
     6.1 --- a/lemon/dfs.h	Wed Oct 01 12:44:16 2008 +0200
     6.2 +++ b/lemon/dfs.h	Wed Oct 01 13:56:40 2008 +0200
     6.3 @@ -136,16 +136,6 @@
     6.4  #endif
     6.5    class Dfs {
     6.6    public:
     6.7 -    ///\ref Exception for uninitialized parameters.
     6.8 -
     6.9 -    ///This error represents problems in the initialization of the
    6.10 -    ///parameters of the algorithm.
    6.11 -    class UninitializedParameter : public lemon::UninitializedParameter {
    6.12 -    public:
    6.13 -      virtual const char* what() const throw() {
    6.14 -        return "lemon::Dfs::UninitializedParameter";
    6.15 -      }
    6.16 -    };
    6.17  
    6.18      ///The type of the digraph the algorithm runs on.
    6.19      typedef typename TR::Digraph Digraph;
    6.20 @@ -232,7 +222,8 @@
    6.21        typedef T PredMap;
    6.22        static PredMap *createPredMap(const Digraph &)
    6.23        {
    6.24 -        throw UninitializedParameter();
    6.25 +        LEMON_ASSERT(false, "PredMap is not initialized");
    6.26 +        return 0; // ignore warnings
    6.27        }
    6.28      };
    6.29      ///\brief \ref named-templ-param "Named parameter" for setting
    6.30 @@ -250,7 +241,8 @@
    6.31        typedef T DistMap;
    6.32        static DistMap *createDistMap(const Digraph &)
    6.33        {
    6.34 -        throw UninitializedParameter();
    6.35 +        LEMON_ASSERT(false, "DistMap is not initialized");
    6.36 +        return 0; // ignore warnings
    6.37        }
    6.38      };
    6.39      ///\brief \ref named-templ-param "Named parameter" for setting
    6.40 @@ -268,7 +260,8 @@
    6.41        typedef T ReachedMap;
    6.42        static ReachedMap *createReachedMap(const Digraph &)
    6.43        {
    6.44 -        throw UninitializedParameter();
    6.45 +        LEMON_ASSERT(false, "ReachedMap is not initialized");
    6.46 +        return 0; // ignore warnings
    6.47        }
    6.48      };
    6.49      ///\brief \ref named-templ-param "Named parameter" for setting
    6.50 @@ -286,7 +279,8 @@
    6.51        typedef T ProcessedMap;
    6.52        static ProcessedMap *createProcessedMap(const Digraph &)
    6.53        {
    6.54 -        throw UninitializedParameter();
    6.55 +        LEMON_ASSERT(false, "ProcessedMap is not initialized");
    6.56 +        return 0; // ignore warnings
    6.57        }
    6.58      };
    6.59      ///\brief \ref named-templ-param "Named parameter" for setting
    6.60 @@ -974,7 +968,6 @@
    6.61      ///\return \c true if \c t is reachable form \c s.
    6.62      bool run(Node s, Node t)
    6.63      {
    6.64 -      if (s==INVALID || t==INVALID) throw UninitializedParameter();
    6.65        Dfs<Digraph,TR> alg(*reinterpret_cast<const Digraph*>(Base::_g));
    6.66        if (Base::_pred)
    6.67          alg.predMap(*reinterpret_cast<PredMap*>(Base::_pred));
    6.68 @@ -1270,18 +1263,6 @@
    6.69    class DfsVisit {
    6.70    public:
    6.71  
    6.72 -    /// \brief \ref Exception for uninitialized parameters.
    6.73 -    ///
    6.74 -    /// This error represents problems in the initialization
    6.75 -    /// of the parameters of the algorithm.
    6.76 -    class UninitializedParameter : public lemon::UninitializedParameter {
    6.77 -    public:
    6.78 -      virtual const char* what() const throw()
    6.79 -      {
    6.80 -        return "lemon::DfsVisit::UninitializedParameter";
    6.81 -      }
    6.82 -    };
    6.83 -
    6.84      ///The traits class.
    6.85      typedef _Traits Traits;
    6.86  
    6.87 @@ -1336,7 +1317,8 @@
    6.88      struct SetReachedMapTraits : public Traits {
    6.89        typedef T ReachedMap;
    6.90        static ReachedMap *createReachedMap(const Digraph &digraph) {
    6.91 -        throw UninitializedParameter();
    6.92 +        LEMON_ASSERT(false, "ReachedMap is not initialized");
    6.93 +        return 0; // ignore warnings
    6.94        }
    6.95      };
    6.96      /// \brief \ref named-templ-param "Named parameter" for setting
     7.1 --- a/lemon/dijkstra.h	Wed Oct 01 12:44:16 2008 +0200
     7.2 +++ b/lemon/dijkstra.h	Wed Oct 01 13:56:40 2008 +0200
     7.3 @@ -225,16 +225,6 @@
     7.4  #endif
     7.5    class Dijkstra {
     7.6    public:
     7.7 -    ///\ref Exception for uninitialized parameters.
     7.8 -
     7.9 -    ///This error represents problems in the initialization of the
    7.10 -    ///parameters of the algorithm.
    7.11 -    class UninitializedParameter : public lemon::UninitializedParameter {
    7.12 -    public:
    7.13 -      virtual const char* what() const throw() {
    7.14 -        return "lemon::Dijkstra::UninitializedParameter";
    7.15 -      }
    7.16 -    };
    7.17  
    7.18      ///The type of the digraph the algorithm runs on.
    7.19      typedef typename TR::Digraph Digraph;
    7.20 @@ -332,7 +322,8 @@
    7.21        typedef T PredMap;
    7.22        static PredMap *createPredMap(const Digraph &)
    7.23        {
    7.24 -        throw UninitializedParameter();
    7.25 +        LEMON_ASSERT(false, "PredMap is not initialized");
    7.26 +        return 0; // ignore warnings
    7.27        }
    7.28      };
    7.29      ///\brief \ref named-templ-param "Named parameter" for setting
    7.30 @@ -351,7 +342,8 @@
    7.31        typedef T DistMap;
    7.32        static DistMap *createDistMap(const Digraph &)
    7.33        {
    7.34 -        throw UninitializedParameter();
    7.35 +        LEMON_ASSERT(false, "DistMap is not initialized");
    7.36 +        return 0; // ignore warnings
    7.37        }
    7.38      };
    7.39      ///\brief \ref named-templ-param "Named parameter" for setting
    7.40 @@ -370,7 +362,8 @@
    7.41        typedef T ProcessedMap;
    7.42        static ProcessedMap *createProcessedMap(const Digraph &)
    7.43        {
    7.44 -        throw UninitializedParameter();
    7.45 +        LEMON_ASSERT(false, "ProcessedMap is not initialized");
    7.46 +        return 0; // ignore warnings
    7.47        }
    7.48      };
    7.49      ///\brief \ref named-templ-param "Named parameter" for setting
    7.50 @@ -408,11 +401,13 @@
    7.51        typedef CR HeapCrossRef;
    7.52        typedef H Heap;
    7.53        static HeapCrossRef *createHeapCrossRef(const Digraph &) {
    7.54 -        throw UninitializedParameter();
    7.55 +        LEMON_ASSERT(false, "HeapCrossRef is not initialized");
    7.56 +        return 0; // ignore warnings
    7.57        }
    7.58        static Heap *createHeap(HeapCrossRef &)
    7.59        {
    7.60 -        throw UninitializedParameter();
    7.61 +        LEMON_ASSERT(false, "Heap is not initialized");
    7.62 +        return 0; // ignore warnings
    7.63        }
    7.64      };
    7.65      ///\brief \ref named-templ-param "Named parameter" for setting
    7.66 @@ -1158,7 +1153,6 @@
    7.67      ///in order to compute the shortest path to each node.
    7.68      void run(Node s)
    7.69      {
    7.70 -      if (s==INVALID) throw UninitializedParameter();
    7.71        Dijkstra<Digraph,LengthMap,TR>
    7.72          dijk(*reinterpret_cast<const Digraph*>(Base::_g),
    7.73               *reinterpret_cast<const LengthMap*>(Base::_length));
    7.74 @@ -1180,7 +1174,6 @@
    7.75      ///\return \c true if \c t is reachable form \c s.
    7.76      bool run(Node s, Node t)
    7.77      {
    7.78 -      if (s==INVALID || t==INVALID) throw UninitializedParameter();
    7.79        Dijkstra<Digraph,LengthMap,TR>
    7.80          dijk(*reinterpret_cast<const Digraph*>(Base::_g),
    7.81               *reinterpret_cast<const LengthMap*>(Base::_length));
     8.1 --- a/lemon/error.h	Wed Oct 01 12:44:16 2008 +0200
     8.2 +++ b/lemon/error.h	Wed Oct 01 13:56:40 2008 +0200
     8.3 @@ -35,380 +35,238 @@
     8.4    /// \addtogroup exceptions
     8.5    /// @{
     8.6  
     8.7 -  /// \brief Exception safe wrapper class.
     8.8 +  /// \brief Generic exception class.
     8.9    ///
    8.10 -  /// Exception safe wrapper class to implement the members of exceptions.
    8.11 -  template <typename _Type>
    8.12 -  class ExceptionMember {
    8.13 -  public:
    8.14 -    typedef _Type Type;
    8.15 -
    8.16 -    ExceptionMember() throw() {
    8.17 -      try {
    8.18 -        ptr.reset(new Type());
    8.19 -      } catch (...) {}
    8.20 -    }
    8.21 -
    8.22 -    ExceptionMember(const Type& type) throw() {
    8.23 -      try {
    8.24 -        ptr.reset(new Type());
    8.25 -        if (ptr.get() == 0) return;
    8.26 -        *ptr = type;
    8.27 -      } catch (...) {}
    8.28 -    }
    8.29 -
    8.30 -    ExceptionMember(const ExceptionMember& copy) throw() {
    8.31 -      try {
    8.32 -        if (!copy.valid()) return;
    8.33 -        ptr.reset(new Type());
    8.34 -        if (ptr.get() == 0) return;
    8.35 -        *ptr = copy.get();
    8.36 -      } catch (...) {}
    8.37 -    }
    8.38 -
    8.39 -    ExceptionMember& operator=(const ExceptionMember& copy) throw() {
    8.40 -      if (ptr.get() == 0) return;
    8.41 -      try {
    8.42 -        if (!copy.valid()) return;
    8.43 -        *ptr = copy.get();
    8.44 -      } catch (...) {}
    8.45 -    }
    8.46 -
    8.47 -    void set(const Type& type) throw() {
    8.48 -      if (ptr.get() == 0) return;
    8.49 -      try {
    8.50 -        *ptr = type;
    8.51 -      } catch (...) {}
    8.52 -    }
    8.53 -
    8.54 -    const Type& get() const {
    8.55 -      return *ptr;
    8.56 -    }
    8.57 -
    8.58 -    bool valid() const throw() {
    8.59 -      return ptr.get() != 0;
    8.60 -    }
    8.61 -
    8.62 -  private:
    8.63 -    std::auto_ptr<_Type> ptr;
    8.64 -  };
    8.65 -
    8.66 -  /// Exception-safe convenient error message builder class.
    8.67 -
    8.68 -  /// Helper class which provides a convenient ostream-like (operator <<
    8.69 -  /// based) interface to create a string message. Mostly useful in
    8.70 -  /// exception classes (therefore the name).
    8.71 -  class ErrorMessage {
    8.72 -  protected:
    8.73 -    ///\e
    8.74 -
    8.75 -    mutable std::auto_ptr<std::ostringstream> buf;
    8.76 -
    8.77 -    ///\e
    8.78 -    bool init() throw() {
    8.79 -      try {
    8.80 -        buf.reset(new std::ostringstream);
    8.81 -      }
    8.82 -      catch(...) {
    8.83 -        buf.reset();
    8.84 -      }
    8.85 -      return buf.get();
    8.86 -    }
    8.87 -
    8.88 -  public:
    8.89 -
    8.90 -    ///\e
    8.91 -    ErrorMessage() throw() { init(); }
    8.92 -
    8.93 -    ErrorMessage(const ErrorMessage& em) throw() : buf(em.buf) { }
    8.94 -
    8.95 -    ///\e
    8.96 -    ErrorMessage(const char *msg) throw() {
    8.97 -      init();
    8.98 -      *this << msg;
    8.99 -    }
   8.100 -
   8.101 -    ///\e
   8.102 -    ErrorMessage(const std::string &msg) throw() {
   8.103 -      init();
   8.104 -      *this << msg;
   8.105 -    }
   8.106 -
   8.107 -    ///\e
   8.108 -    template <typename T>
   8.109 -    ErrorMessage& operator<<(const T &t) throw() {
   8.110 -      if( ! buf.get() ) return *this;
   8.111 -
   8.112 -      try {
   8.113 -        *buf << t;
   8.114 -      }
   8.115 -      catch(...) {
   8.116 -        buf.reset();
   8.117 -      }
   8.118 -      return *this;
   8.119 -    }
   8.120 -
   8.121 -    ///\e
   8.122 -    const char* message() throw() {
   8.123 -      if( ! buf.get() ) return 0;
   8.124 -
   8.125 -      const char* mes = 0;
   8.126 -      try {
   8.127 -        mes = buf->str().c_str();
   8.128 -      }
   8.129 -      catch(...) {}
   8.130 -      return mes;
   8.131 -    }
   8.132 -
   8.133 -  };
   8.134 -
   8.135 -  /// Generic exception class.
   8.136 -
   8.137    /// Base class for exceptions used in LEMON.
   8.138    ///
   8.139    class Exception : public std::exception {
   8.140    public:
   8.141 -    ///\e
   8.142 -    Exception() {}
   8.143 -    ///\e
   8.144 +    ///Constructor
   8.145 +    Exception() throw() {}
   8.146 +    ///Virtual destructor
   8.147      virtual ~Exception() throw() {}
   8.148 -    ///\e
   8.149 +    ///A short description of the exception
   8.150      virtual const char* what() const throw() {
   8.151        return "lemon::Exception";
   8.152      }
   8.153    };
   8.154  
   8.155 -  /// One of the two main subclasses of \ref Exception.
   8.156 +  /// \brief Input-Output error
   8.157 +  ///
   8.158 +  /// This exception is thrown when a file operation cannot be
   8.159 +  /// succeeded.
   8.160 +  class IoError : public Exception {
   8.161 +  protected:
   8.162 +    std::string _message;
   8.163 +    std::string _file;
   8.164  
   8.165 -  /// Logic errors represent problems in the internal logic of a program;
   8.166 -  /// in theory, these are preventable, and even detectable before the
   8.167 -  /// program runs (e.g. violations of class invariants).
   8.168 -  ///
   8.169 -  /// A typical example for this is \ref UninitializedParameter.
   8.170 -  class LogicError : public Exception {
   8.171 +    mutable std::string _what;
   8.172    public:
   8.173 +
   8.174 +    /// Copy constructor
   8.175 +    IoError(const IoError &error) throw() : Exception() {
   8.176 +      message(error._message);
   8.177 +      file(error._file);
   8.178 +    }
   8.179 +
   8.180 +    /// Constructor
   8.181 +    explicit IoError(const char *message) throw() {
   8.182 +      IoError::message(message);
   8.183 +    }
   8.184 +
   8.185 +    /// Constructor
   8.186 +    explicit IoError(const std::string &message) throw() {
   8.187 +      IoError::message(message);
   8.188 +    }
   8.189 +
   8.190 +    /// Constructor
   8.191 +    explicit IoError(const char *message,
   8.192 +                     const std::string &file) throw() {
   8.193 +      IoError::message(message);
   8.194 +      IoError::file(file);
   8.195 +    }
   8.196 +
   8.197 +    /// Constructor
   8.198 +    explicit IoError(const std::string &message,
   8.199 +                     const std::string &file) throw() {
   8.200 +      IoError::message(message);
   8.201 +      IoError::file(file);
   8.202 +    }
   8.203 +
   8.204 +    /// Virtual destructor
   8.205 +    virtual ~IoError() throw() {}
   8.206 +
   8.207 +    /// Set the error message
   8.208 +    void message(const char *message) throw() {
   8.209 +      try {
   8.210 +        _message = message;
   8.211 +      } catch (...) {}
   8.212 +    }
   8.213 +
   8.214 +    /// Set the error message
   8.215 +    void message(const std::string& message) throw() {
   8.216 +      try {
   8.217 +        _message = message;
   8.218 +      } catch (...) {}
   8.219 +    }
   8.220 +
   8.221 +    /// Set the file name
   8.222 +    void file(const std::string &file) throw() {
   8.223 +      try {
   8.224 +        _file = file;
   8.225 +      } catch (...) {}
   8.226 +    }
   8.227 +
   8.228 +    /// Returns the error message
   8.229 +    const std::string& message() const throw() {
   8.230 +      return _message;
   8.231 +    }
   8.232 +
   8.233 +    /// \brief Returns the filename
   8.234 +    ///
   8.235 +    /// Returns the filename or an empty string if it was not specified.
   8.236 +    const std::string& file() const throw() {
   8.237 +      return _file;
   8.238 +    }
   8.239 +
   8.240 +    /// \brief Returns a short error message
   8.241 +    ///
   8.242 +    /// Returns a short error message which contains the message and the
   8.243 +    /// file name.
   8.244      virtual const char* what() const throw() {
   8.245 -      return "lemon::LogicError";
   8.246 +      try {
   8.247 +        _what.clear();
   8.248 +        std::ostringstream oss;
   8.249 +        oss << "lemon:IoError" << ": ";
   8.250 +        oss << _message;
   8.251 +        if (!_file.empty()) {
   8.252 +          oss << " ('" << _file << "')";
   8.253 +        }
   8.254 +        _what = oss.str();
   8.255 +      }
   8.256 +      catch (...) {}
   8.257 +      if (!_what.empty()) return _what.c_str();
   8.258 +      else return "lemon:IoError";
   8.259      }
   8.260 +
   8.261    };
   8.262  
   8.263 -  /// \ref Exception for uninitialized parameters.
   8.264 -
   8.265 -  /// This error represents problems in the initialization
   8.266 -  /// of the parameters of the algorithms.
   8.267 -  class UninitializedParameter : public LogicError {
   8.268 -  public:
   8.269 -    virtual const char* what() const throw() {
   8.270 -      return "lemon::UninitializedParameter";
   8.271 -    }
   8.272 -  };
   8.273 -
   8.274 -
   8.275 -  /// One of the two main subclasses of \ref Exception.
   8.276 -
   8.277 -  /// Runtime errors represent problems outside the scope of a program;
   8.278 -  /// they cannot be easily predicted and can generally only be caught
   8.279 -  /// as the program executes.
   8.280 -  class RuntimeError : public Exception {
   8.281 -  public:
   8.282 -    virtual const char* what() const throw() {
   8.283 -      return "lemon::RuntimeError";
   8.284 -    }
   8.285 -  };
   8.286 -
   8.287 -  ///\e
   8.288 -  class RangeError : public RuntimeError {
   8.289 -  public:
   8.290 -    virtual const char* what() const throw() {
   8.291 -      return "lemon::RangeError";
   8.292 -    }
   8.293 -  };
   8.294 -
   8.295 -  ///\e
   8.296 -  class IoError : public RuntimeError {
   8.297 -  public:
   8.298 -    virtual const char* what() const throw() {
   8.299 -      return "lemon::IoError";
   8.300 -    }
   8.301 -  };
   8.302 -
   8.303 -  ///\e
   8.304 -  class DataFormatError : public IoError {
   8.305 +  /// \brief Format error
   8.306 +  ///
   8.307 +  /// This exception is thrown when an input file has wrong
   8.308 +  /// format or a data representation is not legal.
   8.309 +  class FormatError : public Exception {
   8.310    protected:
   8.311 -    ExceptionMember<std::string> _message;
   8.312 -    ExceptionMember<std::string> _file;
   8.313 +    std::string _message;
   8.314 +    std::string _file;
   8.315      int _line;
   8.316  
   8.317 -    mutable ExceptionMember<std::string> _message_holder;
   8.318 +    mutable std::string _what;
   8.319    public:
   8.320  
   8.321 -    DataFormatError(const DataFormatError &dfe) :
   8.322 -      IoError(dfe), _message(dfe._message), _file(dfe._file),
   8.323 -      _line(dfe._line) {}
   8.324 -
   8.325 -    ///\e
   8.326 -    explicit DataFormatError(const char *the_message)
   8.327 -      : _message(the_message), _line(0) {}
   8.328 -
   8.329 -    ///\e
   8.330 -    DataFormatError(const std::string &file_name, int line_num,
   8.331 -                    const char *the_message)
   8.332 -      : _message(the_message), _line(line_num) { file(file_name); }
   8.333 -
   8.334 -    ///\e
   8.335 -    void line(int ln) { _line = ln; }
   8.336 -    ///\e
   8.337 -    void message(const std::string& msg) { _message.set(msg); }
   8.338 -    ///\e
   8.339 -    void file(const std::string &fl) { _file.set(fl); }
   8.340 -
   8.341 -    ///\e
   8.342 -    int line() const { return _line; }
   8.343 -    ///\e
   8.344 -    const char* message() const {
   8.345 -      if (_message.valid() && !_message.get().empty()) {
   8.346 -        return _message.get().c_str();
   8.347 -      } else {
   8.348 -        return 0;
   8.349 -      }
   8.350 +    /// Copy constructor
   8.351 +    FormatError(const FormatError &error) throw() : Exception() {
   8.352 +      message(error._message);
   8.353 +      file(error._file);
   8.354 +      line(error._line);
   8.355      }
   8.356  
   8.357 -    /// \brief Returns the filename.
   8.358 -    ///
   8.359 -    /// Returns \e null if the filename was not specified.
   8.360 -    const char* file() const {
   8.361 -      if (_file.valid() && !_file.get().empty()) {
   8.362 -        return _file.get().c_str();
   8.363 -      } else {
   8.364 -        return 0;
   8.365 -      }
   8.366 +    /// Constructor
   8.367 +    explicit FormatError(const char *message) throw() {
   8.368 +      FormatError::message(message);
   8.369 +      _line = 0;
   8.370      }
   8.371  
   8.372 -    ///\e
   8.373 +    /// Constructor
   8.374 +    explicit FormatError(const std::string &message) throw() {
   8.375 +      FormatError::message(message);
   8.376 +      _line = 0;
   8.377 +    }
   8.378 +
   8.379 +    /// Constructor
   8.380 +    explicit FormatError(const char *message,
   8.381 +                         const std::string &file, int line = 0) throw() {
   8.382 +      FormatError::message(message);
   8.383 +      FormatError::file(file);
   8.384 +      FormatError::line(line);
   8.385 +    }
   8.386 +
   8.387 +    /// Constructor
   8.388 +    explicit FormatError(const std::string &message,
   8.389 +                         const std::string &file, int line = 0) throw() {
   8.390 +      FormatError::message(message);
   8.391 +      FormatError::file(file);
   8.392 +      FormatError::line(line);
   8.393 +    }
   8.394 +
   8.395 +    /// Virtual destructor
   8.396 +    virtual ~FormatError() throw() {}
   8.397 +
   8.398 +    /// Set the line number
   8.399 +    void line(int line) throw() { _line = line; }
   8.400 +
   8.401 +    /// Set the error message
   8.402 +    void message(const char *message) throw() {
   8.403 +      try {
   8.404 +        _message = message;
   8.405 +      } catch (...) {}
   8.406 +    }
   8.407 +
   8.408 +    /// Set the error message
   8.409 +    void message(const std::string& message) throw() {
   8.410 +      try {
   8.411 +        _message = message;
   8.412 +      } catch (...) {}
   8.413 +    }
   8.414 +
   8.415 +    /// Set the file name
   8.416 +    void file(const std::string &file) throw() {
   8.417 +      try {
   8.418 +        _file = file;
   8.419 +      } catch (...) {}
   8.420 +    }
   8.421 +
   8.422 +    /// \brief Returns the line number
   8.423 +    ///
   8.424 +    /// Returns the line number or zero if it was not specified.
   8.425 +    int line() const throw() { return _line; }
   8.426 +
   8.427 +    /// Returns the error message
   8.428 +    const std::string& message() const throw() {
   8.429 +      return _message;
   8.430 +    }
   8.431 +
   8.432 +    /// \brief Returns the filename
   8.433 +    ///
   8.434 +    /// Returns the filename or an empty string if it was not specified.
   8.435 +    const std::string& file() const throw() {
   8.436 +      return _file;
   8.437 +    }
   8.438 +
   8.439 +    /// \brief Returns a short error message
   8.440 +    ///
   8.441 +    /// Returns a short error message which contains the message, the
   8.442 +    /// file name and the line number.
   8.443      virtual const char* what() const throw() {
   8.444        try {
   8.445 -        std::ostringstream ostr;
   8.446 -        ostr << "lemon:DataFormatError" << ": ";
   8.447 -        if (message()) ostr << message();
   8.448 -        if( file() || line() != 0 ) {
   8.449 -          ostr << " (";
   8.450 -          if( file() ) ostr << "in file '" << file() << "'";
   8.451 -          if( file() && line() != 0 ) ostr << " ";
   8.452 -          if( line() != 0 ) ostr << "at line " << line();
   8.453 -          ostr << ")";
   8.454 +        _what.clear();
   8.455 +        std::ostringstream oss;
   8.456 +        oss << "lemon:FormatError" << ": ";
   8.457 +        oss << _message;
   8.458 +        if (!_file.empty() || _line != 0) {
   8.459 +          oss << " (";
   8.460 +          if (!_file.empty()) oss << "in file '" << _file << "'";
   8.461 +          if (!_file.empty() && _line != 0) oss << " ";
   8.462 +          if (_line != 0) oss << "at line " << _line;
   8.463 +          oss << ")";
   8.464          }
   8.465 -        _message_holder.set(ostr.str());
   8.466 +        _what = oss.str();
   8.467        }
   8.468        catch (...) {}
   8.469 -      if( _message_holder.valid()) return _message_holder.get().c_str();
   8.470 -      return "lemon:DataFormatError";
   8.471 +      if (!_what.empty()) return _what.c_str();
   8.472 +      else return "lemon:FormatError";
   8.473      }
   8.474  
   8.475 -    virtual ~DataFormatError() throw() {}
   8.476 -  };
   8.477 -
   8.478 -  ///\e
   8.479 -  class FileOpenError : public IoError {
   8.480 -  protected:
   8.481 -    ExceptionMember<std::string> _file;
   8.482 -
   8.483 -    mutable ExceptionMember<std::string> _message_holder;
   8.484 -  public:
   8.485 -
   8.486 -    FileOpenError(const FileOpenError &foe) :
   8.487 -      IoError(foe), _file(foe._file) {}
   8.488 -
   8.489 -    ///\e
   8.490 -    explicit FileOpenError(const std::string& fl)
   8.491 -      : _file(fl) {}
   8.492 -
   8.493 -
   8.494 -    ///\e
   8.495 -    void file(const std::string &fl) { _file.set(fl); }
   8.496 -
   8.497 -    /// \brief Returns the filename.
   8.498 -    ///
   8.499 -    /// Returns \e null if the filename was not specified.
   8.500 -    const char* file() const {
   8.501 -      if (_file.valid() && !_file.get().empty()) {
   8.502 -        return _file.get().c_str();
   8.503 -      } else {
   8.504 -        return 0;
   8.505 -      }
   8.506 -    }
   8.507 -
   8.508 -    ///\e
   8.509 -    virtual const char* what() const throw() {
   8.510 -      try {
   8.511 -        std::ostringstream ostr;
   8.512 -        ostr << "lemon::FileOpenError" << ": ";
   8.513 -        ostr << "Cannot open file - " << file();
   8.514 -        _message_holder.set(ostr.str());
   8.515 -      }
   8.516 -      catch (...) {}
   8.517 -      if( _message_holder.valid()) return _message_holder.get().c_str();
   8.518 -      return "lemon::FileOpenError";
   8.519 -    }
   8.520 -    virtual ~FileOpenError() throw() {}
   8.521 -  };
   8.522 -
   8.523 -  class IoParameterError : public IoError {
   8.524 -  protected:
   8.525 -    ExceptionMember<std::string> _message;
   8.526 -    ExceptionMember<std::string> _file;
   8.527 -
   8.528 -    mutable ExceptionMember<std::string> _message_holder;
   8.529 -  public:
   8.530 -
   8.531 -    IoParameterError(const IoParameterError &ile) :
   8.532 -      IoError(ile), _message(ile._message), _file(ile._file) {}
   8.533 -
   8.534 -    ///\e
   8.535 -    explicit IoParameterError(const char *the_message)
   8.536 -      : _message(the_message) {}
   8.537 -
   8.538 -    ///\e
   8.539 -    IoParameterError(const char *file_name, const char *the_message)
   8.540 -      : _message(the_message), _file(file_name) {}
   8.541 -
   8.542 -     ///\e
   8.543 -    void message(const std::string& msg) { _message.set(msg); }
   8.544 -    ///\e
   8.545 -    void file(const std::string &fl) { _file.set(fl); }
   8.546 -
   8.547 -     ///\e
   8.548 -    const char* message() const {
   8.549 -      if (_message.valid()) {
   8.550 -        return _message.get().c_str();
   8.551 -      } else {
   8.552 -        return 0;
   8.553 -      }
   8.554 -    }
   8.555 -
   8.556 -    /// \brief Returns the filename.
   8.557 -    ///
   8.558 -    /// Returns \c 0 if the filename was not specified.
   8.559 -    const char* file() const {
   8.560 -      if (_file.valid()) {
   8.561 -        return _file.get().c_str();
   8.562 -      } else {
   8.563 -        return 0;
   8.564 -      }
   8.565 -    }
   8.566 -
   8.567 -    ///\e
   8.568 -    virtual const char* what() const throw() {
   8.569 -      try {
   8.570 -        std::ostringstream ostr;
   8.571 -        if (message()) ostr << message();
   8.572 -        if (file()) ostr << "(when reading file '" << file() << "')";
   8.573 -        _message_holder.set(ostr.str());
   8.574 -      }
   8.575 -      catch (...) {}
   8.576 -      if( _message_holder.valid() ) return _message_holder.get().c_str();
   8.577 -      return "lemon:IoParameterError";
   8.578 -    }
   8.579 -    virtual ~IoParameterError() throw() {}
   8.580    };
   8.581  
   8.582    /// @}
     9.1 --- a/lemon/graph_to_eps.h	Wed Oct 01 12:44:16 2008 +0200
     9.2 +++ b/lemon/graph_to_eps.h	Wed Oct 01 13:56:40 2008 +0200
     9.3 @@ -40,6 +40,7 @@
     9.4  #include<lemon/maps.h>
     9.5  #include<lemon/color.h>
     9.6  #include<lemon/bits/bezier.h>
     9.7 +#include<lemon/error.h>
     9.8  
     9.9  
    9.10  ///\ingroup eps_io
    9.11 @@ -1166,8 +1167,13 @@
    9.12  GraphToEps<DefaultGraphToEpsTraits<G> >
    9.13  graphToEps(G &g,const char *file_name)
    9.14  {
    9.15 +  std::ostream* os = new std::ofstream(file_name);
    9.16 +  if (!(*os)) {
    9.17 +    delete os;
    9.18 +    throw IoError("Cannot write file", file_name);
    9.19 +  }
    9.20    return GraphToEps<DefaultGraphToEpsTraits<G> >
    9.21 -    (DefaultGraphToEpsTraits<G>(g,*new std::ofstream(file_name),true));
    9.22 +    (DefaultGraphToEpsTraits<G>(g,*os,true));
    9.23  }
    9.24  
    9.25  ///Generates an EPS file from a graph
    9.26 @@ -1182,8 +1188,13 @@
    9.27  GraphToEps<DefaultGraphToEpsTraits<G> >
    9.28  graphToEps(G &g,const std::string& file_name)
    9.29  {
    9.30 +  std::ostream* os = new std::ofstream(file_name.c_str());
    9.31 +  if (!(*os)) {
    9.32 +    delete os;
    9.33 +    throw IoError("Cannot write file", file_name);
    9.34 +  }
    9.35    return GraphToEps<DefaultGraphToEpsTraits<G> >
    9.36 -    (DefaultGraphToEpsTraits<G>(g,*new std::ofstream(file_name.c_str()),true));
    9.37 +    (DefaultGraphToEpsTraits<G>(g,*os,true));
    9.38  }
    9.39  
    9.40  } //END OF NAMESPACE LEMON
    10.1 --- a/lemon/lgf_reader.h	Wed Oct 01 12:44:16 2008 +0200
    10.2 +++ b/lemon/lgf_reader.h	Wed Oct 01 13:56:40 2008 +0200
    10.3 @@ -48,11 +48,13 @@
    10.4        Value operator()(const std::string& str) {
    10.5          std::istringstream is(str);
    10.6          Value value;
    10.7 -        is >> value;
    10.8 +        if (!(is >> value)) {
    10.9 +          throw FormatError("Cannot read token");
   10.10 +        }
   10.11  
   10.12          char c;
   10.13          if (is >> std::ws >> c) {
   10.14 -          throw DataFormatError("Remaining characters in token");
   10.15 +          throw FormatError("Remaining characters in token");
   10.16          }
   10.17          return value;
   10.18        }
   10.19 @@ -166,7 +168,7 @@
   10.20          if (it == _map.end()) {
   10.21            std::ostringstream msg;
   10.22            msg << "Item not found: " << str;
   10.23 -          throw DataFormatError(msg.str().c_str());
   10.24 +          throw FormatError(msg.str());
   10.25          }
   10.26          return it->second;
   10.27        }
   10.28 @@ -184,12 +186,12 @@
   10.29  
   10.30        typename Graph::Arc operator()(const std::string& str) {
   10.31          if (str.empty() || (str[0] != '+' && str[0] != '-')) {
   10.32 -          throw DataFormatError("Item must start with '+' or '-'");
   10.33 +          throw FormatError("Item must start with '+' or '-'");
   10.34          }
   10.35          typename std::map<std::string, typename Graph::Edge>
   10.36            ::const_iterator it = _map.find(str.substr(1));
   10.37          if (it == _map.end()) {
   10.38 -          throw DataFormatError("Item not found");
   10.39 +          throw FormatError("Item not found");
   10.40          }
   10.41          return _graph.direct(it->second, str[0] == '+');
   10.42        }
   10.43 @@ -235,7 +237,7 @@
   10.44      inline char readEscape(std::istream& is) {
   10.45        char c;
   10.46        if (!is.get(c))
   10.47 -        throw DataFormatError("Escape format error");
   10.48 +        throw FormatError("Escape format error");
   10.49  
   10.50        switch (c) {
   10.51        case '\\':
   10.52 @@ -264,7 +266,7 @@
   10.53          {
   10.54            int code;
   10.55            if (!is.get(c) || !isHex(c))
   10.56 -            throw DataFormatError("Escape format error");
   10.57 +            throw FormatError("Escape format error");
   10.58            else if (code = valueHex(c), !is.get(c) || !isHex(c)) is.putback(c);
   10.59            else code = code * 16 + valueHex(c);
   10.60            return code;
   10.61 @@ -273,7 +275,7 @@
   10.62          {
   10.63            int code;
   10.64            if (!isOct(c))
   10.65 -            throw DataFormatError("Escape format error");
   10.66 +            throw FormatError("Escape format error");
   10.67            else if (code = valueOct(c), !is.get(c) || !isOct(c))
   10.68              is.putback(c);
   10.69            else if (code = code * 8 + valueOct(c), !is.get(c) || !isOct(c))
   10.70 @@ -300,7 +302,7 @@
   10.71            os << c;
   10.72          }
   10.73          if (!is)
   10.74 -          throw DataFormatError("Quoted format error");
   10.75 +          throw FormatError("Quoted format error");
   10.76        } else {
   10.77          is.putback(c);
   10.78          while (is.get(c) && !isWhiteSpace(c)) {
   10.79 @@ -461,6 +463,7 @@
   10.80  
   10.81      std::istream* _is;
   10.82      bool local_is;
   10.83 +    std::string _filename;
   10.84  
   10.85      Digraph& _digraph;
   10.86  
   10.87 @@ -510,18 +513,24 @@
   10.88      /// Construct a directed graph reader, which reads from the given
   10.89      /// file.
   10.90      DigraphReader(Digraph& digraph, const std::string& fn)
   10.91 -      : _is(new std::ifstream(fn.c_str())), local_is(true), _digraph(digraph),
   10.92 +      : _is(new std::ifstream(fn.c_str())), local_is(true),
   10.93 +        _filename(fn), _digraph(digraph),
   10.94          _use_nodes(false), _use_arcs(false),
   10.95 -        _skip_nodes(false), _skip_arcs(false) {}
   10.96 +        _skip_nodes(false), _skip_arcs(false) {
   10.97 +      if (!(*_is)) throw IoError("Cannot open file", fn);
   10.98 +    }
   10.99  
  10.100      /// \brief Constructor
  10.101      ///
  10.102      /// Construct a directed graph reader, which reads from the given
  10.103      /// file.
  10.104      DigraphReader(Digraph& digraph, const char* fn)
  10.105 -      : _is(new std::ifstream(fn)), local_is(true), _digraph(digraph),
  10.106 +      : _is(new std::ifstream(fn)), local_is(true),
  10.107 +        _filename(fn), _digraph(digraph),
  10.108          _use_nodes(false), _use_arcs(false),
  10.109 -        _skip_nodes(false), _skip_arcs(false) {}
  10.110 +        _skip_nodes(false), _skip_arcs(false) {
  10.111 +      if (!(*_is)) throw IoError("Cannot open file", fn);
  10.112 +    }
  10.113  
  10.114      /// \brief Destructor
  10.115      ~DigraphReader() {
  10.116 @@ -846,7 +855,7 @@
  10.117        if (!readLine() || !(line >> c) || c == '@') {
  10.118          if (readSuccess() && line) line.putback(c);
  10.119          if (!_node_maps.empty())
  10.120 -          throw DataFormatError("Cannot find map names");
  10.121 +          throw FormatError("Cannot find map names");
  10.122          return;
  10.123        }
  10.124        line.putback(c);
  10.125 @@ -860,7 +869,7 @@
  10.126            if (maps.find(map) != maps.end()) {
  10.127              std::ostringstream msg;
  10.128              msg << "Multiple occurence of node map: " << map;
  10.129 -            throw DataFormatError(msg.str().c_str());
  10.130 +            throw FormatError(msg.str());
  10.131            }
  10.132            maps.insert(std::make_pair(map, index));
  10.133            ++index;
  10.134 @@ -871,8 +880,8 @@
  10.135              maps.find(_node_maps[i].first);
  10.136            if (jt == maps.end()) {
  10.137              std::ostringstream msg;
  10.138 -            msg << "Map not found in file: " << _node_maps[i].first;
  10.139 -            throw DataFormatError(msg.str().c_str());
  10.140 +            msg << "Map not found: " << _node_maps[i].first;
  10.141 +            throw FormatError(msg.str());
  10.142            }
  10.143            map_index[i] = jt->second;
  10.144          }
  10.145 @@ -896,11 +905,11 @@
  10.146            if (!_reader_bits::readToken(line, tokens[i])) {
  10.147              std::ostringstream msg;
  10.148              msg << "Column not found (" << i + 1 << ")";
  10.149 -            throw DataFormatError(msg.str().c_str());
  10.150 +            throw FormatError(msg.str());
  10.151            }
  10.152          }
  10.153          if (line >> std::ws >> c)
  10.154 -          throw DataFormatError("Extra character on the end of line");
  10.155 +          throw FormatError("Extra character at the end of line");
  10.156  
  10.157          Node n;
  10.158          if (!_use_nodes) {
  10.159 @@ -909,13 +918,13 @@
  10.160              _node_index.insert(std::make_pair(tokens[label_index], n));
  10.161          } else {
  10.162            if (label_index == -1)
  10.163 -            throw DataFormatError("Label map not found in file");
  10.164 +            throw FormatError("Label map not found");
  10.165            typename std::map<std::string, Node>::iterator it =
  10.166              _node_index.find(tokens[label_index]);
  10.167            if (it == _node_index.end()) {
  10.168              std::ostringstream msg;
  10.169              msg << "Node with label not found: " << tokens[label_index];
  10.170 -            throw DataFormatError(msg.str().c_str());
  10.171 +            throw FormatError(msg.str());
  10.172            }
  10.173            n = it->second;
  10.174          }
  10.175 @@ -939,7 +948,7 @@
  10.176        if (!readLine() || !(line >> c) || c == '@') {
  10.177          if (readSuccess() && line) line.putback(c);
  10.178          if (!_arc_maps.empty())
  10.179 -          throw DataFormatError("Cannot find map names");
  10.180 +          throw FormatError("Cannot find map names");
  10.181          return;
  10.182        }
  10.183        line.putback(c);
  10.184 @@ -953,7 +962,7 @@
  10.185            if (maps.find(map) != maps.end()) {
  10.186              std::ostringstream msg;
  10.187              msg << "Multiple occurence of arc map: " << map;
  10.188 -            throw DataFormatError(msg.str().c_str());
  10.189 +            throw FormatError(msg.str());
  10.190            }
  10.191            maps.insert(std::make_pair(map, index));
  10.192            ++index;
  10.193 @@ -964,8 +973,8 @@
  10.194              maps.find(_arc_maps[i].first);
  10.195            if (jt == maps.end()) {
  10.196              std::ostringstream msg;
  10.197 -            msg << "Map not found in file: " << _arc_maps[i].first;
  10.198 -            throw DataFormatError(msg.str().c_str());
  10.199 +            msg << "Map not found: " << _arc_maps[i].first;
  10.200 +            throw FormatError(msg.str());
  10.201            }
  10.202            map_index[i] = jt->second;
  10.203          }
  10.204 @@ -988,21 +997,21 @@
  10.205          std::string target_token;
  10.206  
  10.207          if (!_reader_bits::readToken(line, source_token))
  10.208 -          throw DataFormatError("Source not found");
  10.209 +          throw FormatError("Source not found");
  10.210  
  10.211          if (!_reader_bits::readToken(line, target_token))
  10.212 -          throw DataFormatError("Target not found");
  10.213 +          throw FormatError("Target not found");
  10.214  
  10.215          std::vector<std::string> tokens(map_num);
  10.216          for (int i = 0; i < map_num; ++i) {
  10.217            if (!_reader_bits::readToken(line, tokens[i])) {
  10.218              std::ostringstream msg;
  10.219              msg << "Column not found (" << i + 1 << ")";
  10.220 -            throw DataFormatError(msg.str().c_str());
  10.221 +            throw FormatError(msg.str());
  10.222            }
  10.223          }
  10.224          if (line >> std::ws >> c)
  10.225 -          throw DataFormatError("Extra character on the end of line");
  10.226 +          throw FormatError("Extra character at the end of line");
  10.227  
  10.228          Arc a;
  10.229          if (!_use_arcs) {
  10.230 @@ -1013,7 +1022,7 @@
  10.231            if (it == _node_index.end()) {
  10.232              std::ostringstream msg;
  10.233              msg << "Item not found: " << source_token;
  10.234 -            throw DataFormatError(msg.str().c_str());
  10.235 +            throw FormatError(msg.str());
  10.236            }
  10.237            Node source = it->second;
  10.238  
  10.239 @@ -1021,7 +1030,7 @@
  10.240            if (it == _node_index.end()) {
  10.241              std::ostringstream msg;
  10.242              msg << "Item not found: " << target_token;
  10.243 -            throw DataFormatError(msg.str().c_str());
  10.244 +            throw FormatError(msg.str());
  10.245            }
  10.246            Node target = it->second;
  10.247  
  10.248 @@ -1030,13 +1039,13 @@
  10.249              _arc_index.insert(std::make_pair(tokens[label_index], a));
  10.250          } else {
  10.251            if (label_index == -1)
  10.252 -            throw DataFormatError("Label map not found in file");
  10.253 +            throw FormatError("Label map not found");
  10.254            typename std::map<std::string, Arc>::iterator it =
  10.255              _arc_index.find(tokens[label_index]);
  10.256            if (it == _arc_index.end()) {
  10.257              std::ostringstream msg;
  10.258              msg << "Arc with label not found: " << tokens[label_index];
  10.259 -            throw DataFormatError(msg.str().c_str());
  10.260 +            throw FormatError(msg.str());
  10.261            }
  10.262            a = it->second;
  10.263          }
  10.264 @@ -1061,18 +1070,18 @@
  10.265  
  10.266          std::string attr, token;
  10.267          if (!_reader_bits::readToken(line, attr))
  10.268 -          throw DataFormatError("Attribute name not found");
  10.269 +          throw FormatError("Attribute name not found");
  10.270          if (!_reader_bits::readToken(line, token))
  10.271 -          throw DataFormatError("Attribute value not found");
  10.272 +          throw FormatError("Attribute value not found");
  10.273          if (line >> c)
  10.274 -          throw DataFormatError("Extra character on the end of line");
  10.275 +          throw FormatError("Extra character at the end of line");
  10.276  
  10.277          {
  10.278            std::set<std::string>::iterator it = read_attr.find(attr);
  10.279            if (it != read_attr.end()) {
  10.280              std::ostringstream msg;
  10.281 -            msg << "Multiple occurence of attribute " << attr;
  10.282 -            throw DataFormatError(msg.str().c_str());
  10.283 +            msg << "Multiple occurence of attribute: " << attr;
  10.284 +            throw FormatError(msg.str());
  10.285            }
  10.286            read_attr.insert(attr);
  10.287          }
  10.288 @@ -1093,8 +1102,8 @@
  10.289             it != _attributes.end(); ++it) {
  10.290          if (read_attr.find(it->first) == read_attr.end()) {
  10.291            std::ostringstream msg;
  10.292 -          msg << "Attribute not found in file: " << it->first;
  10.293 -          throw DataFormatError(msg.str().c_str());
  10.294 +          msg << "Attribute not found: " << it->first;
  10.295 +          throw FormatError(msg.str());
  10.296          }
  10.297        }
  10.298      }
  10.299 @@ -1109,9 +1118,6 @@
  10.300      /// This function starts the batch processing
  10.301      void run() {
  10.302        LEMON_ASSERT(_is != 0, "This reader assigned to an other reader");
  10.303 -      if (!*_is) {
  10.304 -        throw DataFormatError("Cannot find file");
  10.305 -      }
  10.306  
  10.307        bool nodes_done = _skip_nodes;
  10.308        bool arcs_done = _skip_arcs;
  10.309 @@ -1130,7 +1136,7 @@
  10.310            _reader_bits::readToken(line, caption);
  10.311  
  10.312            if (line >> c)
  10.313 -            throw DataFormatError("Extra character on the end of line");
  10.314 +            throw FormatError("Extra character at the end of line");
  10.315  
  10.316            if (section == "nodes" && !nodes_done) {
  10.317              if (_nodes_caption.empty() || _nodes_caption == caption) {
  10.318 @@ -1152,22 +1158,23 @@
  10.319              readLine();
  10.320              skipSection();
  10.321            }
  10.322 -        } catch (DataFormatError& error) {
  10.323 +        } catch (FormatError& error) {
  10.324            error.line(line_num);
  10.325 +          error.file(_filename);
  10.326            throw;
  10.327          }
  10.328        }
  10.329  
  10.330        if (!nodes_done) {
  10.331 -        throw DataFormatError("Section @nodes not found");
  10.332 +        throw FormatError("Section @nodes not found");
  10.333        }
  10.334  
  10.335        if (!arcs_done) {
  10.336 -        throw DataFormatError("Section @arcs not found");
  10.337 +        throw FormatError("Section @arcs not found");
  10.338        }
  10.339  
  10.340        if (!attributes_done && !_attributes.empty()) {
  10.341 -        throw DataFormatError("Section @attributes not found");
  10.342 +        throw FormatError("Section @attributes not found");
  10.343        }
  10.344  
  10.345      }
  10.346 @@ -1247,6 +1254,7 @@
  10.347  
  10.348      std::istream* _is;
  10.349      bool local_is;
  10.350 +    std::string _filename;
  10.351  
  10.352      Graph& _graph;
  10.353  
  10.354 @@ -1296,18 +1304,24 @@
  10.355      /// Construct an undirected graph reader, which reads from the given
  10.356      /// file.
  10.357      GraphReader(Graph& graph, const std::string& fn)
  10.358 -      : _is(new std::ifstream(fn.c_str())), local_is(true), _graph(graph),
  10.359 +      : _is(new std::ifstream(fn.c_str())), local_is(true),
  10.360 +        _filename(fn), _graph(graph),
  10.361          _use_nodes(false), _use_edges(false),
  10.362 -        _skip_nodes(false), _skip_edges(false) {}
  10.363 +        _skip_nodes(false), _skip_edges(false) {
  10.364 +      if (!(*_is)) throw IoError("Cannot open file", fn);
  10.365 +    }
  10.366  
  10.367      /// \brief Constructor
  10.368      ///
  10.369      /// Construct an undirected graph reader, which reads from the given
  10.370      /// file.
  10.371      GraphReader(Graph& graph, const char* fn)
  10.372 -      : _is(new std::ifstream(fn)), local_is(true), _graph(graph),
  10.373 +      : _is(new std::ifstream(fn)), local_is(true),
  10.374 +        _filename(fn), _graph(graph),
  10.375          _use_nodes(false), _use_edges(false),
  10.376 -        _skip_nodes(false), _skip_edges(false) {}
  10.377 +        _skip_nodes(false), _skip_edges(false) {
  10.378 +      if (!(*_is)) throw IoError("Cannot open file", fn);
  10.379 +    }
  10.380  
  10.381      /// \brief Destructor
  10.382      ~GraphReader() {
  10.383 @@ -1676,7 +1690,7 @@
  10.384        if (!readLine() || !(line >> c) || c == '@') {
  10.385          if (readSuccess() && line) line.putback(c);
  10.386          if (!_node_maps.empty())
  10.387 -          throw DataFormatError("Cannot find map names");
  10.388 +          throw FormatError("Cannot find map names");
  10.389          return;
  10.390        }
  10.391        line.putback(c);
  10.392 @@ -1690,7 +1704,7 @@
  10.393            if (maps.find(map) != maps.end()) {
  10.394              std::ostringstream msg;
  10.395              msg << "Multiple occurence of node map: " << map;
  10.396 -            throw DataFormatError(msg.str().c_str());
  10.397 +            throw FormatError(msg.str());
  10.398            }
  10.399            maps.insert(std::make_pair(map, index));
  10.400            ++index;
  10.401 @@ -1701,8 +1715,8 @@
  10.402              maps.find(_node_maps[i].first);
  10.403            if (jt == maps.end()) {
  10.404              std::ostringstream msg;
  10.405 -            msg << "Map not found in file: " << _node_maps[i].first;
  10.406 -            throw DataFormatError(msg.str().c_str());
  10.407 +            msg << "Map not found: " << _node_maps[i].first;
  10.408 +            throw FormatError(msg.str());
  10.409            }
  10.410            map_index[i] = jt->second;
  10.411          }
  10.412 @@ -1726,11 +1740,11 @@
  10.413            if (!_reader_bits::readToken(line, tokens[i])) {
  10.414              std::ostringstream msg;
  10.415              msg << "Column not found (" << i + 1 << ")";
  10.416 -            throw DataFormatError(msg.str().c_str());
  10.417 +            throw FormatError(msg.str());
  10.418            }
  10.419          }
  10.420          if (line >> std::ws >> c)
  10.421 -          throw DataFormatError("Extra character on the end of line");
  10.422 +          throw FormatError("Extra character at the end of line");
  10.423  
  10.424          Node n;
  10.425          if (!_use_nodes) {
  10.426 @@ -1739,13 +1753,13 @@
  10.427              _node_index.insert(std::make_pair(tokens[label_index], n));
  10.428          } else {
  10.429            if (label_index == -1)
  10.430 -            throw DataFormatError("Label map not found in file");
  10.431 +            throw FormatError("Label map not found");
  10.432            typename std::map<std::string, Node>::iterator it =
  10.433              _node_index.find(tokens[label_index]);
  10.434            if (it == _node_index.end()) {
  10.435              std::ostringstream msg;
  10.436              msg << "Node with label not found: " << tokens[label_index];
  10.437 -            throw DataFormatError(msg.str().c_str());
  10.438 +            throw FormatError(msg.str());
  10.439            }
  10.440            n = it->second;
  10.441          }
  10.442 @@ -1769,7 +1783,7 @@
  10.443        if (!readLine() || !(line >> c) || c == '@') {
  10.444          if (readSuccess() && line) line.putback(c);
  10.445          if (!_edge_maps.empty())
  10.446 -          throw DataFormatError("Cannot find map names");
  10.447 +          throw FormatError("Cannot find map names");
  10.448          return;
  10.449        }
  10.450        line.putback(c);
  10.451 @@ -1783,7 +1797,7 @@
  10.452            if (maps.find(map) != maps.end()) {
  10.453              std::ostringstream msg;
  10.454              msg << "Multiple occurence of edge map: " << map;
  10.455 -            throw DataFormatError(msg.str().c_str());
  10.456 +            throw FormatError(msg.str());
  10.457            }
  10.458            maps.insert(std::make_pair(map, index));
  10.459            ++index;
  10.460 @@ -1794,8 +1808,8 @@
  10.461              maps.find(_edge_maps[i].first);
  10.462            if (jt == maps.end()) {
  10.463              std::ostringstream msg;
  10.464 -            msg << "Map not found in file: " << _edge_maps[i].first;
  10.465 -            throw DataFormatError(msg.str().c_str());
  10.466 +            msg << "Map not found: " << _edge_maps[i].first;
  10.467 +            throw FormatError(msg.str());
  10.468            }
  10.469            map_index[i] = jt->second;
  10.470          }
  10.471 @@ -1818,21 +1832,21 @@
  10.472          std::string target_token;
  10.473  
  10.474          if (!_reader_bits::readToken(line, source_token))
  10.475 -          throw DataFormatError("Node u not found");
  10.476 +          throw FormatError("Node u not found");
  10.477  
  10.478          if (!_reader_bits::readToken(line, target_token))
  10.479 -          throw DataFormatError("Node v not found");
  10.480 +          throw FormatError("Node v not found");
  10.481  
  10.482          std::vector<std::string> tokens(map_num);
  10.483          for (int i = 0; i < map_num; ++i) {
  10.484            if (!_reader_bits::readToken(line, tokens[i])) {
  10.485              std::ostringstream msg;
  10.486              msg << "Column not found (" << i + 1 << ")";
  10.487 -            throw DataFormatError(msg.str().c_str());
  10.488 +            throw FormatError(msg.str());
  10.489            }
  10.490          }
  10.491          if (line >> std::ws >> c)
  10.492 -          throw DataFormatError("Extra character on the end of line");
  10.493 +          throw FormatError("Extra character at the end of line");
  10.494  
  10.495          Edge e;
  10.496          if (!_use_edges) {
  10.497 @@ -1843,7 +1857,7 @@
  10.498            if (it == _node_index.end()) {
  10.499              std::ostringstream msg;
  10.500              msg << "Item not found: " << source_token;
  10.501 -            throw DataFormatError(msg.str().c_str());
  10.502 +            throw FormatError(msg.str());
  10.503            }
  10.504            Node source = it->second;
  10.505  
  10.506 @@ -1851,7 +1865,7 @@
  10.507            if (it == _node_index.end()) {
  10.508              std::ostringstream msg;
  10.509              msg << "Item not found: " << target_token;
  10.510 -            throw DataFormatError(msg.str().c_str());
  10.511 +            throw FormatError(msg.str());
  10.512            }
  10.513            Node target = it->second;
  10.514  
  10.515 @@ -1860,13 +1874,13 @@
  10.516              _edge_index.insert(std::make_pair(tokens[label_index], e));
  10.517          } else {
  10.518            if (label_index == -1)
  10.519 -            throw DataFormatError("Label map not found in file");
  10.520 +            throw FormatError("Label map not found");
  10.521            typename std::map<std::string, Edge>::iterator it =
  10.522              _edge_index.find(tokens[label_index]);
  10.523            if (it == _edge_index.end()) {
  10.524              std::ostringstream msg;
  10.525              msg << "Edge with label not found: " << tokens[label_index];
  10.526 -            throw DataFormatError(msg.str().c_str());
  10.527 +            throw FormatError(msg.str());
  10.528            }
  10.529            e = it->second;
  10.530          }
  10.531 @@ -1891,18 +1905,18 @@
  10.532  
  10.533          std::string attr, token;
  10.534          if (!_reader_bits::readToken(line, attr))
  10.535 -          throw DataFormatError("Attribute name not found");
  10.536 +          throw FormatError("Attribute name not found");
  10.537          if (!_reader_bits::readToken(line, token))
  10.538 -          throw DataFormatError("Attribute value not found");
  10.539 +          throw FormatError("Attribute value not found");
  10.540          if (line >> c)
  10.541 -          throw DataFormatError("Extra character on the end of line");
  10.542 +          throw FormatError("Extra character at the end of line");
  10.543  
  10.544          {
  10.545            std::set<std::string>::iterator it = read_attr.find(attr);
  10.546            if (it != read_attr.end()) {
  10.547              std::ostringstream msg;
  10.548 -            msg << "Multiple occurence of attribute " << attr;
  10.549 -            throw DataFormatError(msg.str().c_str());
  10.550 +            msg << "Multiple occurence of attribute: " << attr;
  10.551 +            throw FormatError(msg.str());
  10.552            }
  10.553            read_attr.insert(attr);
  10.554          }
  10.555 @@ -1923,8 +1937,8 @@
  10.556             it != _attributes.end(); ++it) {
  10.557          if (read_attr.find(it->first) == read_attr.end()) {
  10.558            std::ostringstream msg;
  10.559 -          msg << "Attribute not found in file: " << it->first;
  10.560 -          throw DataFormatError(msg.str().c_str());
  10.561 +          msg << "Attribute not found: " << it->first;
  10.562 +          throw FormatError(msg.str());
  10.563          }
  10.564        }
  10.565      }
  10.566 @@ -1958,7 +1972,7 @@
  10.567            _reader_bits::readToken(line, caption);
  10.568  
  10.569            if (line >> c)
  10.570 -            throw DataFormatError("Extra character on the end of line");
  10.571 +            throw FormatError("Extra character at the end of line");
  10.572  
  10.573            if (section == "nodes" && !nodes_done) {
  10.574              if (_nodes_caption.empty() || _nodes_caption == caption) {
  10.575 @@ -1980,22 +1994,23 @@
  10.576              readLine();
  10.577              skipSection();
  10.578            }
  10.579 -        } catch (DataFormatError& error) {
  10.580 +        } catch (FormatError& error) {
  10.581            error.line(line_num);
  10.582 +          error.file(_filename);
  10.583            throw;
  10.584          }
  10.585        }
  10.586  
  10.587        if (!nodes_done) {
  10.588 -        throw DataFormatError("Section @nodes not found");
  10.589 +        throw FormatError("Section @nodes not found");
  10.590        }
  10.591  
  10.592        if (!edges_done) {
  10.593 -        throw DataFormatError("Section @edges not found");
  10.594 +        throw FormatError("Section @edges not found");
  10.595        }
  10.596  
  10.597        if (!attributes_done && !_attributes.empty()) {
  10.598 -        throw DataFormatError("Section @attributes not found");
  10.599 +        throw FormatError("Section @attributes not found");
  10.600        }
  10.601  
  10.602      }
  10.603 @@ -2056,6 +2071,7 @@
  10.604  
  10.605      std::istream* _is;
  10.606      bool local_is;
  10.607 +    std::string _filename;
  10.608  
  10.609      typedef std::map<std::string, _reader_bits::Section*> Sections;
  10.610      Sections _sections;
  10.611 @@ -2076,13 +2092,19 @@
  10.612      ///
  10.613      /// Construct a section reader, which reads from the given file.
  10.614      SectionReader(const std::string& fn)
  10.615 -      : _is(new std::ifstream(fn.c_str())), local_is(true) {}
  10.616 +      : _is(new std::ifstream(fn.c_str())), local_is(true),
  10.617 +        _filename(fn) {
  10.618 +      if (!(*_is)) throw IoError("Cannot open file", fn);
  10.619 +    }
  10.620  
  10.621      /// \brief Constructor
  10.622      ///
  10.623      /// Construct a section reader, which reads from the given file.
  10.624      SectionReader(const char* fn)
  10.625 -      : _is(new std::ifstream(fn)), local_is(true) {}
  10.626 +      : _is(new std::ifstream(fn)), local_is(true),
  10.627 +        _filename(fn) {
  10.628 +      if (!(*_is)) throw IoError("Cannot open file", fn);
  10.629 +    }
  10.630  
  10.631      /// \brief Destructor
  10.632      ~SectionReader() {
  10.633 @@ -2238,12 +2260,12 @@
  10.634            _reader_bits::readToken(line, caption);
  10.635  
  10.636            if (line >> c)
  10.637 -            throw DataFormatError("Extra character on the end of line");
  10.638 +            throw FormatError("Extra character at the end of line");
  10.639  
  10.640            if (extra_sections.find(section) != extra_sections.end()) {
  10.641              std::ostringstream msg;
  10.642 -            msg << "Multiple occurence of section " << section;
  10.643 -            throw DataFormatError(msg.str().c_str());
  10.644 +            msg << "Multiple occurence of section: " << section;
  10.645 +            throw FormatError(msg.str());
  10.646            }
  10.647            Sections::iterator it = _sections.find(section);
  10.648            if (it != _sections.end()) {
  10.649 @@ -2252,8 +2274,9 @@
  10.650            }
  10.651            readLine();
  10.652            skipSection();
  10.653 -        } catch (DataFormatError& error) {
  10.654 +        } catch (FormatError& error) {
  10.655            error.line(line_num);
  10.656 +          error.file(_filename);
  10.657            throw;
  10.658          }
  10.659        }
  10.660 @@ -2262,7 +2285,7 @@
  10.661          if (extra_sections.find(it->first) == extra_sections.end()) {
  10.662            std::ostringstream os;
  10.663            os << "Cannot find section: " << it->first;
  10.664 -          throw DataFormatError(os.str().c_str());
  10.665 +          throw FormatError(os.str());
  10.666          }
  10.667        }
  10.668      }
  10.669 @@ -2362,14 +2385,18 @@
  10.670      /// Construct an \e LGF contents reader, which reads from the given
  10.671      /// file.
  10.672      LgfContents(const std::string& fn)
  10.673 -      : _is(new std::ifstream(fn.c_str())), local_is(true) {}
  10.674 +      : _is(new std::ifstream(fn.c_str())), local_is(true) {
  10.675 +      if (!(*_is)) throw IoError("Cannot open file", fn);
  10.676 +    }
  10.677  
  10.678      /// \brief Constructor
  10.679      ///
  10.680      /// Construct an \e LGF contents reader, which reads from the given
  10.681      /// file.
  10.682      LgfContents(const char* fn)
  10.683 -      : _is(new std::ifstream(fn)), local_is(true) {}
  10.684 +      : _is(new std::ifstream(fn)), local_is(true) {
  10.685 +      if (!(*_is)) throw IoError("Cannot open file", fn);
  10.686 +    }
  10.687  
  10.688      /// \brief Destructor
  10.689      ~LgfContents() {
    11.1 --- a/lemon/lgf_writer.h	Wed Oct 01 12:44:16 2008 +0200
    11.2 +++ b/lemon/lgf_writer.h	Wed Oct 01 13:56:40 2008 +0200
    11.3 @@ -55,7 +55,7 @@
    11.4  
    11.5      template <typename T>
    11.6      bool operator<(const T&, const T&) {
    11.7 -      throw DataFormatError("Label map is not comparable");
    11.8 +      throw FormatError("Label map is not comparable");
    11.9      }
   11.10  
   11.11      template <typename _Map>
   11.12 @@ -203,7 +203,7 @@
   11.13          typename std::map<Value, std::string>::const_iterator it =
   11.14            _map.find(str);
   11.15          if (it == _map.end()) {
   11.16 -          throw DataFormatError("Item not found");
   11.17 +          throw FormatError("Item not found");
   11.18          }
   11.19          return it->second;
   11.20        }
   11.21 @@ -223,7 +223,7 @@
   11.22          typename std::map<typename Graph::Edge, std::string>
   11.23            ::const_iterator it = _map.find(val);
   11.24          if (it == _map.end()) {
   11.25 -          throw DataFormatError("Item not found");
   11.26 +          throw FormatError("Item not found");
   11.27          }
   11.28          return (_graph.direction(val) ? '+' : '-') + it->second;
   11.29        }
   11.30 @@ -462,7 +462,9 @@
   11.31      /// output file.
   11.32      DigraphWriter(const Digraph& digraph, const std::string& fn)
   11.33        : _os(new std::ofstream(fn.c_str())), local_os(true), _digraph(digraph),
   11.34 -        _skip_nodes(false), _skip_arcs(false) {}
   11.35 +        _skip_nodes(false), _skip_arcs(false) {
   11.36 +      if (!(*_os)) throw IoError("Cannot write file", fn);
   11.37 +    }
   11.38  
   11.39      /// \brief Constructor
   11.40      ///
   11.41 @@ -470,7 +472,9 @@
   11.42      /// output file.
   11.43      DigraphWriter(const Digraph& digraph, const char* fn)
   11.44        : _os(new std::ofstream(fn)), local_os(true), _digraph(digraph),
   11.45 -        _skip_nodes(false), _skip_arcs(false) {}
   11.46 +        _skip_nodes(false), _skip_arcs(false) {
   11.47 +      if (!(*_os)) throw IoError("Cannot write file", fn);
   11.48 +    }
   11.49  
   11.50      /// \brief Destructor
   11.51      ~DigraphWriter() {
   11.52 @@ -1019,7 +1023,9 @@
   11.53      /// output file.
   11.54      GraphWriter(const Graph& graph, const std::string& fn)
   11.55        : _os(new std::ofstream(fn.c_str())), local_os(true), _graph(graph),
   11.56 -        _skip_nodes(false), _skip_edges(false) {}
   11.57 +        _skip_nodes(false), _skip_edges(false) {
   11.58 +      if (!(*_os)) throw IoError("Cannot write file", fn);
   11.59 +    }
   11.60  
   11.61      /// \brief Constructor
   11.62      ///
   11.63 @@ -1027,7 +1033,9 @@
   11.64      /// output file.
   11.65      GraphWriter(const Graph& graph, const char* fn)
   11.66        : _os(new std::ofstream(fn)), local_os(true), _graph(graph),
   11.67 -        _skip_nodes(false), _skip_edges(false) {}
   11.68 +        _skip_nodes(false), _skip_edges(false) {
   11.69 +      if (!(*_os)) throw IoError("Cannot write file", fn);
   11.70 +    }
   11.71  
   11.72      /// \brief Destructor
   11.73      ~GraphWriter() {
   11.74 @@ -1578,13 +1586,17 @@
   11.75      ///
   11.76      /// Construct a section writer, which writes into the given file.
   11.77      SectionWriter(const std::string& fn)
   11.78 -      : _os(new std::ofstream(fn.c_str())), local_os(true) {}
   11.79 +      : _os(new std::ofstream(fn.c_str())), local_os(true) {
   11.80 +      if (!(*_os)) throw IoError("Cannot write file", fn);
   11.81 +    }
   11.82  
   11.83      /// \brief Constructor
   11.84      ///
   11.85      /// Construct a section writer, which writes into the given file.
   11.86      SectionWriter(const char* fn)
   11.87 -      : _os(new std::ofstream(fn)), local_os(true) {}
   11.88 +      : _os(new std::ofstream(fn)), local_os(true) {
   11.89 +      if (!(*_os)) throw IoError("Cannot write file", fn);
   11.90 +    }
   11.91  
   11.92      /// \brief Destructor
   11.93      ~SectionWriter() {