Changeset 173:b026e9779b28 in lemon-main
- Timestamp:
- 06/16/08 18:23:11 (16 years ago)
- Branch:
- default
- Phase:
- public
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
lemon/lgf_reader.h
r165 r173 2072 2072 return tmp; 2073 2073 } 2074 2075 /// \ingroup lemon_io 2076 /// 2077 /// \brief Reader for the content of the \ref lgf-format "LGF" file 2078 /// 2079 /// This class can be used to read the sections, the map names and 2080 /// the attributes from a file. Usually, the Lemon programs know 2081 /// that, which type of graph, which maps and which attributes 2082 /// should be read from a file, but in general tools (like glemon) 2083 /// the content of an LGF file should be guessed somehow. This class 2084 /// reads the graph and stores the appropriate information for 2085 /// reading the graph. 2086 /// 2087 ///\code LgfContent content("graph.lgf"); 2088 /// content.run(); 2089 /// 2090 /// // does it contain any node section and arc section 2091 /// if (content.nodeSectionNum() == 0 || content.arcSectionNum()) { 2092 /// std::cerr << "Failure, cannot find graph" << std::endl; 2093 /// return -1; 2094 /// } 2095 /// std::cout << "The name of the default node section : " 2096 /// << content.nodeSection(0) << std::endl; 2097 /// std::cout << "The number of the arc maps : " 2098 /// << content.arcMaps(0).size() << std::endl; 2099 /// std::cout << "The name of second arc map : " 2100 /// << content.arcMaps(0)[1] << std::endl; 2101 ///\endcode 2102 class LgfContent { 2103 private: 2104 2105 std::istream* _is; 2106 bool local_is; 2107 2108 std::vector<std::string> _node_sections; 2109 std::vector<std::string> _edge_sections; 2110 std::vector<std::string> _attribute_sections; 2111 std::vector<std::string> _extra_sections; 2112 2113 std::vector<bool> _arc_sections; 2114 2115 std::vector<std::vector<std::string> > _node_maps; 2116 std::vector<std::vector<std::string> > _edge_maps; 2117 2118 std::vector<std::vector<std::string> > _attributes; 2119 2120 2121 int line_num; 2122 std::istringstream line; 2123 2124 public: 2125 2126 /// \brief Constructor 2127 /// 2128 /// Construct an \e LGF content reader, which reads from the given 2129 /// input stream. 2130 LgfContent(std::istream& is) 2131 : _is(&is), local_is(false) {} 2132 2133 /// \brief Constructor 2134 /// 2135 /// Construct an \e LGF content reader, which reads from the given 2136 /// file. 2137 LgfContent(const std::string& fn) 2138 : _is(new std::ifstream(fn.c_str())), local_is(true) {} 2139 2140 /// \brief Constructor 2141 /// 2142 /// Construct an \e LGF content reader, which reads from the given 2143 /// file. 2144 LgfContent(const char* fn) 2145 : _is(new std::ifstream(fn)), local_is(true) {} 2146 2147 /// \brief Copy constructor 2148 /// 2149 /// The copy constructor transfers all data from the other reader, 2150 /// therefore the copied reader will not be usable more. 2151 LgfContent(LgfContent& other) 2152 : _is(other._is), local_is(other.local_is) { 2153 2154 other._is = 0; 2155 other.local_is = false; 2156 2157 _node_sections.swap(other._node_sections); 2158 _edge_sections.swap(other._edge_sections); 2159 _attribute_sections.swap(other._attribute_sections); 2160 _extra_sections.swap(other._extra_sections); 2161 2162 _arc_sections.swap(other._arc_sections); 2163 2164 _node_maps.swap(other._node_maps); 2165 _edge_maps.swap(other._edge_maps); 2166 _attributes.swap(other._attributes); 2167 } 2168 2169 /// \brief Destructor 2170 ~LgfContent() { 2171 if (local_is) delete _is; 2172 } 2173 2174 2175 /// \name Node sections 2176 /// @{ 2177 2178 /// \brief Gives back the number of node sections in the file. 2179 /// 2180 /// Gives back the number of node sections in the file. 2181 int nodeSectionNum() const { 2182 return _node_sections.size(); 2183 } 2184 2185 /// \brief Returns the section name at the given position. 2186 /// 2187 /// Returns the section name at the given position. 2188 const std::string& nodeSection(int i) const { 2189 return _node_sections[i]; 2190 } 2191 2192 /// \brief Gives back the node maps for the given section. 2193 /// 2194 /// Gives back the node maps for the given section. 2195 const std::vector<std::string>& nodeMaps(int i) const { 2196 return _node_maps[i]; 2197 } 2198 2199 /// @} 2200 2201 /// \name Arc sections 2202 /// @{ 2203 2204 /// \brief Gives back the number of arc sections in the file. 2205 /// 2206 /// Gives back the number of arc sections in the file. 2207 /// \note It is synonim of \c edgeSectionNum(). 2208 int arcSectionNum() const { 2209 return _edge_sections.size(); 2210 } 2211 2212 /// \brief Returns the section name at the given position. 2213 /// 2214 /// Returns the section name at the given position. 2215 /// \note It is synonim of \c edgeSection(). 2216 const std::string& arcSection(int i) const { 2217 return _edge_sections[i]; 2218 } 2219 2220 /// \brief Gives back the arc maps for the given section. 2221 /// 2222 /// Gives back the arc maps for the given section. 2223 /// \note It is synonim of \c edgeMaps(). 2224 const std::vector<std::string>& arcMaps(int i) const { 2225 return _edge_maps[i]; 2226 } 2227 2228 /// \brief Returns true when the section type is \c "@arcs". 2229 /// 2230 /// Returns true when the section type is \c "@arcs", and not "@edges". 2231 bool isArcSection(int i) const { 2232 return _arc_sections[i]; 2233 } 2234 2235 /// @} 2236 2237 /// \name Edge sections 2238 /// @{ 2239 2240 /// \brief Gives back the number of edge sections in the file. 2241 /// 2242 /// Gives back the number of edge sections in the file. 2243 int edgeSectionNum() const { 2244 return _edge_sections.size(); 2245 } 2246 2247 /// \brief Returns the section name at the given position. 2248 /// 2249 /// Returns the section name at the given position. 2250 const std::string& edgeSection(int i) const { 2251 return _edge_sections[i]; 2252 } 2253 2254 /// \brief Gives back the edge maps for the given section. 2255 /// 2256 /// Gives back the edge maps for the given section. 2257 const std::vector<std::string>& edgeMaps(int i) const { 2258 return _edge_maps[i]; 2259 } 2260 2261 /// \brief Returns true when the section type is \c "@edges". 2262 /// 2263 /// Returns true when the section type is \c "@edges", and not "@arcs". 2264 bool isEdgeSection(int i) const { 2265 return !_arc_sections[i]; 2266 } 2267 2268 /// @} 2269 2270 /// \name Attribute sections 2271 /// @{ 2272 2273 /// \brief Gives back the number of attribute sections in the file. 2274 /// 2275 /// Gives back the number of attribute sections in the file. 2276 int attributeSectionNum() const { 2277 return _attribute_sections.size(); 2278 } 2279 2280 /// \brief Returns the section name at the given position. 2281 /// 2282 /// Returns the section name at the given position. 2283 const std::string& attributeSection(int i) const { 2284 return _attribute_sections[i]; 2285 } 2286 2287 /// \brief Gives back the attributes for the given section. 2288 /// 2289 /// Gives back the attributes for the given section. 2290 const std::vector<std::string>& attributes(int i) const { 2291 return _attributes[i]; 2292 } 2293 2294 /// @} 2295 2296 /// \name Extra sections 2297 /// @{ 2298 2299 /// \brief Gives back the number of extra sections in the file. 2300 /// 2301 /// Gives back the number of extra sections in the file. 2302 int extraSectionNum() const { 2303 return _extra_sections.size(); 2304 } 2305 2306 /// \brief Returns the extra section type at the given position. 2307 /// 2308 /// Returns the section type at the given position. 2309 const std::string& extraSection(int i) const { 2310 return _extra_sections[i]; 2311 } 2312 2313 /// @} 2314 2315 private: 2316 2317 bool readLine() { 2318 std::string str; 2319 while(++line_num, std::getline(*_is, str)) { 2320 line.clear(); line.str(str); 2321 char c; 2322 if (line >> std::ws >> c && c != '#') { 2323 line.putback(c); 2324 return true; 2325 } 2326 } 2327 return false; 2328 } 2329 2330 bool readSuccess() { 2331 return static_cast<bool>(*_is); 2332 } 2333 2334 void skipSection() { 2335 char c; 2336 while (readSuccess() && line >> c && c != '@') { 2337 readLine(); 2338 } 2339 line.putback(c); 2340 } 2341 2342 void readMaps(std::vector<std::string>& maps) { 2343 if (!readLine()) 2344 throw DataFormatError("Cannot find map captions"); 2345 std::string map; 2346 while (_reader_bits::readToken(line, map)) { 2347 maps.push_back(map); 2348 } 2349 } 2350 2351 void readAttributes(std::vector<std::string>& attrs) { 2352 readLine(); 2353 char c; 2354 while (readSuccess() && line >> c && c != '@') { 2355 line.putback(c); 2356 std::string attr; 2357 _reader_bits::readToken(line, attr); 2358 attrs.push_back(attr); 2359 readLine(); 2360 } 2361 line.putback(c); 2362 } 2363 2364 public: 2365 2366 /// \name Execution of the content reader 2367 /// @{ 2368 2369 /// \brief Start the reading 2370 /// 2371 /// This function starts the reading 2372 void run() { 2373 2374 readLine(); 2375 skipSection(); 2376 2377 while (readSuccess()) { 2378 2379 char c; 2380 line >> c; 2381 2382 std::string section, caption; 2383 _reader_bits::readToken(line, section); 2384 _reader_bits::readToken(line, caption); 2385 2386 if (section == "nodes") { 2387 _node_sections.push_back(caption); 2388 _node_maps.push_back(std::vector<std::string>()); 2389 readMaps(_node_maps.back()); 2390 readLine(); skipSection(); 2391 } else if (section == "arcs" || section == "edges") { 2392 _edge_sections.push_back(caption); 2393 _arc_sections.push_back(section == "arcs"); 2394 _edge_maps.push_back(std::vector<std::string>()); 2395 readMaps(_edge_maps.back()); 2396 readLine(); skipSection(); 2397 } else if (section == "attributes") { 2398 _attribute_sections.push_back(caption); 2399 _attributes.push_back(std::vector<std::string>()); 2400 readAttributes(_attributes.back()); 2401 } else { 2402 _extra_sections.push_back(section); 2403 readLine(); skipSection(); 2404 } 2405 } 2406 } 2407 2408 /// @} 2409 2410 }; 2074 2411 } 2075 2412
Note: See TracChangeset
for help on using the changeset viewer.