LCOV - code coverage report
Current view: top level - src/utils/vehicle - SUMOVehicleParameter.cpp (source / functions) Coverage Total Hit
Test: lcov.info Lines: 88.0 % 568 500
Test Date: 2026-07-25 16:16:11 Functions: 92.1 % 38 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    SUMOVehicleParameter.cpp
      15              : /// @author  Daniel Krajzewicz
      16              : /// @author  Jakob Erdmann
      17              : /// @author  Michael Behrisch
      18              : /// @date    Tue, 31.03.2009
      19              : ///
      20              : // Structure representing possible vehicle parameter
      21              : /****************************************************************************/
      22              : #include <config.h>
      23              : #include <utils/common/MsgHandler.h>
      24              : #include <utils/common/StringTokenizer.h>
      25              : #include <utils/common/StringUtils.h>
      26              : #include <utils/common/ToString.h>
      27              : #include <utils/common/RandHelper.h>
      28              : #include <utils/iodevices/OutputDevice.h>
      29              : #include <utils/options/OptionsCont.h>
      30              : 
      31              : #include "SUMOVehicleParameter.h"
      32              : 
      33              : // ===========================================================================
      34              : // member method definitions
      35              : // ===========================================================================
      36              : 
      37      1189590 : SUMOVehicleParameter::SUMOVehicleParameter()
      38      2379180 :     : tag(SUMO_TAG_NOTHING), vtypeid(DEFAULT_VTYPE_ID), color(RGBColor::DEFAULT_COLOR),
      39      1189590 :       depart(-1), departProcedure(DepartDefinition::GIVEN),
      40      1189590 :       departLane(0), departLaneProcedure(DepartLaneDefinition::DEFAULT),
      41      1189590 :       departPos(0), departPosProcedure(DepartPosDefinition::DEFAULT),
      42      1189590 :       departPosLat(0), departPosLatProcedure(DepartPosLatDefinition::DEFAULT),
      43      1189590 :       departSpeed(-1), departSpeedProcedure(DepartSpeedDefinition::DEFAULT),
      44      1189590 :       departEdge(0), departEdgeProcedure(RouteIndexDefinition::DEFAULT),
      45      1189590 :       arrivalLane(0), arrivalLaneProcedure(ArrivalLaneDefinition::DEFAULT),
      46      1189590 :       arrivalPos(0), arrivalPosProcedure(ArrivalPosDefinition::DEFAULT),
      47      1189590 :       arrivalPosLat(0), arrivalPosLatProcedure(ArrivalPosLatDefinition::DEFAULT),
      48      1189590 :       arrivalSpeed(-1), arrivalSpeedProcedure(ArrivalSpeedDefinition::DEFAULT),
      49      1189590 :       arrivalEdge(-1), arrivalEdgeProcedure(RouteIndexDefinition::DEFAULT),
      50      1189590 :       repetitionNumber(-1),
      51      1189590 :       repetitionsDone(-1),
      52      1189590 :       repetitionOffset(-1),
      53      1189590 :       repetitionTotalOffset(0),
      54      1189590 :       repetitionProbability(-1),
      55      1189590 :       poissonRate(0),
      56      1189590 :       repetitionEnd(-1),
      57      1189590 :       line(), fromTaz(), toTaz(), personNumber(0), containerNumber(0),
      58      1189590 :       speedFactor(-1),
      59      1189590 :       calibratorSpeed(-1),
      60      1189590 :       insertionChecks((int)InsertionCheck::ALL),
      61      1189590 :       parametersSet(0)
      62      1189590 : { }
      63              : 
      64              : 
      65     13004399 : SUMOVehicleParameter::~SUMOVehicleParameter() {
      66     13004399 : }
      67              : 
      68              : 
      69              : bool
      70       285922 : SUMOVehicleParameter::defaultOptionOverrides(const OptionsCont& oc, const std::string& optionName) const {
      71       571844 :     return oc.exists(optionName) && oc.isSet(optionName) && oc.getBool("defaults-override");
      72              : }
      73              : 
      74              : 
      75              : void
      76       533177 : SUMOVehicleParameter::write(OutputDevice& dev, const OptionsCont& oc, const SumoXMLTag altTag, const std::string& typeID) const {
      77       533177 :     if (!id.empty()) {
      78              :         // only used by calibrator flows
      79       533177 :         dev.openTag(altTag).writeAttr(SUMO_ATTR_ID, id);
      80              :     }
      81       533177 :     if (typeID == "") {
      82       507513 :         if (wasSet(VEHPARS_VTYPE_SET)) {
      83        35420 :             dev.writeAttr(SUMO_ATTR_TYPE, vtypeid);
      84              :         }
      85              :     } else {
      86        25664 :         dev.writeAttr(SUMO_ATTR_TYPE, typeID);
      87              :     }
      88              :     // write depart depending of tag
      89              :     if (altTag == SUMO_TAG_FLOW
      90       533177 :             || altTag == SUMO_TAG_PERSONFLOW
      91              :             || altTag == SUMO_TAG_CONTAINERFLOW
      92              :             || altTag == GNE_TAG_FLOW_ROUTE
      93              :             || altTag == GNE_TAG_FLOW_WITHROUTE
      94              :             || altTag == SUMO_TAG_FLOWSTATE) {
      95         1021 :         dev.writeAttr(SUMO_ATTR_BEGIN, getDepart());
      96              : 
      97         1021 :         if (wasSet(VEHPARS_END_SET)) {
      98         1017 :             dev.writeAttr(SUMO_ATTR_END, time2string(repetitionEnd));
      99              :         }
     100         1021 :         if (wasSet(VEHPARS_NUMBER_SET)) {
     101           60 :             dev.writeAttr(SUMO_ATTR_NUMBER, repetitionNumber);
     102              :         }
     103         1021 :         if (wasSet(VEHPARS_VPH_SET)) {
     104            0 :             dev.writeAttr(SUMO_ATTR_PERHOUR, 3600 / STEPS2TIME(repetitionOffset));
     105              :         }
     106              :         // netedit uses VEHPARS_POISSON_SET
     107         1021 :         if (wasSet(VEHPARS_PERIOD_SET) || wasSet(VEHPARS_POISSON_SET)) {
     108          603 :             if (repetitionOffset >= 0 && !wasSet(VEHPARS_POISSON_SET)) {
     109          541 :                 dev.writeAttr(SUMO_ATTR_PERIOD, StringUtils::adjustDecimalValue(STEPS2TIME(repetitionOffset), 20));
     110              :             } else {
     111          186 :                 dev.writeAttr(SUMO_ATTR_PERIOD, "exp(" + StringUtils::adjustDecimalValue(poissonRate, 20) + ")");
     112              :             }
     113              :         }
     114         1021 :         if (wasSet(VEHPARS_PROB_SET) && repetitionProbability > 0) {
     115          362 :             dev.writeAttr(SUMO_ATTR_PROB, StringUtils::adjustDecimalValue(repetitionProbability, 20));
     116              :         }
     117              :     } else {
     118       532156 :         dev.writeAttr(SUMO_ATTR_DEPART, getDepart());
     119              :     }
     120              :     // optional parameter
     121              :     //  departlane
     122       635560 :     if (wasSet(VEHPARS_DEPARTLANE_SET) && !defaultOptionOverrides(oc, "departlane")) {
     123       204606 :         dev.writeNonEmptyAttr(SUMO_ATTR_DEPARTLANE, getDepartLane());
     124       745773 :     } else if (oc.exists("departlane") && oc.isSet("departlane")) {
     125          730 :         dev.writeNonEmptyAttr(SUMO_ATTR_DEPARTLANE, oc.getString("departlane"));
     126              :     }
     127              :     //  departpos
     128       573567 :     if (wasSet(VEHPARS_DEPARTPOS_SET) && !defaultOptionOverrides(oc, "departpos")) {
     129        80652 :         dev.writeNonEmptyAttr(SUMO_ATTR_DEPARTPOS, getDepartPos());
     130       888152 :     } else if (oc.exists("departpos") && oc.isSet("departpos")) {
     131          676 :         dev.writeNonEmptyAttr(SUMO_ATTR_DEPARTPOS, oc.getString("departpos"));
     132              :     }
     133              :     //  departPosLat
     134       533177 :     if (wasSet(VEHPARS_DEPARTPOSLAT_SET)) {
     135           12 :         dev.writeNonEmptyAttr(SUMO_ATTR_DEPARTPOS_LAT, getDepartPosLat());
     136              :     }
     137              :     //  departspeed
     138       667646 :     if (wasSet(VEHPARS_DEPARTSPEED_SET) && !defaultOptionOverrides(oc, "departspeed")) {
     139       268810 :         dev.writeNonEmptyAttr(SUMO_ATTR_DEPARTSPEED, getDepartSpeed());
     140       710174 :     } else if (oc.exists("departspeed") && oc.isSet("departspeed")) {
     141          734 :         dev.writeNonEmptyAttr(SUMO_ATTR_DEPARTSPEED, oc.getString("departspeed"));
     142              :     }
     143              :     //  departedge
     144       533517 :     if (wasSet(VEHPARS_DEPARTEDGE_SET) && !defaultOptionOverrides(oc, "departedge")) {
     145          680 :         dev.writeNonEmptyAttr(SUMO_ATTR_DEPARTEDGE, getDepartEdge());
     146       532837 :     } else if (oc.exists("departedge") && oc.isSet("departedge")) {
     147            0 :         dev.writeNonEmptyAttr(SUMO_ATTR_DEPARTEDGE, oc.getString("departedge"));
     148              :     }
     149              :     //  arrivallane
     150       533505 :     if (wasSet(VEHPARS_ARRIVALLANE_SET) && !defaultOptionOverrides(oc, "arrivallane")) {
     151          592 :         dev.writeNonEmptyAttr(SUMO_ATTR_ARRIVALLANE, getArrivalLane());
     152       930358 :     } else if (oc.exists("arrivallane") && oc.isSet("arrivallane")) {
     153          708 :         dev.writeNonEmptyAttr(SUMO_ATTR_ARRIVALLANE, oc.getString("arrivallane"));
     154              :     }
     155              :     //  arrivalpos
     156       537357 :     if (wasSet(VEHPARS_ARRIVALPOS_SET) && !defaultOptionOverrides(oc, "arrivalpos")) {
     157         8264 :         dev.writeNonEmptyAttr(SUMO_ATTR_ARRIVALPOS, getArrivalPos());
     158       926295 :     } else if (oc.exists("arrivalpos") && oc.isSet("arrivalpos")) {
     159          692 :         dev.writeNonEmptyAttr(SUMO_ATTR_ARRIVALPOS, oc.getString("arrivalpos"));
     160              :     }
     161              :     //  arrivalPosLat
     162       533177 :     if (wasSet(VEHPARS_ARRIVALPOSLAT_SET)) {
     163            0 :         dev.writeNonEmptyAttr(SUMO_ATTR_ARRIVALPOS_LAT, getArrivalPosLat());
     164              :     }
     165              :     //  arrivalspeed
     166       536948 :     if (wasSet(VEHPARS_ARRIVALSPEED_SET) && !defaultOptionOverrides(oc, "arrivalspeed")) {
     167         7478 :         dev.writeNonEmptyAttr(SUMO_ATTR_ARRIVALSPEED, getArrivalSpeed());
     168       926923 :     } else if (oc.exists("arrivalspeed") && oc.isSet("arrivalspeed")) {
     169          708 :         dev.writeNonEmptyAttr(SUMO_ATTR_ARRIVALSPEED, oc.getString("arrivalspeed"));
     170              :     }
     171              :     //  arrivalEdge
     172       533398 :     if (wasSet(VEHPARS_ARRIVALEDGE_SET) && !defaultOptionOverrides(oc, "arrivaledge") && arrivalEdge >= 0) {
     173          442 :         dev.writeNonEmptyAttr(SUMO_ATTR_ARRIVALEDGE, getArrivalEdge());
     174       532956 :     } else if (oc.exists("arrivaledge") && oc.isSet("arrivaledge")) {
     175            0 :         dev.writeNonEmptyAttr(SUMO_ATTR_ARRIVALEDGE, oc.getString("arrivaledge"));
     176              :     }
     177              :     // color
     178       533177 :     if (wasSet(VEHPARS_COLOR_SET)) {
     179         7913 :         if (color.isRandom()) {
     180            0 :             dev.writeAttr(SUMO_ATTR_COLOR, "random");
     181              :         } else {
     182         7913 :             dev.writeAttr(SUMO_ATTR_COLOR, color);
     183              :         }
     184              :     }
     185              :     // line
     186       533177 :     if (wasSet(VEHPARS_LINE_SET)) {
     187          405 :         dev.writeAttr(SUMO_ATTR_LINE, line);
     188              :     }
     189              :     // from TAZ
     190       533177 :     if (wasSet(VEHPARS_FROM_TAZ_SET)) {
     191         9594 :         dev.writeAttr(SUMO_ATTR_FROM_TAZ, fromTaz);
     192              :     }
     193              :     // to TAZ
     194       533177 :     if (wasSet(VEHPARS_TO_TAZ_SET)) {
     195         9600 :         dev.writeAttr(SUMO_ATTR_TO_TAZ, toTaz);
     196              :     }
     197              :     // person number
     198       533177 :     if (wasSet(VEHPARS_PERSON_NUMBER_SET)) {
     199            0 :         dev.writeAttr(SUMO_ATTR_PERSON_NUMBER, personNumber);
     200              :     }
     201              :     // container number
     202       533177 :     if (wasSet(VEHPARS_CONTAINER_NUMBER_SET)) {
     203            0 :         dev.writeAttr(SUMO_ATTR_CONTAINER_NUMBER, containerNumber);
     204              :     }
     205              :     // individual speedFactor
     206       533177 :     if (wasSet(VEHPARS_SPEEDFACTOR_SET)) {
     207              :         // might be saving state with custom precision
     208              :         const int precision = dev.getPrecision();
     209        48253 :         dev.setPrecision(MAX2(gPrecisionRandom, precision));
     210        48253 :         dev.writeAttr(SUMO_ATTR_SPEEDFACTOR, speedFactor);
     211        48253 :         dev.setPrecision(precision);
     212              :     }
     213              :     // speed (only used by calibrators)
     214       533177 :     if (wasSet(VEHPARS_CALIBRATORSPEED_SET)) {
     215            0 :         dev.writeAttr(SUMO_ATTR_SPEED, calibratorSpeed);
     216              :     }
     217              :     // insertionChecks
     218       533177 :     if (wasSet(VEHPARS_INSERTION_CHECKS_SET) && insertionChecks != (int)InsertionCheck::ALL) {
     219              :         std::vector<std::string> checks;
     220          109 :         if (insertionChecks == (int)InsertionCheck::NONE) {
     221          204 :             checks.push_back(toString(InsertionCheck::NONE));
     222              :         } else {
     223           98 :             for (auto it : SUMOXMLDefinitions::InsertionChecks.getValues()) {
     224           91 :                 if (((int)it & insertionChecks) != 0) {
     225          126 :                     checks.push_back(toString(it));
     226              :                 }
     227            7 :             }
     228              :         }
     229          109 :         dev.writeAttr(SUMO_ATTR_INSERTIONCHECKS, checks);
     230          109 :     }
     231              :     // parking access rights
     232       533177 :     if (wasSet(VEHPARS_PARKING_BADGES_SET)) {
     233            0 :         dev.writeNonEmptyAttr(SUMO_ATTR_PARKING_BADGES, joinToString(parkingBadges, " "));
     234              :     }
     235       533177 : }
     236              : 
     237              : 
     238              : void
     239        32647 : SUMOVehicleParameter::Stop::write(OutputDevice& dev, const bool close, const bool writeTagAndParents) const {
     240        32647 :     if (writeTagAndParents) {
     241        32647 :         dev.openTag(SUMO_TAG_STOP);
     242        32647 :         if (busstop != "") {
     243        11169 :             dev.writeAttr(SUMO_ATTR_BUS_STOP, busstop);
     244              :         }
     245        32647 :         if (containerstop != "") {
     246          415 :             dev.writeAttr(SUMO_ATTR_CONTAINER_STOP, containerstop);
     247              :         }
     248        32647 :         if (chargingStation != "") {
     249          334 :             dev.writeAttr(SUMO_ATTR_CHARGING_STATION, chargingStation);
     250              :         }
     251        32647 :         if (parkingarea != "") {
     252        10118 :             dev.writeAttr(SUMO_ATTR_PARKING_AREA, parkingarea);
     253              :         }
     254        32647 :         if ((busstop == "") && (containerstop == "") && (parkingarea == "") && (chargingStation == "")) {
     255        10625 :             if (lane != "") {
     256         8982 :                 dev.writeAttr(SUMO_ATTR_LANE, lane);
     257              :             } else {
     258         1643 :                 dev.writeAttr(SUMO_ATTR_EDGE, edge);
     259              :             }
     260        10625 :             if ((parametersSet & STOP_START_SET) != 0) {
     261         5202 :                 dev.writeAttr(SUMO_ATTR_STARTPOS, startPos);
     262              :             }
     263        10625 :             if ((parametersSet & STOP_END_SET) != 0) {
     264         8960 :                 dev.writeAttr(SUMO_ATTR_ENDPOS, endPos);
     265              :             }
     266              :         }
     267              :     }
     268        32647 :     if (index > 0) {
     269          895 :         dev.writeAttr(SUMO_ATTR_INDEX, index);
     270              :     }
     271        32647 :     if ((parametersSet & STOP_POSLAT_SET) != 0 && posLat != INVALID_DOUBLE) {
     272           71 :         dev.writeAttr(SUMO_ATTR_POSITION_LAT, posLat);
     273              :     }
     274        32647 :     if ((parametersSet & STOP_ARRIVAL_SET) && (arrival >= 0)) {
     275          509 :         dev.writeAttr(SUMO_ATTR_ARRIVAL, time2string(arrival));
     276              :     }
     277        32647 :     if ((parametersSet & STOP_DURATION_SET) && (duration >= 0)) {
     278        19645 :         dev.writeAttr(SUMO_ATTR_DURATION, time2string(duration));
     279              :     }
     280        32647 :     if ((parametersSet & STOP_UNTIL_SET) && (until >= 0)) {
     281        14453 :         dev.writeAttr(SUMO_ATTR_UNTIL, time2string(until));
     282              :     }
     283        32647 :     if ((parametersSet & STOP_STARTED_SET) && (started >= 0)) {
     284          107 :         dev.writeAttr(SUMO_ATTR_STARTED, time2string(started));
     285              :     }
     286        32647 :     if ((parametersSet & STOP_ENDED_SET) && (ended >= 0)) {
     287          122 :         dev.writeAttr(SUMO_ATTR_ENDED, time2string(ended));
     288              :     }
     289        32647 :     if ((parametersSet & STOP_EXTENSION_SET) && (extension >= 0)) {
     290           73 :         dev.writeAttr(SUMO_ATTR_EXTENSION, time2string(extension));
     291              :     }
     292        32647 :     if ((parametersSet & STOP_TRIGGER_SET) != 0) {
     293         2460 :         const std::vector<std::string> triggers = getTriggers();
     294         2460 :         if (triggers.size() > 0) {
     295         2450 :             dev.writeAttr(SUMO_ATTR_TRIGGERED, triggers);
     296              :         }
     297         2460 :     }
     298        32647 :     if ((parametersSet & STOP_PARKING_SET) != 0) {
     299         4427 :         dev.writeAttr(SUMO_ATTR_PARKING, parking);
     300              :     }
     301        32647 :     if ((parametersSet & STOP_EXPECTED_SET) != 0 && awaitedPersons.size() > 0) {
     302           51 :         dev.writeAttr(SUMO_ATTR_EXPECTED, awaitedPersons);
     303              :     }
     304        32647 :     if ((parametersSet & STOP_PERMITTED_SET) != 0 && permitted.size() > 0) {
     305         1579 :         dev.writeAttr(SUMO_ATTR_PERMITTED, permitted);
     306              :     }
     307        32647 :     if ((parametersSet & STOP_EXPECTED_CONTAINERS_SET) != 0 && awaitedContainers.size() > 0) {
     308            4 :         dev.writeAttr(SUMO_ATTR_EXPECTED_CONTAINERS, awaitedContainers);
     309              :     }
     310        32647 :     if ((parametersSet & STOP_TRIP_ID_SET) != 0) {
     311           55 :         dev.writeAttr(SUMO_ATTR_TRIP_ID, tripId);
     312              :     }
     313        32647 :     if ((parametersSet & STOP_LINE_SET) != 0) {
     314           22 :         dev.writeAttr(SUMO_ATTR_LINE, line);
     315              :     }
     316        32647 :     if ((parametersSet & STOP_SPLIT_SET) != 0) {
     317           21 :         dev.writeAttr(SUMO_ATTR_SPLIT, split);
     318              :     }
     319        32647 :     if ((parametersSet & STOP_JOIN_SET) != 0) {
     320           17 :         dev.writeAttr(SUMO_ATTR_JOIN, join);
     321              :     }
     322        32647 :     if ((parametersSet & STOP_SPEED_SET) != 0) {
     323          166 :         dev.writeAttr(SUMO_ATTR_SPEED, speed);
     324              :     }
     325        32647 :     if ((parametersSet & STOP_ONDEMAND_SET) != 0) {
     326           88 :         dev.writeAttr(SUMO_ATTR_ONDEMAND, onDemand);
     327              :     }
     328        32647 :     if ((parametersSet & STOP_JUMP_SET) != 0 && jump >= 0) {
     329          304 :         dev.writeAttr(SUMO_ATTR_JUMP, time2string(jump));
     330              :     }
     331        32647 :     if ((parametersSet & STOP_JUMP_UNTIL_SET) != 0 && jumpUntil >= 0) {
     332            9 :         dev.writeAttr(SUMO_ATTR_JUMP_UNTIL, time2string(jumpUntil));
     333              :     }
     334        32647 :     if ((parametersSet & STOP_PRIORITY_SET) != 0 && priority >= 0) {
     335          357 :         dev.writeAttr(SUMO_ATTR_PRIORITY, priority);
     336              :     }
     337        32647 :     if (collision) {
     338          739 :         dev.writeAttr(SUMO_ATTR_COLLISION, collision);
     339              :     }
     340              :     // only write friendly position if is true
     341        32647 :     if (friendlyPos) {
     342            0 :         dev.writeAttr(SUMO_ATTR_FRIENDLY_POS, friendlyPos);
     343              :     }
     344              :     // only write act type if isn't empty
     345        32647 :     if (!actType.empty()) {
     346         3897 :         dev.writeAttr(SUMO_ATTR_ACTTYPE, actType);
     347              :     }
     348        32647 :     if (close) {
     349              :         // the user is closing the stop it is responsible for writing params
     350        23766 :         writeParams(dev);
     351        47532 :         dev.closeTag();
     352              :     }
     353        32647 : }
     354              : 
     355              : std::vector<std::string>
     356          192 : SUMOVehicleParameter::Stop::getStoppingPlaceIDs() const {
     357              :     std::vector<std::string> result;
     358          192 :     if (busstop != "") {
     359           96 :         result.push_back(busstop);
     360              :     }
     361          192 :     if (containerstop != "") {
     362            8 :         result.push_back(containerstop);
     363              :     }
     364          192 :     if (chargingStation != "") {
     365            8 :         result.push_back(chargingStation);
     366              :     }
     367          192 :     if (parkingarea != "") {
     368            8 :         result.push_back(parkingarea);
     369              :     }
     370          192 :     return result;
     371            0 : }
     372              : 
     373              : bool
     374       689295 : SUMOVehicleParameter::parseDepart(const std::string& val, const std::string& element, const std::string& id,
     375              :                                   SUMOTime& depart, DepartDefinition& dd, std::string& error, const std::string& attr) {
     376       689295 :     if (val == "triggered") {
     377         1451 :         dd = DepartDefinition::TRIGGERED;
     378       687844 :     } else if (val == "containerTriggered") {
     379          105 :         dd = DepartDefinition::CONTAINER_TRIGGERED;
     380       687739 :     } else if (val == "now") {
     381              :         // only used via TraCI. depart must be set by the calling code
     382        22903 :         dd = DepartDefinition::NOW;
     383       664836 :     } else if (val == "split") {
     384           40 :         dd = DepartDefinition::SPLIT;
     385       664796 :     } else if (val == "begin") {
     386           11 :         dd = DepartDefinition::BEGIN;
     387              :     } else {
     388              :         try {
     389       664785 :             depart = string2time(val);
     390       664777 :             dd = DepartDefinition::GIVEN;
     391       664777 :             if (depart < 0) {
     392           14 :                 error = "Negative " + attr + " time in the definition of " + element + " '" + id + "'.";
     393            7 :                 return false;
     394              :             }
     395            8 :         } catch (...) {
     396            8 :             if (id.empty()) {
     397            0 :                 error = "Invalid " + attr + " time for " + element + ". Must be one of (\"triggered\", \"containerTriggered\", \"now\", or a float >= 0)";
     398              :             } else {
     399           24 :                 error = "Invalid " + attr + " time for " + element + " '" + id + "';\n must be one of (\"triggered\", \"containerTriggered\", \"now\", or a float >= 0)";
     400              :             }
     401              :             return false;
     402            8 :         }
     403              :     }
     404              :     return true;
     405              : }
     406              : 
     407              : 
     408              : bool
     409       177871 : SUMOVehicleParameter::parseDepartLane(const std::string& val, const std::string& element, const std::string& id,
     410              :                                       int& lane, DepartLaneDefinition& dld, std::string& error) {
     411              :     bool ok = true;
     412       177871 :     lane = 0;
     413       177871 :     dld = DepartLaneDefinition::GIVEN;
     414       177871 :     if (val == "random") {
     415         4151 :         dld = DepartLaneDefinition::RANDOM;
     416       173720 :     } else if (val == "free") {
     417         2361 :         dld = DepartLaneDefinition::FREE;
     418       171359 :     } else if (val == "allowed") {
     419          131 :         dld = DepartLaneDefinition::ALLOWED_FREE;
     420       171228 :     } else if (val == "best") {
     421        94687 :         dld = DepartLaneDefinition::BEST_FREE;
     422        76541 :     } else if (val == "best_prob") {
     423        12886 :         dld = DepartLaneDefinition::BEST_PROB;
     424        63655 :     } else if (val == "first") {
     425        31043 :         dld = DepartLaneDefinition::FIRST_ALLOWED;
     426              :     } else {
     427              :         try {
     428        32612 :             lane = StringUtils::toInt(val);
     429        32558 :             if (lane < 0) {
     430              :                 ok = false;
     431              :             }
     432           54 :         } catch (...) {
     433              :             ok = false;
     434           54 :         }
     435              :     }
     436              :     if (!ok) {
     437           54 :         if (id.empty()) {
     438            0 :             error = "Invalid departLane definition for " + element + ". Must be one of (\"random\", \"free\", \"allowed\", \"best\", \"best_prob\", \"first\", or an int>=0)";
     439              :         } else {
     440          162 :             error = "Invalid departLane definition for " + element + " '" + id + "';\n must be one of (\"random\", \"free\", \"allowed\", \"best\", \"best_prob\", \"first\", or an int>=0)";
     441              :         }
     442              :     }
     443       177871 :     return ok;
     444              : }
     445              : 
     446              : 
     447              : bool
     448       114637 : SUMOVehicleParameter::parseDepartPos(const std::string& val, const std::string& element, const std::string& id,
     449              :                                      double& pos, DepartPosDefinition& dpd, std::string& error) {
     450              :     bool ok = true;
     451       114637 :     pos = 0.;
     452       114637 :     dpd = DepartPosDefinition::GIVEN;
     453       114637 :     if (val == "random") {
     454         3363 :         dpd = DepartPosDefinition::RANDOM;
     455       111274 :     } else if (val == "random_free") {
     456           72 :         dpd = DepartPosDefinition::RANDOM_FREE;
     457       111202 :     } else if (val == "random_location") {
     458            0 :         dpd = DepartPosDefinition::RANDOM_LOCATION;
     459       111202 :     } else if (val == "free") {
     460          417 :         dpd = DepartPosDefinition::FREE;
     461       110785 :     } else if (val == "base") {
     462         1028 :         dpd = DepartPosDefinition::BASE;
     463       109757 :     } else if (val == "last") {
     464          888 :         dpd = DepartPosDefinition::LAST;
     465       108869 :     } else if (val == "splitFront") {
     466            5 :         dpd = DepartPosDefinition::SPLIT_FRONT;
     467       108864 :     } else if (val == "stop") {
     468         2615 :         dpd = DepartPosDefinition::STOP;
     469              :     } else {
     470              :         try {
     471       106249 :             pos = StringUtils::toDouble(val);
     472           54 :         } catch (...) {
     473              :             ok = false;
     474           54 :         }
     475              :     }
     476              :     if (!ok) {
     477           54 :         if (id.empty()) {
     478            0 :             error = "Invalid departPos definition for " + element + ". Must be one of (\"random\", \"random_free\", \"free\", \"base\", \"last\" or a float)";
     479              :         } else {
     480          162 :             error = "Invalid departPos definition for " + element + " '" + id + "';\n must be one of (\"random\", \"random_free\", \"free\", \"base\", \"last\" or a float)";
     481              :         }
     482              :     }
     483       114637 :     return ok;
     484              : }
     485              : 
     486              : 
     487              : bool
     488         8949 : SUMOVehicleParameter::parseDepartPosLat(const std::string& val, const std::string& element, const std::string& id,
     489              :                                         double& pos, DepartPosLatDefinition& dpd, std::string& error) {
     490              :     bool ok = true;
     491         8949 :     pos = 0.;
     492         8949 :     dpd = DepartPosLatDefinition::GIVEN;
     493         8949 :     if (val == "random") {
     494         6181 :         dpd = DepartPosLatDefinition::RANDOM;
     495         2768 :     } else if (val == "random_free") {
     496          448 :         dpd = DepartPosLatDefinition::RANDOM_FREE;
     497         2320 :     } else if (val == "free") {
     498           71 :         dpd = DepartPosLatDefinition::FREE;
     499         2249 :     } else if (val == "right") {
     500          242 :         dpd = DepartPosLatDefinition::RIGHT;
     501         2007 :     } else if (val == "center") {
     502          586 :         dpd = DepartPosLatDefinition::CENTER;
     503         1421 :     } else if (val == "left") {
     504          184 :         dpd = DepartPosLatDefinition::LEFT;
     505              :     } else {
     506              :         try {
     507         1237 :             pos = StringUtils::toDouble(val);
     508            0 :         } catch (...) {
     509              :             ok = false;
     510            0 :         }
     511              :     }
     512              :     if (!ok) {
     513            0 :         if (id.empty()) {
     514            0 :             error = "Invalid departPosLat definition for " + element + ". Must be one of (\"random\", \"random_free\", \"free\", \"right\", \"center\", \"left\", or a float)";
     515              :         } else {
     516            0 :             error = "Invalid departPosLat definition for " + element + " '" + id + "';\n must be one of (\"random\", \"random_free\", \"free\", \"right\", \"center\", \"left\", or a float)";
     517              :         }
     518              :     }
     519         8949 :     return ok;
     520              : }
     521              : 
     522              : 
     523              : bool
     524       309637 : SUMOVehicleParameter::parseDepartSpeed(const std::string& val, const std::string& element, const std::string& id,
     525              :                                        double& speed, DepartSpeedDefinition& dsd, std::string& error) {
     526              :     bool ok = true;
     527       309637 :     speed = -1.;
     528       309637 :     dsd = DepartSpeedDefinition::GIVEN;
     529       309637 :     if (val == "random") {
     530          235 :         dsd = DepartSpeedDefinition::RANDOM;
     531       309402 :     } else if (val == "max") {
     532       138964 :         dsd = DepartSpeedDefinition::MAX;
     533       170438 :     } else if (val == "desired") {
     534          312 :         dsd = DepartSpeedDefinition::DESIRED;
     535       170126 :     } else if (val == "speedLimit") {
     536          546 :         dsd = DepartSpeedDefinition::LIMIT;
     537       169580 :     } else if (val == "last") {
     538           51 :         dsd = DepartSpeedDefinition::LAST;
     539       169529 :     } else if (val == "avg") {
     540        14318 :         dsd = DepartSpeedDefinition::AVG;
     541              :     } else {
     542              :         try {
     543       155211 :             speed = StringUtils::toDouble(val);
     544       155157 :             if (speed < 0) {
     545              :                 ok = false;
     546              :             }
     547           54 :         } catch (...) {
     548              :             ok = false;
     549           54 :         }
     550              :     }
     551              :     if (!ok) {
     552           54 :         if (id.empty()) {
     553            0 :             error = "Invalid departSpeed '" + val + "' definition for " + element + ". Must be one of (\"random\", \"max\", or a float>=0)";
     554              :         } else {
     555          162 :             error = "Invalid departSpeed definition '" + val + "' for " + element + " '" + id + "';\n must be one of (\"random\", \"max\", or a float>=0)";
     556              :         }
     557              :     }
     558       309637 :     return ok;
     559              : }
     560              : 
     561              : 
     562              : bool
     563          401 : SUMOVehicleParameter::parseRouteIndex(const std::string& val, const std::string& element, const std::string& id,
     564              :                                       const SumoXMLAttr attr, int& edgeIndex, RouteIndexDefinition& rid, std::string& error) {
     565              :     bool ok = true;
     566          401 :     edgeIndex = -1;
     567          401 :     rid = RouteIndexDefinition::GIVEN;
     568          401 :     if (val == "random") {
     569           63 :         rid = RouteIndexDefinition::RANDOM;
     570              :     } else {
     571              :         try {
     572          338 :             edgeIndex = StringUtils::toInt(val);
     573          338 :             if (edgeIndex < 0) {
     574              :                 ok = false;
     575              :             }
     576            0 :         } catch (...) {
     577              :             ok = false;
     578            0 :         }
     579              :     }
     580              :     if (!ok) {
     581           14 :         if (id.empty()) {
     582            0 :             error = "Invalid " + toString(attr) + " definition for " + element + ". Must be one of (\"random\", \"free\", or an int>=0)";
     583              :         } else {
     584           42 :             error = "Invalid " + toString(attr) + " definition for " + element + " '" + id + "';\n must be one of (\"random\", \"free\", or an int>=0)";
     585              :         }
     586              :     }
     587          401 :     return ok;
     588              : }
     589              : 
     590              : 
     591              : bool
     592        26252 : SUMOVehicleParameter::parseArrivalLane(const std::string& val, const std::string& element, const std::string& id,
     593              :                                        int& lane, ArrivalLaneDefinition& ald, std::string& error) {
     594              :     bool ok = true;
     595        26252 :     lane = 0;
     596        26252 :     ald = ArrivalLaneDefinition::GIVEN;
     597        26252 :     if (val == "current") {
     598        23481 :         ald = ArrivalLaneDefinition::CURRENT;
     599         2771 :     } else if (val == "random") {
     600           84 :         ald = ArrivalLaneDefinition::RANDOM;
     601         2687 :     } else if (val == "first") {
     602            7 :         ald = ArrivalLaneDefinition::FIRST_ALLOWED;
     603              :     } else {
     604              :         try {
     605         2680 :             lane = StringUtils::toInt(val);
     606         2626 :             if (lane < 0) {
     607              :                 ok = false;
     608              :             }
     609           54 :         } catch (...) {
     610              :             ok = false;
     611           54 :         }
     612              :     }
     613              :     if (!ok) {
     614           54 :         if (id.empty()) {
     615            0 :             error = "Invalid arrivalLane definition for " + element + ". Must be one of (\"current\", or an int>=0)";
     616              :         } else {
     617          162 :             error = "Invalid arrivalLane definition for " + element + " '" + id + "';\n must be one of (\"current\", or an int>=0)";
     618              :         }
     619              :     }
     620        26252 :     return ok;
     621              : }
     622              : 
     623              : 
     624              : bool
     625        63311 : SUMOVehicleParameter::parseArrivalPos(const std::string& val, const std::string& element, const std::string& id,
     626              :                                       double& pos, ArrivalPosDefinition& apd, std::string& error) {
     627              :     bool ok = true;
     628        63311 :     pos = 0.;
     629        63311 :     apd = ArrivalPosDefinition::GIVEN;
     630        63311 :     if (val == "random") {
     631         1666 :         apd = ArrivalPosDefinition::RANDOM;
     632        61645 :     } else if (val == "center") {
     633            0 :         apd = ArrivalPosDefinition::CENTER;
     634        61645 :     } else if (val == "max") {
     635        23035 :         apd = ArrivalPosDefinition::MAX;
     636              :     } else {
     637              :         try {
     638        38610 :             pos = StringUtils::toDouble(val);
     639           54 :         } catch (...) {
     640              :             ok = false;
     641           54 :         }
     642              :     }
     643              :     if (!ok) {
     644           54 :         if (id.empty()) {
     645            0 :             error = "Invalid arrivalPos definition for " + element + ". Must be one of (\"random\", \"max\", or a float)";
     646              :         } else {
     647          162 :             error = "Invalid arrivalPos definition for " + element + " '" + id + "';\n must be one of (\"random\", \"max\", or a float)";
     648              :         }
     649              :     }
     650        63311 :     return ok;
     651              : }
     652              : 
     653              : 
     654              : bool
     655         1072 : SUMOVehicleParameter::parseArrivalPosLat(const std::string& val, const std::string& element, const std::string& id,
     656              :         double& pos, ArrivalPosLatDefinition& apd, std::string& error) {
     657              :     bool ok = true;
     658         1072 :     pos = 0.;
     659         1072 :     apd = ArrivalPosLatDefinition::GIVEN;
     660         1072 :     if (val == "right") {
     661          496 :         apd = ArrivalPosLatDefinition::RIGHT;
     662          576 :     } else if (val == "center") {
     663            9 :         apd = ArrivalPosLatDefinition::CENTER;
     664          567 :     } else if (val == "left") {
     665           41 :         apd = ArrivalPosLatDefinition::LEFT;
     666              :     } else {
     667              :         try {
     668          526 :             pos = StringUtils::toDouble(val);
     669            0 :         } catch (...) {
     670              :             ok = false;
     671            0 :         }
     672              :     }
     673              :     if (!ok) {
     674            0 :         if (id.empty()) {
     675            0 :             error = "Invalid arrivalPosLat definition for " + element + ". Must be one of (\"right\", \"center\", \"left\", or a float)";
     676              :         } else {
     677            0 :             error = "Invalid arrivalPosLat definition for " + element + " '" + id + "';\n must be one of (\"right\", \"center\", \"left\", or a float)";
     678              :         }
     679              :     }
     680         1072 :     return ok;
     681              : }
     682              : 
     683              : 
     684              : bool
     685        26765 : SUMOVehicleParameter::parseArrivalSpeed(const std::string& val, const std::string& element, const std::string& id,
     686              :                                         double& speed, ArrivalSpeedDefinition& asd, std::string& error) {
     687              :     bool ok = true;
     688        26765 :     speed = -1.;
     689        26765 :     asd = ArrivalSpeedDefinition::GIVEN;
     690        26765 :     if (val == "current") {
     691        23553 :         asd = ArrivalSpeedDefinition::CURRENT;
     692              :     } else {
     693              :         try {
     694         3212 :             speed = StringUtils::toDouble(val);
     695         3158 :             if (speed < 0) {
     696              :                 ok = false;
     697              :             }
     698           54 :         } catch (...) {
     699              :             ok = false;
     700           54 :         }
     701              :     }
     702              :     if (!ok) {
     703           54 :         if (id.empty()) {
     704            0 :             error = "Invalid arrivalSpeed definition for " + element + ". Must be one of (\"current\", or a float>=0)";
     705              :         } else {
     706          162 :             error = "Invalid arrivalSpeed definition for " + element + " '" + id + "';\n must be one of (\"current\", or a float>=0)";
     707              :         }
     708              :     }
     709        26765 :     return ok;
     710              : }
     711              : 
     712              : 
     713              : double
     714      1493322 : SUMOVehicleParameter::interpretEdgePos(double pos, double maximumValue, SumoXMLAttr attr, const std::string& id, bool silent) {
     715      1493322 :     if (pos < 0) {
     716        28788 :         pos = maximumValue + pos;
     717              :     }
     718      1493322 :     if (pos > maximumValue && pos != std::numeric_limits<double>::infinity()) {
     719            0 :         if (!silent) {
     720            0 :             WRITE_WARNINGF(TL("Invalid % % given for %. Using edge end instead."), toString(attr), toString(pos), id);
     721              :         }
     722            0 :         pos = maximumValue;
     723              :     }
     724      1493322 :     return pos;
     725              : }
     726              : 
     727              : 
     728              : bool
     729         1159 : SUMOVehicleParameter::parsePersonModes(const std::string& modes, const std::string& element, const std::string& id, SVCPermissions& modeSet, std::string& error) {
     730              :     // separte modes in different strings, and check if modes are valid
     731         3660 :     for (StringTokenizer st(modes); st.hasNext();) {
     732         1342 :         const std::string mode = st.next();
     733         1342 :         if (mode == "car") {
     734          487 :             modeSet |= SVC_PASSENGER;
     735          855 :         } else if (mode == "taxi") {
     736          228 :             modeSet |= SVC_TAXI;
     737          627 :         } else if (mode == "bicycle") {
     738           41 :             modeSet |= SVC_BICYCLE;
     739          586 :         } else if (mode == "public") {
     740          586 :             modeSet |= SVC_BUS;
     741              :         } else {
     742            0 :             if (id.empty()) {
     743            0 :                 error = "Unknown person mode '" + mode + "'. Must be a combination of (\"car\", \"taxi\", \"bicycle\" or \"public\")";
     744              :             } else {
     745            0 :                 error = "Unknown person mode '" + mode + "' for " + element + " '" + id + "';\n must be a combination of (\"car\", \"taxi\", \"bicycle\" or \"public\")";
     746              :             }
     747              :             return false;
     748              :         }
     749         1159 :     }
     750         1159 :     return true;
     751              : }
     752              : 
     753              : 
     754              : void
     755        40943 : SUMOVehicleParameter::parseStopTriggers(const std::vector<std::string>& triggers, bool expectTrigger, Stop& stop) {
     756        40943 :     if (triggers.size() == 0 && expectTrigger) {
     757         1069 :         stop.triggered = true;
     758              :     }
     759        42603 :     for (std::string val : triggers) {
     760         1660 :         if (val == toString(SUMO_TAG_PERSON)) {
     761         1074 :             stop.triggered = true;
     762          586 :         } else if (val == toString(SUMO_TAG_CONTAINER)) {
     763          303 :             stop.containerTriggered = true;
     764          283 :         } else if (val == toString(SUMO_ATTR_JOIN)) {
     765          128 :             stop.joinTriggered = true;
     766              :         } else {
     767              :             try {
     768          155 :                 stop.triggered = StringUtils::toBool(val);
     769            0 :             } catch (BoolFormatException&) {
     770            0 :                 WRITE_ERROR(TL("Value of stop attribute 'trigger' must be 'person', 'container', 'join' or a boolean"));
     771            0 :             }
     772              :         }
     773              :     }
     774        40943 : }
     775              : 
     776              : 
     777              : ParkingType
     778         4504 : SUMOVehicleParameter::parseParkingType(const std::string& value) {
     779         4504 :     if (value == toString(ParkingType::OPPORTUNISTIC)) {
     780              :         return ParkingType::OPPORTUNISTIC;
     781              :     } else {
     782         4504 :         return StringUtils::toBool(value) ? ParkingType::OFFROAD : ParkingType::ONROAD;
     783              :     }
     784              : }
     785              : 
     786              : 
     787              : std::vector<std::string>
     788         2488 : SUMOVehicleParameter::Stop::getTriggers() const {
     789              :     std::vector<std::string> triggers;
     790         2488 :     if (triggered) {
     791         4610 :         triggers.push_back(toString(SUMO_TAG_PERSON));
     792              :     }
     793         2488 :     if (containerTriggered) {
     794          274 :         triggers.push_back(toString(SUMO_TAG_CONTAINER));
     795              :     }
     796         2488 :     if (joinTriggered) {
     797           64 :         triggers.push_back(toString(SUMO_ATTR_JOIN));
     798              :     }
     799         2488 :     return triggers;
     800            0 : }
     801              : 
     802              : int
     803         9861 : SUMOVehicleParameter::Stop::getFlags() const {
     804         9861 :     return (((parking == ParkingType::OFFROAD) ? 1 : 0) +
     805         9861 :             (triggered ? 2 : 0) +
     806         9861 :             (containerTriggered ? 4 : 0) +
     807         9861 :             (busstop != "" ? 8 : 0) +
     808         9861 :             (containerstop != "" ? 16 : 0) +
     809         9861 :             (chargingStation != "" ? 32 : 0) +
     810         9861 :             (parkingarea != "" ? 64 : 0) +
     811         9861 :             (overheadWireSegment != "" ? 128 : 0));
     812              : }
     813              : 
     814              : 
     815              : std::string
     816       533177 : SUMOVehicleParameter::getDepart() const {
     817       533177 :     if (departProcedure == DepartDefinition::TRIGGERED) {
     818          743 :         return "triggered";
     819       532434 :     } else if (departProcedure == DepartDefinition::CONTAINER_TRIGGERED) {
     820           16 :         return "containerTriggered";
     821              : //    } else if (departProcedure == DepartDefinition::NOW) {  // TODO check whether this is useful in XML input (currently TraCI only)
     822              : //        return "now";
     823       532418 :     } else if (departProcedure == DepartDefinition::SPLIT) {
     824            0 :         return "split";
     825       532418 :     } else if (departProcedure == DepartDefinition::BEGIN) {
     826            8 :         return "begin";
     827              :     } else {
     828       532410 :         return time2string(depart);
     829              :     }
     830              : }
     831              : 
     832              : 
     833              : std::string
     834       102303 : SUMOVehicleParameter::getDepartLane() const {
     835              :     std::string val;
     836       102303 :     switch (departLaneProcedure) {
     837        15006 :         case DepartLaneDefinition::GIVEN:
     838        15006 :             val = toString(departLane);
     839        15006 :             break;
     840              :         case DepartLaneDefinition::RANDOM:
     841              :             val = "random";
     842              :             break;
     843              :         case DepartLaneDefinition::FREE:
     844              :             val = "free";
     845              :             break;
     846              :         case DepartLaneDefinition::ALLOWED_FREE:
     847              :             val = "allowed";
     848              :             break;
     849              :         case DepartLaneDefinition::BEST_FREE:
     850              :             val = "best";
     851              :             break;
     852              :         case DepartLaneDefinition::BEST_PROB:
     853              :             val = "best_prob";
     854              :             break;
     855              :         case DepartLaneDefinition::FIRST_ALLOWED:
     856              :             val = "first";
     857              :             break;
     858              :         case DepartLaneDefinition::DEFAULT:
     859              :         default:
     860              :             break;
     861              :     }
     862       102303 :     return val;
     863              : }
     864              : 
     865              : 
     866              : std::string
     867        40326 : SUMOVehicleParameter::getDepartPos() const {
     868              :     std::string val;
     869        40326 :     switch (departPosProcedure) {
     870        24946 :         case DepartPosDefinition::GIVEN:
     871        24946 :             val = toString(departPos);
     872        24946 :             break;
     873        12795 :         case DepartPosDefinition::GIVEN_VEHROUTE:
     874        12795 :             val = StringUtils::pruneZeros(toString(departPos, MAX2(gPrecisionRandom, gPrecision)), 2);
     875        12795 :             break;
     876              :         case DepartPosDefinition::RANDOM:
     877              :             val = "random";
     878              :             break;
     879              :         case DepartPosDefinition::RANDOM_FREE:
     880              :             val = "random_free";
     881              :             break;
     882              :         case DepartPosDefinition::RANDOM_LOCATION:
     883              :             val = "random_location";
     884              :             break;
     885              :         case DepartPosDefinition::FREE:
     886              :             val = "free";
     887              :             break;
     888              :         case DepartPosDefinition::LAST:
     889              :             val = "last";
     890              :             break;
     891              :         case DepartPosDefinition::BASE:
     892              :             val = "base";
     893              :             break;
     894              :         case DepartPosDefinition::SPLIT_FRONT:
     895              :             val = "splitFront";
     896              :             break;
     897              :         case DepartPosDefinition::STOP:
     898              :             val = "stop";
     899              :             break;
     900              :         case DepartPosDefinition::DEFAULT:
     901              :         default:
     902              :             break;
     903              :     }
     904        40326 :     return val;
     905              : }
     906              : 
     907              : 
     908              : std::string
     909            6 : SUMOVehicleParameter::getDepartPosLat() const {
     910              :     std::string val;
     911            6 :     switch (departPosLatProcedure) {
     912            0 :         case DepartPosLatDefinition::GIVEN:
     913            0 :             val = toString(departPosLat);
     914            0 :             break;
     915            4 :         case DepartPosLatDefinition::GIVEN_VEHROUTE:
     916            4 :             val = StringUtils::pruneZeros(toString(departPosLat, MAX2(gPrecisionRandom, gPrecision)), 2);
     917            4 :             break;
     918              :         case DepartPosLatDefinition::RANDOM:
     919              :             val = "random";
     920              :             break;
     921              :         case DepartPosLatDefinition::RANDOM_FREE:
     922              :             val = "random_free";
     923              :             break;
     924              :         case DepartPosLatDefinition::FREE:
     925              :             val = "free";
     926              :             break;
     927              :         case DepartPosLatDefinition::RIGHT:
     928              :             val = "right";
     929              :             break;
     930              :         case DepartPosLatDefinition::CENTER:
     931              :             val = "center";
     932              :             break;
     933              :         case DepartPosLatDefinition::LEFT:
     934              :             val = "left";
     935              :             break;
     936              :         case DepartPosLatDefinition::DEFAULT:
     937              :         default:
     938              :             break;
     939              :     }
     940            6 :     return val;
     941              : }
     942              : 
     943              : 
     944              : std::string
     945       134405 : SUMOVehicleParameter::getDepartSpeed() const {
     946              :     std::string val;
     947       134405 :     switch (departSpeedProcedure) {
     948         2501 :         case DepartSpeedDefinition::GIVEN:
     949         2501 :             val = toString(departSpeed);
     950         2501 :             break;
     951        44210 :         case DepartSpeedDefinition::GIVEN_VEHROUTE:
     952        44210 :             val = StringUtils::pruneZeros(toString(departSpeed, MAX2(gPrecisionRandom, gPrecision)), 2);
     953        44210 :             break;
     954              :         case DepartSpeedDefinition::RANDOM:
     955              :             val = "random";
     956              :             break;
     957              :         case DepartSpeedDefinition::MAX:
     958              :             val = "max";
     959              :             break;
     960              :         case DepartSpeedDefinition::DESIRED:
     961              :             val = "desired";
     962              :             break;
     963              :         case DepartSpeedDefinition::LIMIT:
     964              :             val = "speedLimit";
     965              :             break;
     966              :         case DepartSpeedDefinition::LAST:
     967              :             val = "last";
     968              :             break;
     969              :         case DepartSpeedDefinition::AVG:
     970              :             val = "avg";
     971              :             break;
     972              :         case DepartSpeedDefinition::DEFAULT:
     973              :         default:
     974              :             break;
     975              :     }
     976       134405 :     return val;
     977              : }
     978              : 
     979              : 
     980              : std::string
     981          340 : SUMOVehicleParameter::getDepartEdge() const {
     982              :     std::string val;
     983          340 :     switch (departEdgeProcedure) {
     984          340 :         case RouteIndexDefinition::GIVEN:
     985          340 :             val = toString(departEdge);
     986          340 :             break;
     987              :         case RouteIndexDefinition::RANDOM:
     988              :             val = "random";
     989              :             break;
     990              :         case RouteIndexDefinition::DEFAULT:
     991              :         default:
     992              :             break;
     993              :     }
     994          340 :     return val;
     995              : }
     996              : 
     997              : std::string
     998          221 : SUMOVehicleParameter::getArrivalEdge() const {
     999              :     std::string val;
    1000          221 :     switch (arrivalEdgeProcedure) {
    1001          221 :         case RouteIndexDefinition::GIVEN:
    1002          221 :             val = toString(arrivalEdge);
    1003          221 :             break;
    1004              :         case RouteIndexDefinition::RANDOM:
    1005              :             val = "random";
    1006              :             break;
    1007              :         case RouteIndexDefinition::DEFAULT:
    1008              :         default:
    1009              :             break;
    1010              :     }
    1011          221 :     return val;
    1012              : }
    1013              : 
    1014              : 
    1015              : 
    1016              : 
    1017              : std::string
    1018          296 : SUMOVehicleParameter::getArrivalLane() const {
    1019              :     std::string val;
    1020          296 :     switch (arrivalLaneProcedure) {
    1021          160 :         case ArrivalLaneDefinition::GIVEN:
    1022          160 :             val = toString(arrivalLane);
    1023          160 :             break;
    1024              :         case ArrivalLaneDefinition::CURRENT:
    1025              :             val = "current";
    1026              :             break;
    1027              :         case ArrivalLaneDefinition::RANDOM:
    1028              :             val = "random";
    1029              :             break;
    1030              :         case ArrivalLaneDefinition::FIRST_ALLOWED:
    1031              :             val = "first";
    1032              :             break;
    1033              :         case ArrivalLaneDefinition::DEFAULT:
    1034              :         default:
    1035              :             break;
    1036              :     }
    1037          296 :     return val;
    1038              : }
    1039              : 
    1040              : 
    1041              : std::string
    1042         4132 : SUMOVehicleParameter::getArrivalPos() const {
    1043              :     std::string val;
    1044         4132 :     switch (arrivalPosProcedure) {
    1045         3806 :         case ArrivalPosDefinition::GIVEN:
    1046         3806 :             val = toString(arrivalPos);
    1047         3806 :             break;
    1048              :         case ArrivalPosDefinition::RANDOM:
    1049              :             val = "random";
    1050              :             break;
    1051              :         case ArrivalPosDefinition::CENTER:
    1052              :             val = "center";
    1053              :             break;
    1054              :         case ArrivalPosDefinition::MAX:
    1055              :             val = "max";
    1056              :             break;
    1057              :         case ArrivalPosDefinition::DEFAULT:
    1058              :         default:
    1059              :             break;
    1060              :     }
    1061         4132 :     return val;
    1062              : }
    1063              : 
    1064              : 
    1065              : std::string
    1066            0 : SUMOVehicleParameter::getArrivalPosLat() const {
    1067              :     std::string val;
    1068            0 :     switch (arrivalPosLatProcedure) {
    1069            0 :         case ArrivalPosLatDefinition::GIVEN:
    1070            0 :             val = toString(arrivalPosLat);
    1071            0 :             break;
    1072              :         case ArrivalPosLatDefinition::RIGHT:
    1073              :             val = "right";
    1074              :             break;
    1075              :         case ArrivalPosLatDefinition::CENTER:
    1076              :             val = "center";
    1077              :             break;
    1078              :         case ArrivalPosLatDefinition::LEFT:
    1079              :             val = "left";
    1080              :             break;
    1081              :         case ArrivalPosLatDefinition::DEFAULT:
    1082              :         default:
    1083              :             break;
    1084              :     }
    1085            0 :     return val;
    1086              : }
    1087              : 
    1088              : 
    1089              : std::string
    1090         3739 : SUMOVehicleParameter::getArrivalSpeed() const {
    1091              :     std::string val;
    1092         3739 :     switch (arrivalSpeedProcedure) {
    1093         3603 :         case ArrivalSpeedDefinition::GIVEN:
    1094         3603 :             val = toString(arrivalSpeed);
    1095         3603 :             break;
    1096              :         case ArrivalSpeedDefinition::CURRENT:
    1097              :             val = "current";
    1098              :             break;
    1099              :         case ArrivalSpeedDefinition::DEFAULT:
    1100              :         default:
    1101              :             break;
    1102              :     }
    1103         3739 :     return val;
    1104              : }
    1105              : 
    1106              : 
    1107              : void
    1108      5365351 : SUMOVehicleParameter::incrementFlow(double scale, SumoRNG* rng) {
    1109      5365351 :     repetitionsDone++;
    1110              :     // equidistant or exponential offset (for poisson distributed arrivals)
    1111      5365351 :     if (repetitionProbability < 0) {
    1112      4806391 :         if (repetitionOffset >= 0) {
    1113      4445997 :             repetitionTotalOffset += (SUMOTime)((double)repetitionOffset / scale);
    1114              :         } else {
    1115              :             assert(poissonRate > 0);
    1116              :             // we need to cache this do avoid double generation of the rng in the TIME2STEPS macro
    1117       360394 :             const double r = RandHelper::randExp(poissonRate, rng);
    1118       360394 :             repetitionTotalOffset += TIME2STEPS(r / scale);
    1119              :         }
    1120              :     }
    1121      5365351 : }
    1122              : 
    1123              : 
    1124              : std::string
    1125            0 : SUMOVehicleParameter::getInsertionChecks() const {
    1126            0 :     if ((insertionChecks == 0) || (insertionChecks == (int)InsertionCheck::ALL)) {
    1127            0 :         return SUMOXMLDefinitions::InsertionChecks.getString(InsertionCheck::ALL);
    1128              :     } else {
    1129              :         std::vector<std::string> insertionChecksStrs;
    1130            0 :         const auto insertionCheckValues = SUMOXMLDefinitions::InsertionChecks.getValues();
    1131              :         // iterate over values
    1132            0 :         for (const auto insertionCheckValue : insertionCheckValues) {
    1133            0 :             if ((insertionCheckValue != InsertionCheck::ALL) && (insertionChecks & (int)insertionCheckValue) != 0) {
    1134            0 :                 insertionChecksStrs.push_back(SUMOXMLDefinitions::InsertionChecks.getString(insertionCheckValue));
    1135              :             }
    1136              :         }
    1137            0 :         return toString(insertionChecksStrs);
    1138            0 :     }
    1139              : }
    1140              : 
    1141              : 
    1142              : bool
    1143            0 : SUMOVehicleParameter::areInsertionChecksValid(const std::string& value) const {
    1144            0 :     if (value.empty()) {
    1145              :         return true;
    1146              :     } else {
    1147              :         // split value in substrinsg
    1148            0 :         StringTokenizer valueStrs(value, " ");
    1149              :         // iterate over values
    1150            0 :         while (valueStrs.hasNext()) {
    1151            0 :             if (!SUMOXMLDefinitions::InsertionChecks.hasString(valueStrs.next())) {
    1152              :                 return false;
    1153              :             }
    1154              :         }
    1155              :         return true;
    1156            0 :     }
    1157              : }
    1158              : 
    1159              : 
    1160              : int
    1161        43788 : SUMOVehicleParameter::parseInsertionChecks(const std::string& value) {
    1162              :     // first reset insertionChecks
    1163              :     int result = 0;
    1164        43788 :     if (value.empty()) {
    1165              :         return (int)InsertionCheck::ALL;
    1166              :     } else {
    1167              :         // split value in substrinsg
    1168       131364 :         StringTokenizer insertionCheckStrs(value, " ");
    1169        90226 :         while (insertionCheckStrs.hasNext()) {
    1170        46442 :             std::string val = insertionCheckStrs.next();
    1171              :             if (SUMOXMLDefinitions::InsertionChecks.hasString(val)) {
    1172        46438 :                 result |= (int)SUMOXMLDefinitions::InsertionChecks.get(val);
    1173              :             } else {
    1174           16 :                 throw InvalidArgument("Unknown value '" + val + "' in " + toString(SUMO_ATTR_INSERTIONCHECKS) + ".");
    1175              :             }
    1176              :         }
    1177        43788 :     }
    1178        43784 :     return result;
    1179              : }
    1180              : 
    1181              : /****************************************************************************/
        

Generated by: LCOV version 2.0-1