SUMO - Simulation of Urban MObility

NIImporter_DlrNavteq.cpp

Go to the documentation of this file.
00001 /****************************************************************************/
00007 // Importer for networks stored in Elmar's format
00008 /****************************************************************************/
00009 // SUMO, Simulation of Urban MObility; see http://sumo.sourceforge.net/
00010 // Copyright (C) 2001-2011 DLR (http://www.dlr.de/) and contributors
00011 /****************************************************************************/
00012 //
00013 //   This program is free software; you can redistribute it and/or modify
00014 //   it under the terms of the GNU General Public License as published by
00015 //   the Free Software Foundation; either version 2 of the License, or
00016 //   (at your option) any later version.
00017 //
00018 /****************************************************************************/
00019 
00020 
00021 // ===========================================================================
00022 // included modules
00023 // ===========================================================================
00024 #ifdef _MSC_VER
00025 #include <windows_config.h>
00026 #else
00027 #include <config.h>
00028 #endif
00029 
00030 #include <string>
00031 #include <sstream>
00032 #include <utils/importio/LineHandler.h>
00033 #include <utils/common/StringTokenizer.h>
00034 #include <utils/common/MsgHandler.h>
00035 #include <utils/common/UtilExceptions.h>
00036 #include <utils/common/TplConvert.h>
00037 #include <utils/options/OptionsCont.h>
00038 #include <utils/importio/LineReader.h>
00039 #include <utils/geom/GeoConvHelper.h>
00040 #include <netbuild/NBNetBuilder.h>
00041 #include <netbuild/NBNode.h>
00042 #include <netbuild/NBNodeCont.h>
00043 #include <netbuild/NBEdge.h>
00044 #include <netbuild/NBEdgeCont.h>
00045 #include <netbuild/NBTypeCont.h>
00046 #include <netbuild/NBOwnTLDef.h>
00047 #include <netimport/NINavTeqHelper.h>
00048 #include "NILoader.h"
00049 #include "NIImporter_DlrNavteq.h"
00050 
00051 
00052 #ifdef CHECK_MEMORY_LEAKS
00053 #include <foreign/nvwa/debug_new.h>
00054 #endif // CHECK_MEMORY_LEAKS
00055 
00056 
00057 // ===========================================================================
00058 // method definitions
00059 // ===========================================================================
00060 // ---------------------------------------------------------------------------
00061 // static methods
00062 // ---------------------------------------------------------------------------
00063 void
00064 NIImporter_DlrNavteq::loadNetwork(const OptionsCont& oc, NBNetBuilder& nb) {
00065     // check whether the option is set (properly)
00066     if (!oc.isSet("dlr-navteq-prefix")) {
00067         return;
00068     }
00069     // parse file(s)
00070     LineReader lr;
00071     // load nodes
00072     std::map<std::string, PositionVector> myGeoms;
00073     PROGRESS_BEGIN_MESSAGE("Loading nodes");
00074     std::string file = oc.getString("dlr-navteq-prefix") + "_nodes_unsplitted.txt";
00075     NodesHandler handler1(nb.getNodeCont(), file, myGeoms);
00076     if (!lr.setFile(file)) {
00077         throw ProcessError("The file '" + file + "' could not be opened.");
00078     }
00079     lr.readAll(handler1);
00080     PROGRESS_DONE_MESSAGE();
00081 
00082     // load traffic lights
00083     file = oc.getString("dlr-navteq-prefix") + "_traffic_signals.txt";
00084     if (lr.setFile(file)) {
00085         PROGRESS_BEGIN_MESSAGE("Loading traffic lights");
00086         TrafficlightsHandler handler3(nb.getNodeCont(), nb.getTLLogicCont(), file);
00087         lr.readAll(handler3);
00088         PROGRESS_DONE_MESSAGE();
00089     }
00090 
00091     // load edges
00092     PROGRESS_BEGIN_MESSAGE("Loading edges");
00093     file = oc.getString("dlr-navteq-prefix") + "_links_unsplitted.txt";
00094     // parse the file
00095     EdgesHandler handler2(nb.getNodeCont(), nb.getEdgeCont(), file, myGeoms);
00096     if (!lr.setFile(file)) {
00097         throw ProcessError("The file '" + file + "' could not be opened.");
00098     }
00099     lr.readAll(handler2);
00100     nb.getEdgeCont().recheckLaneSpread();
00101     PROGRESS_DONE_MESSAGE();
00102 }
00103 
00104 
00105 // ---------------------------------------------------------------------------
00106 // definitions of NIImporter_DlrNavteq::NodesHandler-methods
00107 // ---------------------------------------------------------------------------
00108 NIImporter_DlrNavteq::NodesHandler::NodesHandler(NBNodeCont& nc,
00109         const std::string& file,
00110         std::map<std::string, PositionVector> &geoms) throw()
00111     : myNodeCont(nc), myGeoms(geoms) {
00112     UNUSED_PARAMETER(file);
00113 }
00114 
00115 
00116 NIImporter_DlrNavteq::NodesHandler::~NodesHandler() throw() {}
00117 
00118 
00119 bool
00120 NIImporter_DlrNavteq::NodesHandler::report(const std::string& result) throw(ProcessError) {
00121     if (result[0]=='#') {
00122         return true;
00123     }
00124     std::string id;
00125     double x, y;
00126     int no_geoms, intermediate;
00127     // parse
00128     std::istringstream stream(result);
00129     // id
00130     stream >> id;
00131     if (stream.fail()) {
00132         throw ProcessError("Something is wrong with the following data line\n" + result);
00133     }
00134     // intermediate?
00135     stream >> intermediate;
00136     if (stream.fail()) {
00137         if (myNodeCont.size() == 0) { // be generous with extra data at beginning of file
00138             return true;
00139         }
00140         throw ProcessError("Non-numerical value for intermediate status in node " + id + ".");
00141     }
00142     // number of geometrical information
00143     stream >> no_geoms;
00144     if (stream.fail()) {
00145         throw ProcessError("Non-numerical value for number of geometries in node " + id + ".");
00146     }
00147     // geometrical information
00148     PositionVector geoms;
00149     for (int i=0; i<no_geoms; i++) {
00150         stream >> x;
00151         if (stream.fail()) {
00152             throw ProcessError("Non-numerical value for x-position in node " + id + ".");
00153         }
00154         stream >> y;
00155         if (stream.fail()) {
00156             throw ProcessError("Non-numerical value for y-position in node " + id + ".");
00157         }
00158         Position pos(x, y);
00159         if (!NILoader::transformCoordinates(pos, true)) {
00160             throw ProcessError("Unable to project coordinates for node " + id + ".");
00161         }
00162         geoms.push_back(pos);
00163     }
00164 
00165     if (intermediate==0) {
00166         NBNode* n = new NBNode(id, geoms[0]);
00167         if (!myNodeCont.insert(n)) {
00168             delete n;
00169             throw ProcessError("Could not add node '" + id + "'.");
00170         }
00171     } else {
00172         myGeoms[id] = geoms;
00173     }
00174     return true;
00175 }
00176 
00177 
00178 // ---------------------------------------------------------------------------
00179 // definitions of NIImporter_DlrNavteq::EdgesHandler-methods
00180 // ---------------------------------------------------------------------------
00181 NIImporter_DlrNavteq::EdgesHandler::EdgesHandler(NBNodeCont& nc, NBEdgeCont& ec,
00182         const std::string& file,
00183         std::map<std::string,
00184         PositionVector> &geoms) throw()
00185     : myNodeCont(nc), myEdgeCont(ec), myGeoms(geoms) {
00186     UNUSED_PARAMETER(file);
00187 }
00188 
00189 
00190 NIImporter_DlrNavteq::EdgesHandler::~EdgesHandler() throw() {}
00191 
00192 
00193 bool
00194 NIImporter_DlrNavteq::EdgesHandler::report(const std::string& result) throw(ProcessError) {
00195 //  0: LINK_ID  NODE_ID_FROM    NODE_ID_TO  BETWEEN_NODE_ID
00196 //  4: length   vehicle_type    form_of_way brunnel_type
00197 //  7: street_type  speed_category  number_of_lanes average_speed
00198 //  10: NAME_ID1    NAME_ID2    housenumbers_right  housenumbers_left
00199 //  ZIP_CODE    AREA_ID SUBAREA_ID  through_traffic special_restrictions
00200 //  extended_number_of_lanes  isRamp    (these two only exist in networks extracted since 05/2009)
00201 //  connection (this may be omitted)
00202 
00203     if (result[0]=='#') {
00204         return true;
00205     }
00206     std::string id, fromID, toID, interID;
00207     SUMOReal length;
00208     SUMOReal speed = (SUMOReal) 30.0 / (SUMOReal) 3.6;
00209     int nolanes = 1;
00210     int priority = -1;
00211     // parse
00212     StringTokenizer st(result, StringTokenizer::WHITECHARS);
00213     // id
00214     id = st.next();
00215     // from node id
00216     fromID = st.next();
00217     // to node id
00218     toID = st.next();
00219     // intermediate node id
00220     interID = st.next();
00221     // length
00222     try {
00223         length = TplConvert<char>::_2SUMOReal(st.next().c_str());
00224     } catch (NumberFormatException&) {
00225         throw ProcessError("Non-numerical value for an edge's length occured (edge '" + id + "'.");
00226     }
00227     // vehicle_type
00228     std::string veh_type = st.next();
00229     // form_of_way
00230     std::string form_of_way = st.next();
00231     // brunnel_type
00232     std::string brunnel_type = st.next();
00233     // street_type
00234     std::string street_type = st.next();
00235     speed = NINavTeqHelper::getSpeed(id, st.next());
00236     // number of lanes
00237     nolanes = NINavTeqHelper::getLaneNumber(id, st.next(), speed);
00238     std::vector<std::string> theRest = st.getVector();
00239     bool connection = (theRest.size() == 11) && (theRest[10] == "1");
00240     if (theRest.size() > 11) {
00241         // post 05/2009 network
00242         if (theRest[11] != "-1") {
00243             try {
00244                 nolanes = TplConvert<char>::_2int(theRest[11].c_str());
00245             } catch (NumberFormatException&) {
00246                 throw ProcessError("Non-numerical value for the extended number of lanes (edge '" + id + "'.");
00247             }
00248         }
00249         connection = (theRest.size() == 13) && (theRest[12] == "1");
00250     }
00251     // try to get the nodes
00252     NBNode* from = myNodeCont.retrieve(fromID);
00253     NBNode* to = myNodeCont.retrieve(toID);
00254     if (from==0) {
00255         throw ProcessError("The from-node '" + fromID + "' of edge '" + id + "' could not be found");
00256     }
00257     if (to==0) {
00258         throw ProcessError("The to-node '" + toID + "' of edge '" + id + "' could not be found");
00259     }
00260     // build the edge
00261     NBEdge* e = 0;
00262     if (interID=="-1") {
00263         e = new NBEdge(id, from, to, "", speed, nolanes, priority, -1, -1);
00264     } else {
00265         PositionVector geoms = myGeoms[interID];
00266         if (connection) {
00267             geoms = geoms.reverse();
00268             geoms.push_front(from->getPosition());
00269             geoms.push_back(to->getPosition());
00270             e = new NBEdge(id, from, to, "", speed, nolanes, priority, -1, -1, geoms, "", LANESPREAD_CENTER);
00271         } else {
00272             geoms.push_front(from->getPosition());
00273             geoms.push_back(to->getPosition());
00274             e = new NBEdge(id, from, to, "", speed, nolanes, priority, -1, -1, geoms, "", LANESPREAD_CENTER);
00275         }
00276     }
00277     // add vehicle type information to the edge
00278     NINavTeqHelper::addVehicleClasses(*e, veh_type);
00279     // insert the edge to the network
00280     if (!myEdgeCont.insert(e)) {
00281         delete e;
00282         throw ProcessError("Could not add edge '" + id + "'.");
00283     }
00284     return true;
00285 }
00286 
00287 
00288 // ---------------------------------------------------------------------------
00289 // definitions of NIImporter_DlrNavteq::TrafficlightsHandler-methods
00290 // ---------------------------------------------------------------------------
00291 NIImporter_DlrNavteq::TrafficlightsHandler::TrafficlightsHandler(NBNodeCont& nc,
00292         NBTrafficLightLogicCont& tlc,
00293         const std::string& file) throw()
00294     : myNodeCont(nc), myTLLogicCont(tlc) {
00295     UNUSED_PARAMETER(file);
00296 }
00297 
00298 
00299 NIImporter_DlrNavteq::TrafficlightsHandler::~TrafficlightsHandler() throw() {}
00300 
00301 
00302 bool
00303 NIImporter_DlrNavteq::TrafficlightsHandler::report(const std::string& result) throw(ProcessError) {
00304 // #ID     POICOL-TYPE     DESCRIPTION     LONGITUDE       LATITUDE        NAVTEQ_LINK_ID  NODEID
00305 
00306     if (result[0]=='#') {
00307         return true;
00308     }
00309     StringTokenizer st(result, StringTokenizer::WHITECHARS);
00310     std::string nodeID = st.getVector().back();
00311     NBNode* node = myNodeCont.retrieve(nodeID);
00312     if (node==0) {
00313         WRITE_WARNING("The traffic light node '" + nodeID + "' could not be found");
00314     } else {
00315         if (node->getType() != NODETYPE_TRAFFIC_LIGHT) {
00316             node->reinit(node->getPosition(), NODETYPE_TRAFFIC_LIGHT);
00317             NBTrafficLightDefinition* tlDef = new NBOwnTLDef(nodeID, node);
00318             if (!myTLLogicCont.insert(tlDef)) {
00319                 // actually, nothing should fail here
00320                 delete tlDef;
00321                 throw ProcessError("Could not allocate tls for '" + nodeID + "'.");
00322             }
00323         }
00324     }
00325     return true;
00326 }
00327 
00328 /****************************************************************************/
 All Data Structures Files Functions Variables Typedefs Enumerations Enumerator Friends Defines