LCOV - code coverage report
Current view: top level - src/microsim - MSVehicleControl.cpp (source / functions) Coverage Total Hit
Test: lcov.info Lines: 97.6 % 295 288
Test Date: 2026-04-16 16:39:47 Functions: 97.2 % 36 35

            Line data    Source code
       1              : /****************************************************************************/
       2              : // Eclipse SUMO, Simulation of Urban MObility; see https://eclipse.dev/sumo
       3              : // Copyright (C) 2001-2026 German Aerospace Center (DLR) and others.
       4              : // This program and the accompanying materials are made available under the
       5              : // terms of the Eclipse Public License 2.0 which is available at
       6              : // https://www.eclipse.org/legal/epl-2.0/
       7              : // This Source Code may also be made available under the following Secondary
       8              : // Licenses when the conditions for such availability set forth in the Eclipse
       9              : // Public License 2.0 are satisfied: GNU General Public License, version 2
      10              : // or later which is available at
      11              : // https://www.gnu.org/licenses/old-licenses/gpl-2.0-standalone.html
      12              : // SPDX-License-Identifier: EPL-2.0 OR GPL-2.0-or-later
      13              : /****************************************************************************/
      14              : /// @file    MSVehicleControl.cpp
      15              : /// @author  Daniel Krajzewicz
      16              : /// @author  Jakob Erdmann
      17              : /// @author  Michael Behrisch
      18              : /// @date    Wed, 10. Dec 2003
      19              : ///
      20              : // The class responsible for building and deletion of vehicles
      21              : /****************************************************************************/
      22              : #include <config.h>
      23              : 
      24              : #include "MSVehicleControl.h"
      25              : #include "MSVehicle.h"
      26              : #include "MSLane.h"
      27              : #include "MSEdge.h"
      28              : #include "MSNet.h"
      29              : #include "MSRouteHandler.h"
      30              : #include "MSEventControl.h"
      31              : #include "MSStop.h"
      32              : #include <microsim/devices/MSVehicleDevice.h>
      33              : #include <microsim/devices/MSDevice_Tripinfo.h>
      34              : #include <utils/common/FileHelpers.h>
      35              : #include <utils/common/Named.h>
      36              : #include <utils/common/RGBColor.h>
      37              : #include <utils/vehicle/SUMOVTypeParameter.h>
      38              : #include <utils/iodevices/OutputDevice.h>
      39              : #include <utils/options/OptionsCont.h>
      40              : #include <utils/router/IntermodalRouter.h>
      41              : 
      42              : 
      43              : // ===========================================================================
      44              : // member method definitions
      45              : // ===========================================================================
      46        41790 : MSVehicleControl::MSVehicleControl() :
      47        41790 :     myLoadedVehNo(0),
      48        41790 :     myRunningVehNo(0),
      49        41790 :     myEndedVehNo(0),
      50        41790 :     myDiscarded(0),
      51        41790 :     myCollisions(0),
      52        41790 :     myTeleportsCollision(0),
      53        41790 :     myTeleportsJam(0),
      54        41790 :     myTeleportsYield(0),
      55        41790 :     myTeleportsWrongLane(0),
      56        41790 :     myEmergencyStops(0),
      57        41790 :     myEmergencyBrakingCount(0),
      58        41790 :     myStoppedVehicles(0),
      59        41790 :     myTotalDepartureDelay(0),
      60        41790 :     myTotalTravelTime(0),
      61        41790 :     myWaitingForTransportable(0),
      62        41790 :     myMaxSpeedFactor(1),
      63        41790 :     myMinDeceleration(SUMOVTypeParameter::getDefaultDecel(SVC_IGNORING)),
      64        41790 :     myMinDecelerationRail(SUMOVTypeParameter::getDefaultDecel(SVC_RAIL)),
      65        83580 :     myPendingRemovals(MSGlobals::gNumSimThreads > 1) {
      66              : 
      67        41790 :     initDefaultTypes();
      68        41790 :     myScale = OptionsCont::getOptions().getFloat("scale");
      69        41790 :     myKeepTime = string2time(OptionsCont::getOptions().getString("keep-after-arrival"));
      70        41790 : }
      71              : 
      72              : 
      73        70245 : MSVehicleControl::~MSVehicleControl() {
      74        41176 :     clearState(false);
      75        70245 : }
      76              : 
      77              : 
      78              : void
      79        41958 : MSVehicleControl::initDefaultTypes() {
      80        41958 :     SUMOVTypeParameter defType(DEFAULT_VTYPE_ID, SVC_PASSENGER);
      81        41958 :     myVTypeDict[DEFAULT_VTYPE_ID] = MSVehicleType::build(defType);
      82              : 
      83        41958 :     SUMOVTypeParameter defPedType(DEFAULT_PEDTYPE_ID, SVC_PEDESTRIAN);
      84        41958 :     defPedType.parametersSet |= VTYPEPARS_VEHICLECLASS_SET;
      85        41958 :     myVTypeDict[DEFAULT_PEDTYPE_ID] = MSVehicleType::build(defPedType);
      86              : 
      87        41958 :     SUMOVTypeParameter defBikeType(DEFAULT_BIKETYPE_ID, SVC_BICYCLE);
      88        41958 :     defBikeType.parametersSet |= VTYPEPARS_VEHICLECLASS_SET;
      89        41958 :     myVTypeDict[DEFAULT_BIKETYPE_ID] = MSVehicleType::build(defBikeType);
      90              : 
      91        41958 :     SUMOVTypeParameter defTaxiType(DEFAULT_TAXITYPE_ID, SVC_TAXI);
      92        41958 :     defTaxiType.parametersSet |= VTYPEPARS_VEHICLECLASS_SET;
      93        41958 :     myVTypeDict[DEFAULT_TAXITYPE_ID] = MSVehicleType::build(defTaxiType);
      94              : 
      95        41958 :     SUMOVTypeParameter defRailType(DEFAULT_RAILTYPE_ID, SVC_RAIL);
      96        41958 :     defRailType.parametersSet |= VTYPEPARS_VEHICLECLASS_SET;
      97        41958 :     myVTypeDict[DEFAULT_RAILTYPE_ID] = MSVehicleType::build(defRailType);
      98              : 
      99        41958 :     SUMOVTypeParameter defContainerType(DEFAULT_CONTAINERTYPE_ID, SVC_CONTAINER);
     100        41958 :     defContainerType.parametersSet |= VTYPEPARS_VEHICLECLASS_SET;
     101        41958 :     myVTypeDict[DEFAULT_CONTAINERTYPE_ID] = MSVehicleType::build(defContainerType);
     102              : 
     103              :     myReplaceableDefaultVTypes = DEFAULT_VTYPES;
     104        41958 : }
     105              : 
     106              : 
     107              : SUMOVehicle*
     108      3848288 : MSVehicleControl::buildVehicle(SUMOVehicleParameter* defs,
     109              :                                ConstMSRoutePtr route, MSVehicleType* type,
     110              :                                const bool ignoreStopErrors, const VehicleDefinitionSource source, bool addRouteStops) {
     111      3848288 :     const double speedFactor = (source == VehicleDefinitionSource::STATE ? 1 :
     112      3947246 :                                 type->computeChosenSpeedDeviation(source == VehicleDefinitionSource::ROUTEFILE ? MSRouteHandler::getParsingRNG() : nullptr));
     113      7696576 :     MSVehicle* built = new MSVehicle(defs, route, type, speedFactor);
     114      3848288 :     initVehicle(built, ignoreStopErrors, addRouteStops, source);
     115      3848232 :     return built;
     116              : }
     117              : 
     118              : 
     119              : void
     120      5255349 : MSVehicleControl::initVehicle(MSBaseVehicle* built, const bool ignoreStopErrors, bool addRouteStops, const VehicleDefinitionSource source) {
     121      5255349 :     myLoadedVehNo++;
     122              :     try {
     123      5255349 :         built->initDevices();
     124      5255310 :         if (source != VehicleDefinitionSource::STATE) {
     125      5250661 :             built->addStops(ignoreStopErrors, nullptr, addRouteStops);
     126              :         }
     127          116 :     } catch (ProcessError&) {
     128          116 :         delete built;
     129          116 :         throw;
     130          116 :     }
     131      5255232 :     MSNet::getInstance()->informVehicleStateListener(built, MSNet::VehicleState::BUILT);
     132      5255232 : }
     133              : 
     134              : 
     135              : void
     136      4019499 : MSVehicleControl::scheduleVehicleRemoval(SUMOVehicle* veh, bool checkDuplicate) {
     137              :     assert(myRunningVehNo > 0);
     138      4019499 :     if (!checkDuplicate || !isPendingRemoval(veh)) {
     139      4019499 :         myPendingRemovals.push_back(veh);
     140              :     }
     141      4019499 : }
     142              : 
     143              : 
     144              : bool
     145        17549 : MSVehicleControl::isPendingRemoval(SUMOVehicle* veh) {
     146              : #ifdef HAVE_FOX
     147        17549 :     return myPendingRemovals.contains(veh);
     148              : #else
     149              :     return std::find(myPendingRemovals.begin(), myPendingRemovals.end(), veh) == myPendingRemovals.end();
     150              : #endif
     151              : }
     152              : 
     153              : 
     154              : void
     155     96925457 : MSVehicleControl::removePending() {
     156    113737782 :     OutputDevice* const tripinfoOut = OptionsCont::getOptions().isSet("tripinfo-output") ? &OutputDevice::getDeviceByOption("tripinfo-output") : nullptr;
     157              : #ifdef HAVE_FOX
     158              :     std::vector<SUMOVehicle*>& vehs = myPendingRemovals.getContainer();
     159              : #else
     160              :     std::vector<SUMOVehicle*>& vehs = myPendingRemovals;
     161              : #endif
     162     96925457 :     std::sort(vehs.begin(), vehs.end(), ComparatorNumericalIdLess());
     163    100944952 :     for (SUMOVehicle* const veh : vehs) {
     164      4019495 :         myTotalTravelTime += STEPS2TIME(MSNet::getInstance()->getCurrentTimeStep() - veh->getDeparture());
     165      4019495 :         myRunningVehNo--;
     166      4019495 :         MSNet::getInstance()->informVehicleStateListener(veh, MSNet::VehicleState::ARRIVED);
     167              :         // vehicle is equipped with tripinfo device (not all vehicles are)
     168      4019495 :         const bool hasTripinfo = veh->getDevice(typeid(MSDevice_Tripinfo)) != nullptr;
     169      7088391 :         for (MSVehicleDevice* const dev : veh->getDevices()) {
     170      3785327 :             dev->generateOutput(hasTripinfo ? tripinfoOut : nullptr);
     171              :         }
     172      4019495 :         if (tripinfoOut != nullptr && hasTripinfo) {
     173              :             // close tag after tripinfo (possibly including emissions from another device) have been written
     174       473696 :             tripinfoOut->closeTag();
     175              :         }
     176      4019495 :         if (myKeepTime == 0) {
     177      4019483 :             deleteVehicle(veh);
     178              :         } else {
     179           12 :             deleteKeptVehicle(veh);
     180              :         }
     181              :     }
     182              :     vehs.clear();
     183     96925457 :     if (tripinfoOut != nullptr) {
     184              :         // there seem to be people who think reading an unfinished xml is a good idea ;-)
     185              :         tripinfoOut->flush();
     186              :     }
     187              : #ifdef HAVE_FOX
     188              :     myPendingRemovals.unlock();
     189              : #endif
     190     96925457 : }
     191              : 
     192              : 
     193              : void
     194           15 : MSVehicleControl::deleteKeptVehicle(SUMOVehicle* veh) {
     195           15 :     myEndedVehNo++;
     196           15 :     MSNet::getInstance()->getEndOfTimestepEvents()->addEvent(new DeleteKeptVehicle(veh), SIMSTEP + myKeepTime);
     197           15 : }
     198              : 
     199              : void
     200      4167564 : MSVehicleControl::vehicleDeparted(const SUMOVehicle& v) {
     201      4167564 :     ++myRunningVehNo;
     202      4167564 :     myTotalDepartureDelay += STEPS2TIME(v.getDeparture() - STEPFLOOR(v.getParameter().depart));
     203      4167564 :     MSNet::getInstance()->informVehicleStateListener(&v, MSNet::VehicleState::DEPARTED);
     204      4167564 :     myMaxSpeedFactor = MAX2(myMaxSpeedFactor, v.getChosenSpeedFactor());
     205      4167564 :     if ((v.getVClass() & (SVC_PEDESTRIAN | SVC_NON_ROAD)) == 0) {
     206              :         // only  worry about deceleration of road users
     207      8120116 :         myMinDeceleration = MIN2(myMinDeceleration, v.getVehicleType().getCarFollowModel().getMaxDecel());
     208         7845 :     } else if ((v.getVClass() & SVC_RAIL_CLASSES) != 0) {
     209        14017 :         myMinDecelerationRail = MIN2(myMinDecelerationRail, v.getVehicleType().getCarFollowModel().getMaxDecel());
     210              :     }
     211      4167564 : }
     212              : 
     213              : 
     214              : void
     215          422 : MSVehicleControl::setState(int runningVehNo, int loadedVehNo, int endedVehNo, double totalDepartureDelay, double totalTravelTime, double maxSpeedFactor, double minDecel) {
     216          422 :     myRunningVehNo = runningVehNo;
     217          422 :     myLoadedVehNo = loadedVehNo;
     218          422 :     myEndedVehNo = endedVehNo;
     219          422 :     myTotalDepartureDelay = totalDepartureDelay;
     220          422 :     myTotalTravelTime = totalTravelTime;
     221          422 :     myMaxSpeedFactor = maxSpeedFactor;
     222          422 :     myMinDeceleration = minDecel;
     223          422 : }
     224              : 
     225              : 
     226              : void
     227          496 : MSVehicleControl::saveState(OutputDevice& out) {
     228          496 :     out.openTag(SUMO_TAG_DELAY);
     229          496 :     out.writeAttr(SUMO_ATTR_NUMBER, myRunningVehNo);
     230          496 :     out.writeAttr(SUMO_ATTR_BEGIN, myLoadedVehNo);
     231          496 :     out.writeAttr(SUMO_ATTR_END, myEndedVehNo);
     232          496 :     out.writeAttr(SUMO_ATTR_DEPART, myTotalDepartureDelay);
     233          496 :     out.writeAttr(SUMO_ATTR_TIME, myTotalTravelTime);
     234          496 :     out.writeAttr(SUMO_ATTR_SPEEDFACTOR, myMaxSpeedFactor);
     235          496 :     out.writeAttr(SUMO_ATTR_DECEL, myMinDeceleration);
     236          992 :     out.closeTag();
     237              :     // save vehicle types
     238         4253 :     for (const auto& item : myVTypeDict) {
     239         3757 :         if (myReplaceableDefaultVTypes.count(item.first) == 0) {
     240         1014 :             item.second->getParameter().write(out);
     241              :         }
     242              :     }
     243          676 :     for (const auto& item : myVTypeDistDict) {
     244          180 :         out.openTag(SUMO_TAG_VTYPE_DISTRIBUTION).writeAttr(SUMO_ATTR_ID, item.first);
     245          180 :         out.writeAttr(SUMO_ATTR_VTYPES, item.second->getVals());
     246          180 :         out.writeAttr(SUMO_ATTR_PROBS, item.second->getProbs());
     247          360 :         out.closeTag();
     248              :     }
     249              :     std::vector<SUMOVehicle*> sortedVehs;
     250         4823 :     for (const auto& item : myVehicleDict) {
     251         4327 :         sortedVehs.push_back(item.second);
     252              :     }
     253          496 :     std::sort(sortedVehs.begin(), sortedVehs.end(), ComparatorNumericalIdLess());
     254         4823 :     for (SUMOVehicle* veh : sortedVehs) {
     255         4327 :         veh->saveState(out);
     256              :     }
     257          496 : }
     258              : 
     259              : 
     260              : void
     261        41344 : MSVehicleControl::clearState(const bool reinit) {
     262       352831 :     for (const auto& item : myVehicleDict) {
     263       311487 :         delete item.second;
     264              :     }
     265              :     myVehicleDict.clear();
     266              :     // delete vehicle type distributions
     267        41796 :     for (const auto& item : myVTypeDistDict) {
     268          904 :         delete item.second;
     269              :     }
     270              :     myVTypeDistDict.clear();
     271              :     // delete vehicle types
     272       340516 :     for (const auto& item : myVTypeDict) {
     273       299172 :         delete item.second;
     274              :     }
     275              :     myVTypeDict.clear();
     276        41344 :     myPendingRemovals.clear(); // could be leftovers from MSVehicleTransfer::checkInsertions (teleport beyond arrival)
     277        41344 :     if (reinit) {
     278          168 :         initDefaultTypes();
     279              :     }
     280        41344 :     myLoadedVehNo = 0;
     281        41344 :     myRunningVehNo = 0;
     282        41344 :     myEndedVehNo = 0;
     283        41344 :     myDiscarded = 0;
     284        41344 :     myCollisions = 0;
     285        41344 :     myTeleportsCollision = 0;
     286        41344 :     myTeleportsJam = 0;
     287        41344 :     myTeleportsYield = 0;
     288        41344 :     myTeleportsWrongLane = 0;
     289        41344 :     myEmergencyStops = 0;
     290        41344 :     myEmergencyBrakingCount = 0;
     291        41344 :     myStoppedVehicles = 0;
     292        41344 :     myTotalDepartureDelay = 0;
     293        41344 :     myTotalTravelTime = 0;
     294        41344 : }
     295              : 
     296              : 
     297              : bool
     298      5150133 : MSVehicleControl::addVehicle(const std::string& id, SUMOVehicle* v) {
     299              :     VehicleDictType::iterator it = myVehicleDict.find(id);
     300      5150133 :     if (it == myVehicleDict.end()) {
     301              :         // id not in myVehicleDict.
     302      5150133 :         myVehicleDict[id] = v;
     303      5150133 :         handleTriggeredDepart(v, true);
     304      5150133 :         const SUMOVehicleParameter& pars = v->getParameter();
     305      5150133 :         if (v->getVClass() != SVC_TAXI && pars.line != "" && pars.repetitionNumber < 0) {
     306         1117 :             myPTVehicles.push_back(v);
     307              :         }
     308      5150133 :         return true;
     309              :     }
     310              :     return false;
     311              : }
     312              : 
     313              : 
     314              : void
     315      5154461 : MSVehicleControl::handleTriggeredDepart(SUMOVehicle* v, bool add) {
     316      5154461 :     const SUMOVehicleParameter& pars = v->getParameter();
     317      5154461 :     if (pars.departProcedure == DepartDefinition::TRIGGERED || pars.departProcedure == DepartDefinition::CONTAINER_TRIGGERED || pars.departProcedure == DepartDefinition::SPLIT) {
     318         4212 :         const MSEdge* const firstEdge = v->getRoute().getEdges()[pars.departEdge];
     319         4212 :         if (add) {
     320         2171 :             if (!MSGlobals::gUseMesoSim) {
     321              :                 // position will be checked against person position later
     322         1793 :                 static_cast<MSVehicle*>(v)->setTentativeLaneAndPosition(nullptr, v->getParameter().departPos);
     323              :             }
     324         2171 :             if (firstEdge->isTazConnector()) {
     325           78 :                 for (MSEdge* out : firstEdge->getSuccessors()) {
     326           51 :                     out->addWaiting(v);
     327              :                 }
     328              :             } else {
     329         2144 :                 firstEdge->addWaiting(v);
     330              :             }
     331              :             registerOneWaiting();
     332              :         } else {
     333         2041 :             if (firstEdge->isTazConnector()) {
     334           14 :                 for (MSEdge* out : firstEdge->getSuccessors()) {
     335            7 :                     out->removeWaiting(v);
     336              :                 }
     337              :             } else {
     338         2034 :                 firstEdge->removeWaiting(v);
     339              :             }
     340              :             unregisterOneWaiting();
     341              :         }
     342              :     }
     343      5154461 : }
     344              : 
     345              : 
     346              : SUMOVehicle*
     347     22720425 : MSVehicleControl::getVehicle(const std::string& id) const {
     348              :     VehicleDictType::const_iterator it = myVehicleDict.find(id);
     349     22720425 :     if (it == myVehicleDict.end()) {
     350              :         return nullptr;
     351              :     }
     352     17379461 :     return it->second;
     353              : }
     354              : 
     355              : 
     356              : void
     357      4943659 : MSVehicleControl::deleteVehicle(SUMOVehicle* veh, bool discard, bool wasKept) {
     358      4943659 :     if (!wasKept) {
     359      4943647 :         myEndedVehNo++;
     360      4943647 :         if (discard) {
     361       924164 :             myDiscarded++;
     362              :         }
     363              :     }
     364      4943659 :     if (veh != nullptr) {
     365              :         myVehicleDict.erase(veh->getID());
     366              :     }
     367      4943659 :     auto ptVehIt = std::find(myPTVehicles.begin(), myPTVehicles.end(), veh);
     368      4943659 :     if (ptVehIt != myPTVehicles.end()) {
     369          941 :         myPTVehicles.erase(ptVehIt);
     370              :     }
     371      4943659 :     delete veh;
     372      4943659 : }
     373              : 
     374              : 
     375              : bool
     376        63208 : MSVehicleControl::checkVType(const std::string& id) {
     377        63208 :     if (myReplaceableDefaultVTypes.erase(id) > 0) {
     378         9867 :         delete myVTypeDict[id];
     379              :         myVTypeDict.erase(myVTypeDict.find(id));
     380              :     } else {
     381        53341 :         if (myVTypeDict.find(id) != myVTypeDict.end() || myVTypeDistDict.find(id) != myVTypeDistDict.end()) {
     382          181 :             return false;
     383              :         }
     384              :     }
     385              :     return true;
     386              : }
     387              : 
     388              : 
     389              : bool
     390        62756 : MSVehicleControl::addVType(MSVehicleType* vehType) {
     391        62756 :     if (checkVType(vehType->getID())) {
     392        62575 :         myVTypeDict[vehType->getID()] = vehType;
     393        62575 :         return true;
     394              :     }
     395              :     return false;
     396              : }
     397              : 
     398              : 
     399              : void
     400         1432 : MSVehicleControl::removeVType(const MSVehicleType* vehType) {
     401              :     assert(vehType != nullptr);
     402              :     assert(myVTypeDict.find(vehType->getID()) != myVTypeDict.end());
     403              :     myVTypeDict.erase(vehType->getID());
     404         1432 :     if (myVTypeToDist.find(vehType->getID()) != myVTypeToDist.end()) {
     405              :         myVTypeToDist.erase(vehType->getID());
     406              :     }
     407         1432 :     delete vehType;
     408         1432 : }
     409              : 
     410              : 
     411              : bool
     412          452 : MSVehicleControl::addVTypeDistribution(const std::string& id, RandomDistributor<MSVehicleType*>* vehTypeDistribution) {
     413          452 :     if (checkVType(id)) {
     414          452 :         myVTypeDistDict[id] = vehTypeDistribution;
     415          452 :         std::vector<MSVehicleType*> vehTypes = vehTypeDistribution->getVals();
     416         1688 :         for (auto vehType : vehTypes) {
     417         1236 :             if (myVTypeToDist.find(vehType->getID()) != myVTypeToDist.end()) {
     418           42 :                 myVTypeToDist[vehType->getID()].insert(id);
     419              :             } else {
     420         3582 :                 myVTypeToDist[vehType->getID()] = { id };
     421              :             }
     422              :         }
     423              :         return true;
     424          452 :     }
     425              :     return false;
     426              : }
     427              : 
     428              : 
     429              : bool
     430        46174 : MSVehicleControl::hasVType(const std::string& id) const {
     431        46174 :     return myVTypeDict.count(id) > 0 || myVTypeDistDict.count(id) > 0;
     432              : }
     433              : 
     434              : 
     435              : bool
     436        19148 : MSVehicleControl::hasVTypeDistribution(const std::string& id) const {
     437        19148 :     return myVTypeDistDict.count(id) > 0;
     438              : }
     439              : 
     440              : 
     441              : MSVehicleType*
     442      8107412 : MSVehicleControl::getVType(const std::string& id, SumoRNG* rng, bool readOnly) {
     443              :     VTypeDictType::iterator it = myVTypeDict.find(id);
     444      8107412 :     if (it == myVTypeDict.end()) {
     445              :         VTypeDistDictType::iterator it2 = myVTypeDistDict.find(id);
     446      2227394 :         if (it2 == myVTypeDistDict.end()) {
     447              :             return nullptr;
     448              :         }
     449        86239 :         return it2->second->get(rng);
     450              :     }
     451     11735970 :     if (!readOnly && myReplaceableDefaultVTypes.erase(id) > 0) {
     452        19856 :         it->second->check();
     453              :     }
     454      5880018 :     return it->second;
     455              : }
     456              : 
     457              : 
     458              : void
     459          311 : MSVehicleControl::insertVTypeIDs(std::vector<std::string>& into) const {
     460          311 :     into.reserve(into.size() + myVTypeDict.size() + myVTypeDistDict.size());
     461         2477 :     for (VTypeDictType::const_iterator i = myVTypeDict.begin(); i != myVTypeDict.end(); ++i) {
     462         2166 :         into.push_back((*i).first);
     463              :     }
     464          311 :     for (VTypeDistDictType::const_iterator i = myVTypeDistDict.begin(); i != myVTypeDistDict.end(); ++i) {
     465            0 :         into.push_back((*i).first);
     466              :     }
     467          311 : }
     468              : 
     469              : 
     470              : const std::set<std::string>
     471       149575 : MSVehicleControl::getVTypeDistributionMembership(const std::string& id) const {
     472              :     std::map<std::string, std::set<std::string>>::const_iterator it = myVTypeToDist.find(id);
     473       149575 :     if (it == myVTypeToDist.end()) {
     474        60114 :         return std::set<std::string>();
     475              :     }
     476              :     return it->second;
     477              : }
     478              : 
     479              : 
     480              : const RandomDistributor<MSVehicleType*>*
     481       135263 : MSVehicleControl::getVTypeDistribution(const std::string& typeDistID) const {
     482              :     const auto it = myVTypeDistDict.find(typeDistID);
     483       135263 :     if (it != myVTypeDistDict.end()) {
     484         2202 :         return it->second;
     485              :     }
     486              :     return nullptr;
     487              : }
     488              : 
     489              : 
     490              : const std::vector<MSVehicleType*>
     491            0 : MSVehicleControl::getPedestrianTypes(void) const {
     492              :     std::vector<MSVehicleType*> pedestrianTypes;
     493            0 :     for (auto const& e : myVTypeDict)
     494            0 :         if (e.second->getVehicleClass() == SUMOVehicleClass::SVC_PEDESTRIAN) {
     495            0 :             pedestrianTypes.push_back(e.second);
     496              :         }
     497            0 :     return pedestrianTypes;
     498            0 : }
     499              : 
     500              : 
     501              : void
     502        27757 : MSVehicleControl::abortWaiting() {
     503        29676 :     for (VehicleDictType::iterator i = myVehicleDict.begin(); i != myVehicleDict.end(); ++i) {
     504         1919 :         SUMOVehicle* veh = i->second;
     505              :         std::string waitReason;
     506         1919 :         if (veh->isStoppedTriggered()) {
     507         1845 :             const MSStop& stop = veh->getNextStop();
     508         1845 :             if (stop.triggered) {
     509              :                 waitReason = "for a person that will never come";
     510          124 :             } else if (stop.containerTriggered) {
     511              :                 waitReason = "for a container that will never come";
     512           36 :             } else if (stop.joinTriggered) {
     513           36 :                 if (stop.pars.join != "") {
     514           48 :                     waitReason = "to be joined to vehicle '" + stop.pars.join + "'";
     515              :                 } else {
     516              :                     waitReason = "for a joining vehicle that will never come";
     517              :                 }
     518              :             } else {
     519              :                 waitReason = "for an unknown trigger";
     520              :             }
     521           74 :         } else if (!veh->hasDeparted()) {
     522           74 :             if (veh->getParameter().departProcedure == DepartDefinition::SPLIT) {
     523              :                 waitReason = "for a train from which to split";
     524           58 :             } else if (veh->getParameter().departProcedure == DepartDefinition::TRIGGERED) {
     525              :                 waitReason = "at insertion for a person that will never come";
     526           22 :             } else if (veh->getParameter().departProcedure == DepartDefinition::CONTAINER_TRIGGERED) {
     527              :                 waitReason = "at insertion for a container that will never come";
     528              :             } else {
     529              :                 waitReason = "for an unknown departure trigger";
     530              :             }
     531              :         } else {
     532              :             waitReason = "for an unknown reason";
     533              :         }
     534         5757 :         WRITE_WARNINGF(TL("Vehicle '%' aborted waiting %."), i->first, waitReason);
     535              :     }
     536        27757 : }
     537              : 
     538              : 
     539              : int
     540       522721 : MSVehicleControl::getHaltingVehicleNo() const {
     541              :     int result = 0;
     542     75575773 :     for (MSVehicleControl::constVehIt it = loadedVehBegin(); it != loadedVehEnd(); ++it) {
     543     75053052 :         const SUMOVehicle* veh = it->second;
     544     75053052 :         if ((veh->isOnRoad() || veh->isRemoteControlled()) && veh->getSpeed() < SUMO_const_haltingSpeed)  {
     545     18905441 :             result++;
     546              :         }
     547              :     }
     548       522721 :     return result;
     549              : }
     550              : 
     551              : 
     552              : std::pair<double, double>
     553       522721 : MSVehicleControl::getVehicleMeanSpeeds() const {
     554              :     double speedSum = 0;
     555              :     double relSpeedSum = 0;
     556              :     int count = 0;
     557     75575773 :     for (MSVehicleControl::constVehIt it = loadedVehBegin(); it != loadedVehEnd(); ++it) {
     558     75053052 :         const SUMOVehicle* veh = it->second;
     559     75053052 :         if ((veh->isOnRoad() || veh->isRemoteControlled()) && !veh->isStopped()) {
     560     42243186 :             count++;
     561     42243186 :             speedSum += veh->getSpeed();
     562     42243186 :             relSpeedSum += veh->getEdge()->getSpeedLimit() > 0 ? veh->getSpeed() / veh->getEdge()->getSpeedLimit() : 0;
     563              :         }
     564              :     }
     565       522721 :     if (count > 0) {
     566       427718 :         return std::make_pair(speedSum / count, relSpeedSum / count);
     567              :     } else {
     568        95003 :         return std::make_pair(-1, -1);
     569              :     }
     570              : }
     571              : 
     572              : 
     573              : int
     574      1325135 : MSVehicleControl::getQuota(double frac, int loaded) const {
     575      1325135 :     frac = frac < 0 ? myScale : frac;
     576              :     const int origLoaded = (loaded < 1
     577              :                             // the vehicle in question has already been loaded, hence  the '-1'
     578      1325135 :                             ? frac > 1. ? (int)(myLoadedVehNo / frac) : myLoadedVehNo - 1
     579              :                             // given transportable number reflects only previously loaded
     580       459116 :                             : frac > 1. ? (int)(loaded / frac) : loaded);
     581      1325135 :     return getScalingQuota(frac, origLoaded);
     582              : }
     583              : 
     584              : 
     585              : int
     586       552000 : MSVehicleControl::getTeleportCount() const {
     587       552000 :     return myTeleportsCollision + myTeleportsJam + myTeleportsYield + myTeleportsWrongLane;
     588              : }
     589              : 
     590              : 
     591              : void
     592         4898 : MSVehicleControl::adaptIntermodalRouter(MSTransportableRouter& router) const {
     593         5171 :     for (const SUMOVehicle* const veh : myPTVehicles) {
     594              :         // add single vehicles with line attribute which are not part of a flow
     595          273 :         ConstMSRoutePtr const route = MSRoute::dictionary(veh->getParameter().routeid);
     596          273 :         router.getNetwork()->addSchedule(veh->getParameter(), route == nullptr ? nullptr : &route->getStops());
     597              :     }
     598         4898 : }
     599              : 
     600              : // ===========================================================================
     601              : // MSVehicleControl::DeleteKeptVehicle method definitions
     602              : // ===========================================================================
     603              : 
     604              : SUMOTime
     605           12 : MSVehicleControl::DeleteKeptVehicle::execute(SUMOTime /*currentTime*/) {
     606           12 :     MSNet::getInstance()->getVehicleControl().deleteVehicle(myVehicle, false, true);
     607           12 :     return 0;
     608              : }
     609              : 
     610              : /****************************************************************************/
        

Generated by: LCOV version 2.0-1