SUMO - Simulation of Urban MObility
MSEdge.cpp
Go to the documentation of this file.
00001 /****************************************************************************/
00013 // A road/street connecting two junctions
00014 /****************************************************************************/
00015 // SUMO, Simulation of Urban MObility; see http://sumo.sourceforge.net/
00016 // Copyright (C) 2001-2012 DLR (http://www.dlr.de/) and contributors
00017 /****************************************************************************/
00018 //
00019 //   This file is part of SUMO.
00020 //   SUMO is free software: you can redistribute it and/or modify
00021 //   it under the terms of the GNU General Public License as published by
00022 //   the Free Software Foundation, either version 3 of the License, or
00023 //   (at your option) any later version.
00024 //
00025 /****************************************************************************/
00026 
00027 
00028 // ===========================================================================
00029 // included modules
00030 // ===========================================================================
00031 #ifdef _MSC_VER
00032 #include <windows_config.h>
00033 #else
00034 #include <config.h>
00035 #endif
00036 
00037 #include <algorithm>
00038 #include <iostream>
00039 #include <cassert>
00040 #include <utils/common/StringTokenizer.h>
00041 #include <utils/options/OptionsCont.h>
00042 #include "MSEdge.h"
00043 #include "MSLane.h"
00044 #include "MSLaneChanger.h"
00045 #include "MSGlobals.h"
00046 #include "MSVehicle.h"
00047 #include "MSEdgeWeightsStorage.h"
00048 
00049 #ifdef HAVE_MESOSIM
00050 #include <mesosim/MELoop.h>
00051 #include <mesosim/MESegment.h>
00052 #include <mesosim/MEVehicle.h>
00053 #endif
00054 
00055 #ifdef CHECK_MEMORY_LEAKS
00056 #include <foreign/nvwa/debug_new.h>
00057 #endif // CHECK_MEMORY_LEAKS
00058 
00059 
00060 // ===========================================================================
00061 // static member definitions
00062 // ===========================================================================
00063 MSEdge::DictType MSEdge::myDict;
00064 std::vector<MSEdge*> MSEdge::myEdges;
00065 
00066 
00067 // ===========================================================================
00068 // member method definitions
00069 // ===========================================================================
00070 MSEdge::MSEdge(const std::string& id, unsigned int numericalID,
00071                const std::string& streetName) :
00072     myID(id), myNumericalID(numericalID), myLanes(0),
00073     myLaneChanger(0), myVaporizationRequests(0), myLastFailedInsertionTime(-1),
00074     myStreetName(streetName) {}
00075 
00076 
00077 MSEdge::~MSEdge() {
00078     delete myLaneChanger;
00079     for (AllowedLanesCont::iterator i1 = myAllowed.begin(); i1 != myAllowed.end(); i1++) {
00080         delete(*i1).second;
00081     }
00082     for (ClassedAllowedLanesCont::iterator i2 = myClassedAllowed.begin(); i2 != myClassedAllowed.end(); i2++) {
00083         for (AllowedLanesCont::iterator i1 = (*i2).second.begin(); i1 != (*i2).second.end(); i1++) {
00084             delete(*i1).second;
00085         }
00086     }
00087     delete myLanes;
00088     // Note: Lanes are delete using MSLane::clear();
00089 }
00090 
00091 
00092 void
00093 MSEdge::initialize(std::vector<MSLane*>* lanes, EdgeBasicFunction function) {
00094     assert(function == EDGEFUNCTION_DISTRICT || lanes != 0);
00095     myLanes = lanes;
00096     myFunction = function;
00097     if (myLanes && myLanes->size() > 1 && function != EDGEFUNCTION_INTERNAL) {
00098         myLaneChanger = new MSLaneChanger(myLanes, OptionsCont::getOptions().getBool("lanechange.allow-swap"));
00099     }
00100 }
00101 
00102 
00103 void
00104 MSEdge::closeBuilding() {
00105     myAllowed[0] = new std::vector<MSLane*>();
00106     for (std::vector<MSLane*>::iterator i = myLanes->begin(); i != myLanes->end(); ++i) {
00107         myAllowed[0]->push_back(*i);
00108         const MSLinkCont& lc = (*i)->getLinkCont();
00109         for (MSLinkCont::const_iterator j = lc.begin(); j != lc.end(); ++j) {
00110             MSLane* toL = (*j)->getLane();
00111             if (toL != 0) {
00112                 MSEdge& to = toL->getEdge();
00113                 //
00114                 if (std::find(mySuccessors.begin(), mySuccessors.end(), &to) == mySuccessors.end()) {
00115                     mySuccessors.push_back(&to);
00116                 }
00117                 if (std::find(to.myPredeccesors.begin(), to.myPredeccesors.end(), this) == to.myPredeccesors.end()) {
00118                     to.myPredeccesors.push_back(this);
00119                 }
00120                 //
00121                 if (myAllowed.find(&to) == myAllowed.end()) {
00122                     myAllowed[&to] = new std::vector<MSLane*>();
00123                 }
00124                 myAllowed[&to]->push_back(*i);
00125             }
00126         }
00127     }
00128     std::sort(mySuccessors.begin(), mySuccessors.end(), by_id_sorter());
00129     rebuildAllowedLanes();
00130 }
00131 
00132 
00133 void
00134 MSEdge::rebuildAllowedLanes() {
00135     // clear myClassedAllowed. 
00136     // it will be rebuilt on demand
00137     for (ClassedAllowedLanesCont::iterator i2 = myClassedAllowed.begin(); i2 != myClassedAllowed.end(); i2++) {
00138         for (AllowedLanesCont::iterator i1 = (*i2).second.begin(); i1 != (*i2).second.end(); i1++) {
00139             delete(*i1).second;
00140         }
00141     }
00142     myClassedAllowed.clear();
00143     // rebuild myMinimumPermissions and myCombinedPermissions
00144     myMinimumPermissions = SVCFreeForAll;
00145     myCombinedPermissions = 0;
00146     for (std::vector<MSLane*>::iterator i = myLanes->begin(); i != myLanes->end(); ++i) {
00147         myMinimumPermissions &= (*i)->getPermissions();
00148         myCombinedPermissions |= (*i)->getPermissions();
00149     }
00150 }
00151 
00152 
00153 // ------------ Access to the edge's lanes
00154 MSLane*
00155 MSEdge::leftLane(const MSLane* const lane) const {
00156     std::vector<MSLane*>::iterator laneIt = find(myLanes->begin(), myLanes->end(), lane);
00157     if (laneIt == myLanes->end() || laneIt == myLanes->end() - 1) {
00158         return 0;
00159     }
00160     return *(laneIt + 1);
00161 }
00162 
00163 
00164 MSLane*
00165 MSEdge::rightLane(const MSLane* const lane) const {
00166     std::vector<MSLane*>::iterator laneIt = find(myLanes->begin(), myLanes->end(), lane);
00167     if (laneIt == myLanes->end() || laneIt == myLanes->begin()) {
00168         return 0;
00169     }
00170     return *(laneIt - 1);
00171 }
00172 
00173 
00174 const std::vector<MSLane*>*
00175 MSEdge::allowedLanes(const MSEdge& destination, SUMOVehicleClass vclass) const {
00176     return allowedLanes(&destination, vclass);
00177 }
00178 
00179 
00180 const std::vector<MSLane*>*
00181 MSEdge::allowedLanes(SUMOVehicleClass vclass) const {
00182     return allowedLanes(0, vclass);
00183 }
00184 
00185 
00186 const std::vector<MSLane*>* 
00187 MSEdge::getAllowedLanesWithDefault(const AllowedLanesCont& c, const MSEdge* dest) const {
00188     AllowedLanesCont::const_iterator it = c.find(dest);
00189     if (it == c.end()) {
00190         return 0;
00191     }
00192     return it->second;
00193 }
00194 
00195 
00196 const std::vector<MSLane*>*
00197 MSEdge::allowedLanes(const MSEdge* destination, SUMOVehicleClass vclass) const {
00198     if ((myMinimumPermissions & vclass) == vclass) {
00199         // all lanes allow vclass
00200         return getAllowedLanesWithDefault(myAllowed, destination);
00201     }
00202     // look up cached result in myClassedAllowed
00203     ClassedAllowedLanesCont::const_iterator i = myClassedAllowed.find(vclass);
00204     if (i != myClassedAllowed.end()) {
00205         // can use cached value
00206         const AllowedLanesCont& c = (*i).second;
00207         return getAllowedLanesWithDefault(c, destination);
00208     } else {
00209         // this vclass is requested for the first time. rebuild all destinations
00210         // go through connected edges
00211         for (AllowedLanesCont::const_iterator i1 = myAllowed.begin(); i1 != myAllowed.end(); ++i1) {
00212             const MSEdge* edge = i1->first;
00213             const std::vector<MSLane*>* lanes = i1->second;
00214             myClassedAllowed[vclass][edge] = new std::vector<MSLane*>();
00215             // go through lanes approaching current edge
00216             for (std::vector<MSLane*>::const_iterator i2 = lanes->begin(); i2 != lanes->end(); ++i2) {
00217                 // allows the current vehicle class?
00218                 if ((*i2)->allowsVehicleClass(vclass)) {
00219                     // -> may be used
00220                     myClassedAllowed[vclass][edge]->push_back(*i2);
00221                 }
00222             }
00223             // assert that 0 is returned if no connection is allowed for a class
00224             if (myClassedAllowed[vclass][edge]->size() == 0) {
00225                 delete myClassedAllowed[vclass][edge];
00226                 myClassedAllowed[vclass][edge] = 0;
00227             }
00228         }
00229         return myClassedAllowed[vclass][destination];
00230     }
00231 }
00232 
00233 
00234 // ------------
00235 SUMOTime
00236 MSEdge::incVaporization(SUMOTime) {
00237     ++myVaporizationRequests;
00238     return 0;
00239 }
00240 
00241 
00242 SUMOTime
00243 MSEdge::decVaporization(SUMOTime) {
00244     --myVaporizationRequests;
00245     return 0;
00246 }
00247 
00248 
00249 MSLane*
00250 MSEdge::getFreeLane(const std::vector<MSLane*>* allowed, const SUMOVehicleClass vclass) const {
00251     if (allowed == 0) {
00252         allowed = allowedLanes(vclass);
00253     }
00254     MSLane* res = 0;
00255     if (allowed != 0) {
00256         unsigned int noCars = INT_MAX;
00257         for (std::vector<MSLane*>::const_iterator i = allowed->begin(); i != allowed->end(); ++i) {
00258             if ((*i)->getVehicleNumber() < noCars) {
00259                 res = (*i);
00260                 noCars = (*i)->getVehicleNumber();
00261             }
00262         }
00263     }
00264     return res;
00265 }
00266 
00267 
00268 MSLane*
00269 MSEdge::getDepartLane(const MSVehicle& veh) const {
00270     switch (veh.getParameter().departLaneProcedure) {
00271         case DEPART_LANE_GIVEN:
00272             if ((int) myLanes->size() <= veh.getParameter().departLane || !(*myLanes)[veh.getParameter().departLane]->allowsVehicleClass(veh.getVehicleType().getVehicleClass())) {
00273                 return 0;
00274             }
00275             return (*myLanes)[veh.getParameter().departLane];
00276         case DEPART_LANE_RANDOM:
00277             return RandHelper::getRandomFrom(*allowedLanes(veh.getVehicleType().getVehicleClass()));
00278         case DEPART_LANE_FREE:
00279             return getFreeLane(0, veh.getVehicleType().getVehicleClass());
00280         case DEPART_LANE_ALLOWED_FREE:
00281             if (veh.getRoute().size() == 1) {
00282                 return getFreeLane(0, veh.getVehicleType().getVehicleClass());
00283             } else {
00284                 return getFreeLane(allowedLanes(**(veh.getRoute().begin() + 1)), veh.getVehicleType().getVehicleClass());
00285             }
00286         case DEPART_LANE_BEST_FREE: {
00287             const std::vector<MSVehicle::LaneQ> &bl = veh.getBestLanes(false, (*myLanes)[0]);
00288             SUMOReal bestLength = -1;
00289             for (std::vector<MSVehicle::LaneQ>::const_iterator i = bl.begin(); i != bl.end(); ++i) {
00290                 if ((*i).length > bestLength) {
00291                     bestLength = (*i).length;
00292                 }
00293             }
00294             std::vector<MSLane*> *bestLanes = new std::vector<MSLane*>();
00295             for (std::vector<MSVehicle::LaneQ>::const_iterator i = bl.begin(); i != bl.end(); ++i) {
00296                 if ((*i).length == bestLength) {
00297                     bestLanes->push_back((*i).lane);
00298                 }
00299             }
00300             MSLane* ret = getFreeLane(bestLanes, veh.getVehicleType().getVehicleClass());
00301             delete bestLanes;
00302             return ret;
00303         }
00304         case DEPART_LANE_DEFAULT:
00305         default:
00306             break;
00307     }
00308     if (!(*myLanes)[0]->allowsVehicleClass(veh.getVehicleType().getVehicleClass())) {
00309         return 0;
00310     }
00311     return (*myLanes)[0];
00312 }
00313 
00314 
00315 bool
00316 MSEdge::insertVehicle(SUMOVehicle& v, SUMOTime time) const {
00317     // when vaporizing, no vehicles are inserted...
00318     if (isVaporizing()) {
00319         return false;
00320     }
00321 #ifdef HAVE_MESOSIM
00322     if (MSGlobals::gUseMesoSim) {
00323         const SUMOVehicleParameter& pars = v.getParameter();
00324         SUMOReal pos = 0.0;
00325         switch (pars.departPosProcedure) {
00326             case DEPART_POS_GIVEN:
00327                 if (pars.departPos >= 0.) {
00328                     pos = pars.departPos;
00329                 } else {
00330                     pos = pars.departPos + getLength();
00331                 }
00332                 if (pos < 0 || pos > getLength()) {
00333                     WRITE_WARNING("Invalid departPos " + toString(pos) + " given for vehicle '" + 
00334                             v.getID() + "'. Inserting at lane end instead.");
00335                     pos = getLength();
00336                 }
00337                 break;
00338             case DEPART_POS_RANDOM:
00339             case DEPART_POS_RANDOM_FREE:
00340                 pos = RandHelper::rand(getLength());
00341                 break;
00342             default:
00343                 break;
00344         }
00345         bool result = false;
00346         MESegment* segment = MSGlobals::gMesoNet->getSegmentForEdge(*this, pos);
00347         MEVehicle* veh = static_cast<MEVehicle*>(&v);
00348         if (pars.departPosProcedure == DEPART_POS_FREE) {
00349             while (segment != 0 && !result) {
00350                 result = segment->initialise(veh, time);
00351                 segment = segment->getNextSegment();
00352             }
00353         } else {
00354             result = segment->initialise(veh, time);
00355         }
00356         return result;
00357     }
00358 #endif
00359     MSLane* insertionLane = getDepartLane(static_cast<MSVehicle&>(v));
00360     return insertionLane != 0 && insertionLane->insertVehicle(static_cast<MSVehicle&>(v));
00361 }
00362 
00363 
00364 void
00365 MSEdge::changeLanes(SUMOTime t) {
00366     if (myFunction == EDGEFUNCTION_INTERNAL) {
00367         return;
00368     }
00369     assert(myLaneChanger != 0);
00370     myLaneChanger->laneChange(t);
00371 }
00372 
00373 
00374 
00375 #ifdef HAVE_INTERNAL_LANES
00376 const MSEdge*
00377 MSEdge::getInternalFollowingEdge(MSEdge* followerAfterInternal) const {
00378     //@todo to be optimized
00379     for (std::vector<MSLane*>::const_iterator i = myLanes->begin(); i != myLanes->end(); ++i) {
00380         MSLane* l = *i;
00381         const MSLinkCont& lc = l->getLinkCont();
00382         for (MSLinkCont::const_iterator j = lc.begin(); j != lc.end(); ++j) {
00383             MSLink* link = *j;
00384             if (&link->getLane()->getEdge() == followerAfterInternal) {
00385                 return &link->getViaLane()->getEdge();
00386             }
00387         }
00388     }
00389     return 0;
00390 }
00391 #endif
00392 
00393 
00394 SUMOReal
00395 MSEdge::getCurrentTravelTime() const {
00396     SUMOReal v = 0;
00397 #ifdef HAVE_MESOSIM
00398     if (MSGlobals::gUseMesoSim) {
00399         MESegment* first = MSGlobals::gMesoNet->getSegmentForEdge(*this);
00400         unsigned segments = 0;
00401         do {
00402             v += first->getMeanSpeed();
00403             first = first->getNextSegment();
00404             segments++;
00405         } while (first != 0);
00406         v /= (SUMOReal) segments;
00407     } else {
00408 #endif
00409         for (std::vector<MSLane*>::iterator i = myLanes->begin(); i != myLanes->end(); ++i) {
00410             v += (*i)->getMeanSpeed();
00411         }
00412         v /= (SUMOReal) myLanes->size();
00413 #ifdef HAVE_MESOSIM
00414     }
00415 #endif
00416     if (v != 0) {
00417         return getLength() / v;
00418     } else {
00419         return 1000000.;
00420     }
00421 }
00422 
00423 
00424 bool
00425 MSEdge::dictionary(const std::string& id, MSEdge* ptr) {
00426     DictType::iterator it = myDict.find(id);
00427     if (it == myDict.end()) {
00428         // id not in myDict.
00429         myDict[id] = ptr;
00430         while (myEdges.size() < ptr->getNumericalID() + 1) {
00431             myEdges.push_back(0);
00432         }
00433         myEdges[ptr->getNumericalID()] = ptr;
00434         return true;
00435     }
00436     return false;
00437 }
00438 
00439 
00440 MSEdge*
00441 MSEdge::dictionary(const std::string& id) {
00442     DictType::iterator it = myDict.find(id);
00443     if (it == myDict.end()) {
00444         // id not in myDict.
00445         return 0;
00446     }
00447     return it->second;
00448 }
00449 
00450 
00451 MSEdge*
00452 MSEdge::dictionary(size_t id) {
00453     assert(myEdges.size() > id);
00454     return myEdges[id];
00455 }
00456 
00457 
00458 size_t
00459 MSEdge::dictSize() {
00460     return myDict.size();
00461 }
00462 
00463 
00464 void
00465 MSEdge::clear() {
00466     for (DictType::iterator i = myDict.begin(); i != myDict.end(); ++i) {
00467         delete(*i).second;
00468     }
00469     myDict.clear();
00470 }
00471 
00472 
00473 void
00474 MSEdge::insertIDs(std::vector<std::string> &into) {
00475     for (DictType::iterator i = myDict.begin(); i != myDict.end(); ++i) {
00476         into.push_back((*i).first);
00477     }
00478 }
00479 
00480 
00481 void
00482 MSEdge::parseEdgesList(const std::string& desc, std::vector<const MSEdge*> &into,
00483                        const std::string& rid) {
00484     StringTokenizer st(desc);
00485     parseEdgesList(st.getVector(), into, rid);
00486 }
00487 
00488 
00489 void
00490 MSEdge::parseEdgesList(const std::vector<std::string> &desc, std::vector<const MSEdge*> &into,
00491                        const std::string& rid) {
00492     for (std::vector<std::string>::const_iterator i = desc.begin(); i != desc.end(); ++i) {
00493         const MSEdge* edge = MSEdge::dictionary(*i);
00494         // check whether the edge exists
00495         if (edge == 0) {
00496             throw ProcessError("The edge '" + *i + "' within the route " + rid + " is not known."
00497                                + "\n The route can not be build.");
00498         }
00499         into.push_back(edge);
00500     }
00501 }
00502 
00503 
00504 SUMOReal 
00505 MSEdge::getDistanceTo(const MSEdge* other) const {
00506     return getLanes()[0]->getShape()[-1].distanceTo2D(other->getLanes()[0]->getShape()[0]);
00507 }
00508 
00509 
00510 SUMOReal 
00511 MSEdge::getLength() const {
00512     return getLanes()[0]->getLength();
00513 }
00514 
00515 
00516 SUMOReal 
00517 MSEdge::getMaxSpeed() const {
00518     // @note lanes might have different maximum speeds in theory
00519     return getLanes()[0]->getMaxSpeed();
00520 }
00521 
00522 /****************************************************************************/
00523 
 All Data Structures Files Functions Variables Typedefs Enumerations Enumerator Friends Defines