SUMO - Simulation of Urban MObility
|
00001 /****************************************************************************/ 00012 // The simulated network and simulation perfomer 00013 /****************************************************************************/ 00014 // SUMO, Simulation of Urban MObility; see http://sumo.sourceforge.net/ 00015 // Copyright (C) 2001-2012 DLR (http://www.dlr.de/) and contributors 00016 /****************************************************************************/ 00017 // 00018 // This file is part of SUMO. 00019 // SUMO is free software: you can redistribute it and/or modify 00020 // it under the terms of the GNU General Public License as published by 00021 // the Free Software Foundation, either version 3 of the License, or 00022 // (at your option) any later version. 00023 // 00024 /****************************************************************************/ 00025 00026 00027 // =========================================================================== 00028 // included modules 00029 // =========================================================================== 00030 #ifdef _MSC_VER 00031 #include <windows_config.h> 00032 #else 00033 #include <config.h> 00034 #endif 00035 00036 #ifdef HAVE_VERSION_H 00037 #include <version.h> 00038 #endif 00039 00040 #include <iostream> 00041 #include <sstream> 00042 #include <typeinfo> 00043 #include <algorithm> 00044 #include <cassert> 00045 #include <vector> 00046 #include <sstream> 00047 #include <utils/common/UtilExceptions.h> 00048 #include "MSNet.h" 00049 #include "MSPersonControl.h" 00050 #include "MSEdgeControl.h" 00051 #include "MSJunctionControl.h" 00052 #include "MSInsertionControl.h" 00053 #include "MSEventControl.h" 00054 #include "MSEdge.h" 00055 #include "MSJunction.h" 00056 #include "MSJunctionLogic.h" 00057 #include "MSLane.h" 00058 #include "MSVehicleTransfer.h" 00059 #include "MSRoute.h" 00060 #include "MSRouteLoaderControl.h" 00061 #include "traffic_lights/MSTLLogicControl.h" 00062 #include "MSVehicleControl.h" 00063 #include <utils/common/MsgHandler.h> 00064 #include <utils/common/ToString.h> 00065 #include <microsim/output/MSDetectorControl.h> 00066 #include <microsim/MSVehicleTransfer.h> 00067 #include "traffic_lights/MSTrafficLightLogic.h" 00068 #include <utils/shapes/Polygon.h> 00069 #include <utils/shapes/ShapeContainer.h> 00070 #include "output/MSXMLRawOut.h" 00071 #include <utils/iodevices/OutputDevice.h> 00072 #include <utils/common/SysUtils.h> 00073 #include <utils/common/WrappingCommand.h> 00074 #include <utils/options/OptionsCont.h> 00075 #include "MSGlobals.h" 00076 #include <utils/geom/GeoConvHelper.h> 00077 #include <ctime> 00078 #include "MSPerson.h" 00079 #include "MSEdgeWeightsStorage.h" 00080 00081 00082 #ifdef _MESSAGES 00083 #include "MSMessageEmitter.h" 00084 #endif 00085 00086 #ifdef HAVE_MESOSIM 00087 #include <mesosim/MELoop.h> 00088 #include <utils/iodevices/BinaryInputDevice.h> 00089 #endif 00090 00091 #ifndef NO_TRACI 00092 #include <traci-server/TraCIServer.h> 00093 #endif 00094 00095 #ifdef CHECK_MEMORY_LEAKS 00096 #include <foreign/nvwa/debug_new.h> 00097 #endif // CHECK_MEMORY_LEAKS 00098 00099 00100 // =========================================================================== 00101 // static member definitions 00102 // =========================================================================== 00103 MSNet* MSNet::myInstance = 0; 00104 00105 00106 // =========================================================================== 00107 // member method definitions 00108 // =========================================================================== 00109 // --------------------------------------------------------------------------- 00110 // MSNet::EdgeWeightsProxi - methods 00111 // --------------------------------------------------------------------------- 00112 SUMOReal 00113 MSNet::EdgeWeightsProxi::getEffort(const MSEdge* const e, 00114 const SUMOVehicle* const v, 00115 SUMOReal t) const { 00116 SUMOReal value; 00117 if (myVehicleKnowledge.retrieveExistingEffort(e, v, t, value)) { 00118 return value; 00119 } 00120 if (myNetKnowledge.retrieveExistingEffort(e, v, t, value)) { 00121 return value; 00122 } 00123 return 0; 00124 } 00125 00126 00127 SUMOReal 00128 MSNet::EdgeWeightsProxi::getTravelTime(const MSEdge* const e, 00129 const SUMOVehicle* const v, 00130 SUMOReal t) const { 00131 SUMOReal value; 00132 if (myVehicleKnowledge.retrieveExistingTravelTime(e, v, t, value)) { 00133 return value; 00134 } 00135 if (myNetKnowledge.retrieveExistingTravelTime(e, v, t, value)) { 00136 return value; 00137 } 00138 const MSLane* const l = e->getLanes()[0]; 00139 return l->getLength() / l->getMaxSpeed(); 00140 } 00141 00142 00143 00144 // --------------------------------------------------------------------------- 00145 // MSNet - methods 00146 // --------------------------------------------------------------------------- 00147 MSNet* 00148 MSNet::getInstance(void) { 00149 if (myInstance != 0) { 00150 return myInstance; 00151 } 00152 throw ProcessError("A network was not yet constructed."); 00153 } 00154 00155 00156 MSNet::MSNet(MSVehicleControl* vc, MSEventControl* beginOfTimestepEvents, 00157 MSEventControl* endOfTimestepEvents, MSEventControl* insertionEvents, 00158 ShapeContainer* shapeCont) { 00159 if (myInstance != 0) { 00160 throw ProcessError("A network was already constructed."); 00161 } 00162 OptionsCont& oc = OptionsCont::getOptions(); 00163 myStep = string2time(oc.getString("begin")); 00164 myLogExecutionTime = !oc.getBool("no-duration-log"); 00165 myLogStepNumber = !oc.getBool("no-step-log"); 00166 myTooManyVehicles = oc.getInt("max-num-vehicles"); 00167 myInserter = new MSInsertionControl(*vc, string2time(oc.getString("max-depart-delay")), oc.getBool("sloppy-insert")); 00168 myVehicleControl = vc; 00169 myDetectorControl = new MSDetectorControl(); 00170 myEdges = 0; 00171 myJunctions = 0; 00172 myRouteLoaders = 0; 00173 myLogics = 0; 00174 myPersonControl = 0; 00175 myEdgeWeights = 0; 00176 myShapeContainer = shapeCont == 0 ? new ShapeContainer() : shapeCont; 00177 00178 myBeginOfTimestepEvents = beginOfTimestepEvents; 00179 myEndOfTimestepEvents = endOfTimestepEvents; 00180 myInsertionEvents = insertionEvents; 00181 00182 #ifdef HAVE_MESOSIM 00183 if (MSGlobals::gUseMesoSim) { 00184 MSGlobals::gMesoNet = new MELoop(string2time(oc.getString("meso-recheck"))); 00185 } 00186 #endif 00187 myInstance = this; 00188 } 00189 00190 00191 00192 00193 void 00194 MSNet::closeBuilding(MSEdgeControl* edges, MSJunctionControl* junctions, 00195 MSRouteLoaderControl* routeLoaders, 00196 MSTLLogicControl* tlc, 00197 std::vector<SUMOTime> stateDumpTimes, 00198 std::vector<std::string> stateDumpFiles) { 00199 myEdges = edges; 00200 myJunctions = junctions; 00201 myRouteLoaders = routeLoaders; 00202 myLogics = tlc; 00203 // save the time the network state shall be saved at 00204 myStateDumpTimes = stateDumpTimes; 00205 myStateDumpFiles = stateDumpFiles; 00206 00207 // set requests/responses 00208 myJunctions->postloadInitContainer(); 00209 00210 // initialise performance computation 00211 if (myLogExecutionTime) { 00212 mySimBeginMillis = SysUtils::getCurrentMillis(); 00213 } 00214 } 00215 00216 00217 MSNet::~MSNet() { 00218 // delete events first maybe they do some cleanup 00219 delete myBeginOfTimestepEvents; 00220 delete myEndOfTimestepEvents; 00221 delete myInsertionEvents; 00222 // delete controls 00223 delete myJunctions; 00224 delete myDetectorControl; 00225 // delete mean data 00226 delete myEdges; 00227 delete myInserter; 00228 delete myLogics; 00229 delete myRouteLoaders; 00230 delete myVehicleControl; 00231 if (myPersonControl != 0) { 00232 delete myPersonControl; 00233 } 00234 delete myShapeContainer; 00235 #ifdef _MESSAGES 00236 myMsgEmitter.clear(); 00237 msgEmitVec.clear(); 00238 #endif 00239 delete myEdgeWeights; 00240 #ifdef HAVE_MESOSIM 00241 if (MSGlobals::gUseMesoSim) { 00242 delete MSGlobals::gMesoNet; 00243 } 00244 #endif 00245 clearAll(); 00246 myInstance = 0; 00247 } 00248 00249 00250 int 00251 MSNet::simulate(SUMOTime start, SUMOTime stop) { 00252 // report the begin when wished 00253 WRITE_MESSAGE("Simulation started with time: " + time2string(start)); 00254 // the simulation loop 00255 MSNet::SimulationState state = SIMSTATE_RUNNING; 00256 myStep = start; 00257 #ifndef NO_TRACI 00258 #ifdef HAVE_PYTHON 00259 if (OptionsCont::getOptions().isSet("python-script")) { 00260 traci::TraCIServer::runEmbedded(OptionsCont::getOptions().getString("python-script")); 00261 closeSimulation(start); 00262 WRITE_MESSAGE("Simulation ended at time: " + time2string(getCurrentTimeStep())); 00263 WRITE_MESSAGE("Reason: Script ended"); 00264 return 0; 00265 } 00266 #endif 00267 #endif 00268 while (state == SIMSTATE_RUNNING) { 00269 if (myLogStepNumber) { 00270 preSimStepOutput(); 00271 } 00272 simulationStep(); 00273 if (myLogStepNumber) { 00274 postSimStepOutput(); 00275 } 00276 state = simulationState(stop); 00277 #ifndef NO_TRACI 00278 if (state != SIMSTATE_RUNNING) { 00279 if (OptionsCont::getOptions().getInt("remote-port") != 0 && !traci::TraCIServer::wasClosed()) { 00280 state = SIMSTATE_RUNNING; 00281 } 00282 } 00283 #endif 00284 } 00285 // report the end when wished 00286 WRITE_MESSAGE("Simulation ended at time: " + time2string(getCurrentTimeStep())); 00287 WRITE_MESSAGE("Reason: " + getStateMessage(state)); 00288 // exit simulation loop 00289 closeSimulation(start); 00290 return 0; 00291 } 00292 00293 00294 void 00295 MSNet::closeSimulation(SUMOTime start) { 00296 if (myLogExecutionTime) { 00297 long duration = SysUtils::getCurrentMillis() - mySimBeginMillis; 00298 std::ostringstream msg; 00299 msg << "Performance: " << "\n" << " Duration: " << duration << " ms" << "\n"; 00300 if (duration != 0) { 00301 msg << " Real time factor: " << (STEPS2TIME(myStep - start) * 1000. / (SUMOReal)duration) << "\n"; 00302 msg.setf(std::ios::fixed , std::ios::floatfield); // use decimal format 00303 msg.setf(std::ios::showpoint); // print decimal point 00304 msg << " UPS: " << ((SUMOReal) myVehiclesMoved * 1000. / (SUMOReal) duration) << "\n"; 00305 } 00306 const std::string scaleNotice = ((myVehicleControl->getLoadedVehicleNo() != myVehicleControl->getDepartedVehicleNo()) ? 00307 " (Loaded: " + toString(myVehicleControl->getLoadedVehicleNo()) + ")" : ""); 00308 msg << "Vehicles: " << "\n" 00309 << " Emitted: " << myVehicleControl->getDepartedVehicleNo() << scaleNotice << "\n" 00310 << " Running: " << myVehicleControl->getRunningVehicleNo() << "\n" 00311 << " Waiting: " << myInserter->getWaitingVehicleNo() << "\n"; 00312 WRITE_MESSAGE(msg.str()); 00313 } 00314 myDetectorControl->close(myStep); 00315 #ifndef NO_TRACI 00316 traci::TraCIServer::close(); 00317 #endif 00318 } 00319 00320 00321 void 00322 MSNet::simulationStep() { 00323 #ifndef NO_TRACI 00324 traci::TraCIServer::processCommandsUntilSimStep(myStep); 00325 #endif 00326 // execute beginOfTimestepEvents 00327 if (myLogExecutionTime) { 00328 mySimStepBegin = SysUtils::getCurrentMillis(); 00329 } 00330 #ifdef HAVE_MESOSIM 00331 // netstate output 00332 std::vector<SUMOTime>::iterator timeIt = find(myStateDumpTimes.begin(), myStateDumpTimes.end(), myStep); 00333 if (timeIt != myStateDumpTimes.end()) { 00334 const int dist = distance(myStateDumpTimes.begin(), timeIt); 00335 std::ofstream strm(myStateDumpFiles[dist].c_str(), std::fstream::out | std::fstream::binary); 00336 saveState(strm); 00337 } 00338 #endif 00339 myBeginOfTimestepEvents->execute(myStep); 00340 if (MSGlobals::gCheck4Accidents) { 00341 myEdges->detectCollisions(myStep); 00342 } 00343 // check whether the tls programs need to be switched 00344 myLogics->check2Switch(myStep); 00345 // set the signals 00346 myLogics->setTrafficLightSignals(myStep); 00347 00348 #ifdef HAVE_MESOSIM 00349 if (MSGlobals::gUseMesoSim) { 00350 MSGlobals::gMesoNet->simulate(myStep); 00351 } else { 00352 #endif 00353 00354 // assure all lanes with vehicles are 'active' 00355 myEdges->patchActiveLanes(); 00356 00357 // move vehicles 00358 // precompute possible positions for vehicles that do interact with 00359 // their lane's end 00360 myEdges->moveCritical(myStep); 00361 00362 // move vehicles which do interact with their lane's end 00363 // (it is now known whether they may drive 00364 myEdges->moveFirst(myStep); 00365 if (MSGlobals::gCheck4Accidents) { 00366 myEdges->detectCollisions(myStep); 00367 } 00368 00369 // Vehicles change Lanes (maybe) 00370 myEdges->changeLanes(myStep); 00371 00372 if (MSGlobals::gCheck4Accidents) { 00373 myEdges->detectCollisions(myStep); 00374 } 00375 #ifdef HAVE_MESOSIM 00376 } 00377 #endif 00378 // load routes 00379 myRouteLoaders->loadNext(myStep); 00380 00381 // persons 00382 if (myPersonControl != 0) { 00383 myPersonControl->checkArrivedPersons(this, myStep); 00384 } 00385 // emit Vehicles 00386 myInsertionEvents->execute(myStep); 00387 myInserter->emitVehicles(myStep); 00388 if (MSGlobals::gCheck4Accidents) { 00389 myEdges->detectCollisions(myStep); 00390 } 00391 MSVehicleTransfer::getInstance()->checkInsertions(myStep); 00392 00393 // execute endOfTimestepEvents 00394 myEndOfTimestepEvents->execute(myStep); 00395 00396 // update and write (if needed) detector values 00397 writeOutput(); 00398 00399 if (myLogExecutionTime) { 00400 mySimStepEnd = SysUtils::getCurrentMillis(); 00401 mySimStepDuration = mySimStepEnd - mySimStepBegin; 00402 myVehiclesMoved += myVehicleControl->getRunningVehicleNo(); 00403 } 00404 myStep += DELTA_T; 00405 } 00406 00407 00408 MSNet::SimulationState 00409 MSNet::simulationState(SUMOTime stopTime) const { 00410 if (myTooManyVehicles > 0 && (int) myVehicleControl->getRunningVehicleNo() > myTooManyVehicles) { 00411 return SIMSTATE_TOO_MANY_VEHICLES; 00412 } 00413 #ifndef NO_TRACI 00414 if (traci::TraCIServer::wasClosed()) { 00415 return SIMSTATE_CONNECTION_CLOSED; 00416 } 00417 if (stopTime < 0 && OptionsCont::getOptions().getInt("remote-port") == 0) { 00418 #else 00419 if (stopTime < 0) { 00420 #endif 00421 if (myInsertionEvents->isEmpty() 00422 && (myVehicleControl->getActiveVehicleCount() == 0) 00423 && (myInserter->getPendingFlowCount() == 0) 00424 && (myPersonControl == 0 || !myPersonControl->hasPedestrians())) { 00425 if (myPersonControl) { 00426 myPersonControl->abortWaiting(); 00427 } 00428 myVehicleControl->abortWaiting(); 00429 return SIMSTATE_NO_FURTHER_VEHICLES; 00430 } 00431 } 00432 if (stopTime >= 0 && myStep >= stopTime) { 00433 return SIMSTATE_END_STEP_REACHED; 00434 } 00435 return SIMSTATE_RUNNING; 00436 } 00437 00438 00439 std::string 00440 MSNet::getStateMessage(MSNet::SimulationState state) { 00441 switch (state) { 00442 case MSNet::SIMSTATE_RUNNING: 00443 return ""; 00444 case MSNet::SIMSTATE_END_STEP_REACHED: 00445 return "The final simulation step has been reached."; 00446 case MSNet::SIMSTATE_NO_FURTHER_VEHICLES: 00447 return "All vehicles have left the simulation."; 00448 case MSNet::SIMSTATE_CONNECTION_CLOSED: 00449 return "TraCI requested termination."; 00450 case MSNet::SIMSTATE_ERROR_IN_SIM: 00451 return "An error occured (see log)."; 00452 case MSNet::SIMSTATE_TOO_MANY_VEHICLES: 00453 return "Too many vehicles."; 00454 default: 00455 return "Unknown reason."; 00456 } 00457 } 00458 00459 00460 void 00461 MSNet::clearAll() { 00462 // clear container 00463 MSEdge::clear(); 00464 MSLane::clear(); 00465 MSRoute::clear(); 00466 delete MSVehicleTransfer::getInstance(); 00467 } 00468 00469 00470 SUMOTime 00471 MSNet::getCurrentTimeStep() const { 00472 return myStep; 00473 } 00474 00475 00476 void 00477 MSNet::writeOutput() { 00478 // update detector values 00479 myDetectorControl->updateDetectors(myStep); 00480 // check state dumps 00481 if (OptionsCont::getOptions().isSet("netstate-dump")) { 00482 MSXMLRawOut::write(OutputDevice::getDeviceByOption("netstate-dump"), *myEdges, myStep); 00483 } 00484 // emission output 00485 if (OptionsCont::getOptions().isSet("summary-output")) { 00486 OutputDevice& od = OutputDevice::getDeviceByOption("summary"); 00487 od << " <step time=\"" << time2string(myStep) << "\" " 00488 << "loaded=\"" << myVehicleControl->getLoadedVehicleNo() << "\" " 00489 << "emitted=\"" << myVehicleControl->getDepartedVehicleNo() << "\" " 00490 << "running=\"" << myVehicleControl->getRunningVehicleNo() << "\" " 00491 << "waiting=\"" << myInserter->getWaitingVehicleNo() << "\" " 00492 << "ended=\"" << myVehicleControl->getEndedVehicleNo() << "\" " 00493 << "meanWaitingTime=\""; 00494 myVehicleControl->printMeanWaitingTime(od); 00495 od << "\" meanTravelTime=\""; 00496 myVehicleControl->printMeanTravelTime(od); 00497 od << "\" "; 00498 if (myLogExecutionTime) { 00499 od << "duration=\"" << mySimStepDuration << "\" "; 00500 } 00501 od << "/>\n"; 00502 } 00503 // write detector values 00504 myDetectorControl->writeOutput(myStep + DELTA_T, false); 00505 } 00506 00507 00508 bool 00509 MSNet::logSimulationDuration() const { 00510 return myLogExecutionTime; 00511 } 00512 00513 00514 #ifdef HAVE_MESOSIM 00515 void 00516 MSNet::saveState(std::ostream& os) { 00517 FileHelpers::writeString(os, VERSION_STRING); 00518 FileHelpers::writeUInt(os, sizeof(size_t)); 00519 FileHelpers::writeUInt(os, sizeof(SUMOReal)); 00520 FileHelpers::writeUInt(os, MSEdge::dictSize()); 00521 FileHelpers::writeUInt(os, myStep); 00522 MSRoute::dict_saveState(os); 00523 myVehicleControl->saveState(os); 00524 if (MSGlobals::gUseMesoSim) { 00525 MSGlobals::gMesoNet->saveState(os); 00526 } 00527 } 00528 00529 00530 unsigned int 00531 MSNet::loadState(BinaryInputDevice& bis) { 00532 std::string version; 00533 unsigned int sizeT, fpSize, numEdges, step; 00534 bis >> version; 00535 bis >> sizeT; 00536 bis >> fpSize; 00537 bis >> numEdges; 00538 bis >> step; 00539 if (version != VERSION_STRING) { 00540 WRITE_WARNING("State was written with sumo version " + version + " (present: " + VERSION_STRING + ")!"); 00541 } 00542 if (sizeT != sizeof(size_t)) { 00543 WRITE_WARNING("State was written on a different platform (32bit vs. 64bit)!"); 00544 } 00545 if (fpSize != sizeof(SUMOReal)) { 00546 WRITE_WARNING("State was written with a different precision for SUMOReal!"); 00547 } 00548 if (numEdges != MSEdge::dictSize()) { 00549 WRITE_WARNING("State was written for a different net!"); 00550 } 00551 const SUMOTime offset = string2time(OptionsCont::getOptions().getString("load-state.offset")); 00552 MSRoute::dict_loadState(bis); 00553 myVehicleControl->loadState(bis, offset); 00554 if (MSGlobals::gUseMesoSim) { 00555 MSGlobals::gMesoNet->loadState(bis, *myVehicleControl, offset); 00556 } 00557 return step; 00558 } 00559 #endif 00560 00561 00562 MSPersonControl& 00563 MSNet::getPersonControl() { 00564 if (myPersonControl == 0) { 00565 myPersonControl = new MSPersonControl(); 00566 } 00567 return *myPersonControl; 00568 } 00569 00570 00571 MSEdgeWeightsStorage& 00572 MSNet::getWeightsStorage() { 00573 if (myEdgeWeights == 0) { 00574 myEdgeWeights = new MSEdgeWeightsStorage(); 00575 } 00576 return *myEdgeWeights; 00577 } 00578 00579 00580 void 00581 MSNet::preSimStepOutput() const { 00582 std::cout << "Step #" << time2string(myStep); 00583 } 00584 00585 00586 void 00587 MSNet::postSimStepOutput() const { 00588 if (myLogExecutionTime) { 00589 std::ostringstream oss; 00590 oss.setf(std::ios::fixed , std::ios::floatfield); // use decimal format 00591 oss.setf(std::ios::showpoint); // print decimal point 00592 oss << std::setprecision(OUTPUT_ACCURACY); 00593 if (mySimStepDuration != 0) { 00594 oss << " (" << mySimStepDuration << "ms ~= " 00595 << (1000. / (SUMOReal) mySimStepDuration) << "*RT, ~" 00596 << ((SUMOReal) myVehicleControl->getRunningVehicleNo() / (SUMOReal) mySimStepDuration * 1000.); 00597 } else { 00598 oss << " (0ms ?*RT. ?"; 00599 } 00600 oss << "UPS, vehicles" 00601 << " TOT " << myVehicleControl->getDepartedVehicleNo() 00602 << " ACT " << myVehicleControl->getRunningVehicleNo() 00603 << ") "; 00604 std::string prev = "Step #" + time2string(myStep - DELTA_T); 00605 std::cout << oss.str().substr(0, 78 - prev.length()); 00606 } 00607 std::cout << '\r'; 00608 } 00609 00610 00611 void 00612 MSNet::addVehicleStateListener(VehicleStateListener* listener) { 00613 if (find(myVehicleStateListeners.begin(), myVehicleStateListeners.end(), listener) == myVehicleStateListeners.end()) { 00614 myVehicleStateListeners.push_back(listener); 00615 } 00616 } 00617 00618 00619 void 00620 MSNet::removeVehicleStateListener(VehicleStateListener* listener) { 00621 std::vector<VehicleStateListener*>::iterator i = find(myVehicleStateListeners.begin(), myVehicleStateListeners.end(), listener); 00622 if (i != myVehicleStateListeners.end()) { 00623 myVehicleStateListeners.erase(i); 00624 } 00625 } 00626 00627 00628 void 00629 MSNet::informVehicleStateListener(const SUMOVehicle* const vehicle, VehicleState to) { 00630 for (std::vector<VehicleStateListener*>::iterator i = myVehicleStateListeners.begin(); i != myVehicleStateListeners.end(); ++i) { 00631 (*i)->vehicleStateChanged(vehicle, to); 00632 } 00633 } 00634 00635 00636 00637 // ------ Insertion and retrieval of bus stops ------ 00638 bool 00639 MSNet::addBusStop(MSBusStop* busStop) { 00640 return myBusStopDict.add(busStop->getID(), busStop); 00641 } 00642 00643 00644 MSBusStop* 00645 MSNet::getBusStop(const std::string& id) const { 00646 return myBusStopDict.get(id); 00647 } 00648 00649 00650 std::string 00651 MSNet::getBusStopID(const MSLane* lane, const SUMOReal pos) const { 00652 const std::map<std::string, MSBusStop*> &vals = myBusStopDict.getMyMap(); 00653 for (std::map<std::string, MSBusStop*>::const_iterator it = vals.begin(); it != vals.end(); ++it) { 00654 MSBusStop* stop = it->second; 00655 if (&stop->getLane() == lane && fabs(stop->getEndLanePosition() - pos) < POSITION_EPS) { 00656 return stop->getID(); 00657 } 00658 } 00659 return ""; 00660 } 00661 00662 00663 #ifdef _MESSAGES 00664 MSMessageEmitter* 00665 MSNet::getMsgEmitter(const std::string& whatemit) { 00666 msgEmitVec.clear(); 00667 msgEmitVec = myMsgEmitter.buildAndGetStaticVector(); 00668 MSMessageEmitter* msgEmitter = 0; 00669 for (int i = 0; i < msgEmitVec.size(); ++i) { 00670 if (msgEmitVec.at(i)->getEventsEnabled(whatemit)) { 00671 msgEmitter = msgEmitVec.at(i); 00672 break; 00673 } 00674 } 00675 // returns 0 if the requested MessageEmitter is not in the map 00676 return msgEmitter; 00677 } 00678 00679 00680 void 00681 MSNet::createMsgEmitter(std::string& id, 00682 std::string& file, 00683 const std::string& base, 00684 std::string& whatemit, 00685 bool reverse, 00686 bool table, 00687 bool xy, 00688 SUMOReal step) { 00689 MSMessageEmitter* msgEmitter = new MSMessageEmitter(file, base, whatemit, reverse, table, xy, step); 00690 myMsgEmitter.add(id, msgEmitter); 00691 } 00692 #endif 00693 00694 00695 /****************************************************************************/ 00696