MSEdge.cpp
Go to the documentation of this file.00001
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024 #ifdef _MSC_VER
00025 #include <windows_config.h>
00026 #else
00027 #include <config.h>
00028 #endif
00029
00030 #include "MSEdge.h"
00031 #include "MSLane.h"
00032 #include "MSLaneChanger.h"
00033 #include "MSGlobals.h"
00034 #include <algorithm>
00035 #include <iostream>
00036 #include <cassert>
00037 #include "MSVehicle.h"
00038 #include <utils/common/StringTokenizer.h>
00039 #include "MSEdgeWeightsStorage.h"
00040
00041 #ifdef HAVE_MESOSIM
00042 #include <mesosim/MELoop.h>
00043 #endif
00044
00045 #ifdef CHECK_MEMORY_LEAKS
00046 #include <foreign/nvwa/debug_new.h>
00047 #endif // CHECK_MEMORY_LEAKS
00048
00049
00050
00051
00052
00053 MSEdge::DictType MSEdge::myDict;
00054 std::vector<MSEdge*> MSEdge::myEdges;
00055
00056
00057
00058
00059
00060 MSEdge::MSEdge(const std::string &id, unsigned int numericalID) throw()
00061 : myID(id), myNumericalID(numericalID), myLanes(0),
00062 myLaneChanger(0), myVaporizationRequests(0), myLastFailedEmissionTime(-1) {}
00063
00064
00065 MSEdge::~MSEdge() throw() {
00066 delete myLaneChanger;
00067 for (AllowedLanesCont::iterator i1=myAllowed.begin(); i1!=myAllowed.end(); i1++) {
00068 delete(*i1).second;
00069 }
00070 for (ClassedAllowedLanesCont::iterator i2=myClassedAllowed.begin(); i2!=myClassedAllowed.end(); i2++) {
00071 for (AllowedLanesCont::iterator i1=(*i2).second.begin(); i1!=(*i2).second.end(); i1++) {
00072 delete(*i1).second;
00073 }
00074 }
00075 delete myLanes;
00076
00077 }
00078
00079
00080 void
00081 MSEdge::initialize(MSLane* departLane,
00082 std::vector<MSLane*>* lanes, EdgeBasicFunction function) throw() {
00083 assert(function == EDGEFUNCTION_DISTRICT || lanes!=0);
00084 myDepartLane = departLane;
00085 myLanes = lanes;
00086 myFunction = function;
00087 if (myLanes && myLanes->size() > 1 && function!=EDGEFUNCTION_INTERNAL) {
00088 myLaneChanger = new MSLaneChanger(myLanes);
00089 }
00090 }
00091
00092
00093 void
00094 MSEdge::closeBuilding() {
00095 myAllowed[0] = new std::vector<MSLane*>();
00096 for (std::vector<MSLane*>::iterator i=myLanes->begin(); i!=myLanes->end(); ++i) {
00097 myAllowed[0]->push_back(*i);
00098 const MSLinkCont &lc = (*i)->getLinkCont();
00099 for (MSLinkCont::const_iterator j=lc.begin(); j!=lc.end(); ++j) {
00100 MSLane *toL = (*j)->getLane();
00101 if (toL!=0) {
00102 MSEdge &to = toL->getEdge();
00103
00104 if (std::find(mySuccessors.begin(), mySuccessors.end(), &to)==mySuccessors.end()) {
00105 mySuccessors.push_back(&to);
00106 }
00107 if (std::find(to.myPredeccesors.begin(), to.myPredeccesors.end(), this)==to.myPredeccesors.end()) {
00108 to.myPredeccesors.push_back(this);
00109 }
00110
00111 if (myAllowed.find(&to)==myAllowed.end()) {
00112 myAllowed[&to] = new std::vector<MSLane*>();
00113 }
00114 myAllowed[&to]->push_back(*i);
00115 }
00116 }
00117 }
00118 std::sort(mySuccessors.begin(), mySuccessors.end(), by_id_sorter());
00119 rebuildAllowedLanes();
00120 }
00121
00122
00123 void
00124 MSEdge::rebuildAllowedLanes() throw() {
00125
00126 myHaveClassConstraints = false;
00127
00128
00129 std::set<SUMOVehicleClass> vclasses;
00130 for (std::vector<MSLane*>::const_iterator i2=myLanes->begin(); i2!=myLanes->end(); ++i2) {
00131 const std::vector<SUMOVehicleClass> &allowed = (*i2)->getAllowedClasses();
00132 for (std::vector<SUMOVehicleClass>::const_iterator j=allowed.begin(); j!=allowed.end(); j++) {
00133 vclasses.insert(*j);
00134 }
00135 const std::vector<SUMOVehicleClass> &disallowed = (*i2)->getNotAllowedClasses();
00136 for (std::vector<SUMOVehicleClass>::const_iterator j=disallowed.begin(); j!=disallowed.end(); j++) {
00137 vclasses.insert(*j);
00138 }
00139 }
00140
00141 for (std::set<SUMOVehicleClass>::const_iterator j=vclasses.begin(); j!=vclasses.end(); ++j) {
00142
00143 for (AllowedLanesCont::iterator i1=myAllowed.begin(); i1!=myAllowed.end(); ++i1) {
00144 delete myClassedAllowed[*j][(*i1).first];
00145 myClassedAllowed[*j][(*i1).first] = new std::vector<MSLane*>();
00146
00147 for (std::vector<MSLane*>::iterator i2=(*i1).second->begin(); i2!=(*i1).second->end(); ++i2) {
00148
00149 if ((*i2)->allowsVehicleClass(*j)) {
00150
00151 myClassedAllowed[*j][(*i1).first]->push_back(*i2);
00152 }
00153 }
00154
00155 if (myClassedAllowed[*j][(*i1).first]->size()==0) {
00156 delete myClassedAllowed[*j][(*i1).first];
00157 myClassedAllowed[*j][(*i1).first] = 0;
00158 }
00159 }
00160 myHaveClassConstraints = true;
00161 }
00162 }
00163
00164
00165
00166 MSLane * const
00167 MSEdge::leftLane(const MSLane * const lane) const throw() {
00168 std::vector<MSLane*>::iterator laneIt = find(myLanes->begin(), myLanes->end(), lane);
00169 if (laneIt==myLanes->end()||laneIt==myLanes->end()-1) {
00170 return 0;
00171 }
00172 return *(laneIt+1);
00173 }
00174
00175
00176 MSLane * const
00177 MSEdge::rightLane(const MSLane * const lane) const throw() {
00178 std::vector<MSLane*>::iterator laneIt = find(myLanes->begin(), myLanes->end(), lane);
00179 if (laneIt==myLanes->end()||laneIt==myLanes->begin()) {
00180 return 0;
00181 }
00182 return *(laneIt-1);
00183 }
00184
00185
00186 const std::vector<MSLane*>*
00187 MSEdge::allowedLanes(const MSEdge& destination, SUMOVehicleClass vclass) const throw() {
00188 return allowedLanes(&destination, vclass);
00189 }
00190
00191
00192 const std::vector<MSLane*>*
00193 MSEdge::allowedLanes(SUMOVehicleClass vclass) const throw() {
00194 return allowedLanes(0, vclass);
00195 }
00196
00197
00198 const std::vector<MSLane*>*
00199 MSEdge::allowedLanes(const MSEdge *destination, SUMOVehicleClass vclass) const throw() {
00200 if (myHaveClassConstraints&&vclass!=SVC_UNKNOWN) {
00201 ClassedAllowedLanesCont::const_iterator i = myClassedAllowed.find(vclass);
00202 if (i!=myClassedAllowed.end()) {
00203 const AllowedLanesCont &c = (*i).second;
00204 AllowedLanesCont::const_iterator j = (*i).second.find(destination);
00205 if (j==c.end()) {
00206
00207 return 0;
00208 }
00209 return (*j).second;
00210 }
00211 }
00212 AllowedLanesCont::const_iterator it = myAllowed.find(destination);
00213 if (it!=myAllowed.end()) {
00214 return it->second;
00215 } else {
00216
00217 return 0;
00218 }
00219 }
00220
00221
00222
00223 SUMOTime
00224 MSEdge::incVaporization(SUMOTime) throw(ProcessError) {
00225 ++myVaporizationRequests;
00226 return 0;
00227 }
00228
00229
00230 SUMOTime
00231 MSEdge::decVaporization(SUMOTime) throw(ProcessError) {
00232 --myVaporizationRequests;
00233 return 0;
00234 }
00235
00236
00237 MSLane *
00238 MSEdge::getFreeLane(const SUMOVehicleClass vclass) const throw() {
00239 const std::vector<MSLane*>* lanes = allowedLanes(vclass);
00240 MSLane* res = 0;
00241 if (lanes != 0) {
00242 unsigned int noCars = INT_MAX;
00243 for (std::vector<MSLane*>::const_iterator i=lanes->begin(); i!=lanes->end(); ++i) {
00244 if ((*i)->getVehicleNumber()<noCars) {
00245 res = (*i);
00246 noCars = (*i)->getVehicleNumber();
00247 }
00248 }
00249 }
00250 return res;
00251 }
00252
00253
00254 MSLane *
00255 MSEdge::getDepartLane(const MSVehicle &v) const throw() {
00256 const SUMOVehicleParameter &pars = v.getParameter();
00257 switch (pars.departLaneProcedure) {
00258 case DEPART_LANE_GIVEN:
00259 if ((int) myLanes->size() <= pars.departLane || !(*myLanes)[pars.departLane]->allowsVehicleClass(v.getVehicleType().getVehicleClass())) {
00260 return 0;
00261 }
00262 return (*myLanes)[pars.departLane];
00263 case DEPART_LANE_RANDOM:
00264 return RandHelper::getRandomFrom(*allowedLanes(v.getVehicleType().getVehicleClass()));
00265 case DEPART_LANE_FREE:
00266 return getFreeLane(v.getVehicleType().getVehicleClass());
00267 case DEPART_LANE_DEPARTLANE:
00268 case DEPART_LANE_DEFAULT:
00269 default:
00270 break;
00271 }
00272 if (!myDepartLane->allowsVehicleClass(v.getVehicleType().getVehicleClass())) {
00273 return 0;
00274 }
00275 return myDepartLane;
00276 }
00277
00278
00279 bool
00280 MSEdge::emit(MSVehicle &v, SUMOTime time) const throw(ProcessError) {
00281
00282 if (isVaporizing()) {
00283 return false;
00284 }
00285 const SUMOVehicleParameter &pars = v.getParameter();
00286 #ifdef HAVE_MESOSIM
00287 if (MSGlobals::gUseMesoSim) {
00288 SUMOReal pos = 0.0;
00289 switch (pars.departPosProcedure) {
00290 case DEPART_POS_GIVEN:
00291 if (pars.departPos >= 0.) {
00292 pos = pars.departPos;
00293 } else {
00294 pos = pars.departPos + getLanes()[0]->getLength();
00295 }
00296 break;
00297 case DEPART_POS_RANDOM:
00298 case DEPART_POS_RANDOM_FREE:
00299 pos = RandHelper::rand(getLanes()[0]->getLength());
00300 break;
00301 default:
00302 break;
00303 }
00304 bool result = false;
00305 bool insertToNet = false;
00306 MESegment* segment = MSGlobals::gMesoNet->getSegmentForEdge(*this, pos);
00307 if (pars.departPosProcedure == DEPART_POS_FREE) {
00308 while (segment != 0 && !result) {
00309 result = segment->initialise(&v, time, insertToNet);
00310 segment = segment->getNextSegment();
00311 }
00312 } else {
00313 result = segment->initialise(&v, time, insertToNet);
00314 }
00315 if (insertToNet) {
00316 MSGlobals::gMesoNet->addCar(&v);
00317 }
00318 return result;
00319 }
00320 #endif
00321 MSLane* emitLane = getDepartLane(v);
00322 return emitLane != 0 && emitLane->emit(v);
00323 }
00324
00325
00326 void
00327 MSEdge::changeLanes(SUMOTime t) throw() {
00328 if (myFunction==EDGEFUNCTION_INTERNAL) {
00329 return;
00330 }
00331 assert(myLaneChanger != 0);
00332 myLaneChanger->laneChange(t);
00333 }
00334
00335
00336
00337 #ifdef HAVE_INTERNAL_LANES
00338 const MSEdge *
00339 MSEdge::getInternalFollowingEdge(MSEdge *followerAfterInternal) const throw() {
00340
00341 for (std::vector<MSLane*>::const_iterator i=myLanes->begin(); i!=myLanes->end(); ++i) {
00342 MSLane *l = *i;
00343 const MSLinkCont &lc = l->getLinkCont();
00344 for (MSLinkCont::const_iterator j=lc.begin(); j!=lc.end(); ++j) {
00345 MSLink *link = *j;
00346 if (&link->getLane()->getEdge()==followerAfterInternal) {
00347 return &link->getViaLane()->getEdge();
00348 }
00349 }
00350 }
00351 return 0;
00352 }
00353 #endif
00354
00355
00356 SUMOReal
00357 MSEdge::getCurrentTravelTime() const throw() {
00358 SUMOReal v = 0;
00359 #ifdef HAVE_MESOSIM
00360 if (MSGlobals::gUseMesoSim) {
00361 MESegment *first = MSGlobals::gMesoNet->getSegmentForEdge(*this);
00362 unsigned segments = 0;
00363 do {
00364 v += first->getMeanSpeed();
00365 first = first->getNextSegment();
00366 segments++;
00367 } while (first!=0);
00368 v /= (SUMOReal) segments;
00369 } else {
00370 #endif
00371 for (std::vector<MSLane*>::iterator i=myLanes->begin(); i!=myLanes->end(); ++i) {
00372 v += (*i)->getMeanSpeed();
00373 }
00374 v /= (SUMOReal) myLanes->size();
00375 #ifdef HAVE_MESOSIM
00376 }
00377 #endif
00378 if (v!=0) {
00379 return (*myLanes)[0]->getLength() / v;
00380 } else {
00381 return 1000000.;
00382 }
00383 }
00384
00385
00386 bool
00387 MSEdge::prohibits(const SUMOVehicle * const vehicle) const throw() {
00388 if (myFunction == EDGEFUNCTION_DISTRICT || !myHaveClassConstraints) {
00389 return false;
00390 }
00391 SUMOVehicleClass vclass = vehicle->getVehicleType().getVehicleClass();
00392 for (std::vector<MSLane*>::iterator i=myLanes->begin(); i!=myLanes->end(); ++i) {
00393 if ((*i)->allowsVehicleClass(vclass)) {
00394 return false;
00395 }
00396 }
00397 return true;
00398 }
00399
00400
00401 bool
00402 MSEdge::dictionary(const std::string &id, MSEdge* ptr) throw() {
00403 DictType::iterator it = myDict.find(id);
00404 if (it == myDict.end()) {
00405
00406 myDict[id] = ptr;
00407 while (myEdges.size()<ptr->getNumericalID()+1) {
00408 myEdges.push_back(0);
00409 }
00410 myEdges[ptr->getNumericalID()] = ptr;
00411 return true;
00412 }
00413 return false;
00414 }
00415
00416
00417 MSEdge*
00418 MSEdge::dictionary(const std::string &id) throw() {
00419 DictType::iterator it = myDict.find(id);
00420 if (it == myDict.end()) {
00421
00422 return 0;
00423 }
00424 return it->second;
00425 }
00426
00427
00428 MSEdge*
00429 MSEdge::dictionary(size_t id) throw() {
00430 assert(myEdges.size()>id);
00431 return myEdges[id];
00432 }
00433
00434
00435 size_t
00436 MSEdge::dictSize() throw() {
00437 return myDict.size();
00438 }
00439
00440
00441 void
00442 MSEdge::clear() throw() {
00443 for (DictType::iterator i=myDict.begin(); i!=myDict.end(); ++i) {
00444 delete(*i).second;
00445 }
00446 myDict.clear();
00447 }
00448
00449
00450 void
00451 MSEdge::insertIDs(std::vector<std::string> &into) throw() {
00452 for (DictType::iterator i=myDict.begin(); i!=myDict.end(); ++i) {
00453 into.push_back((*i).first);
00454 }
00455 }
00456
00457
00458 void
00459 MSEdge::parseEdgesList(const std::string &desc, std::vector<const MSEdge*> &into,
00460 const std::string &rid) throw(ProcessError) {
00461 StringTokenizer st(desc);
00462 parseEdgesList(st.getVector(), into, rid);
00463 }
00464
00465
00466 void
00467 MSEdge::parseEdgesList(const std::vector<std::string> &desc, std::vector<const MSEdge*> &into,
00468 const std::string &rid) throw(ProcessError) {
00469 for (std::vector<std::string>::const_iterator i=desc.begin(); i!=desc.end(); ++i) {
00470 const MSEdge *edge = MSEdge::dictionary(*i);
00471
00472 if (edge==0) {
00473 throw ProcessError("The edge '" + *i + "' within route '" + rid + "' is not known."
00474 + "\n The route can not be build.");
00475 }
00476 into.push_back(edge);
00477 }
00478 }
00479
00480
00481
00482