LCOV - code coverage report
Current view: top level - src/microsim/trigger - MSOverheadWire.h (source / functions) Coverage Total Hit
Test: lcov.info Lines: 97.8 % 46 45
Test Date: 2025-11-13 15:38:19 Functions: 100.0 % 2 2

            Line data    Source code
       1              : /****************************************************************************/
       2              : // Eclipse SUMO, Simulation of Urban MObility; see https://eclipse.dev/sumo
       3              : // Copyright (C) 2002-2025 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    MSOverheadWire.h
      15              : /// @author  Jakub Sevcik (RICE)
      16              : /// @author  Jan Prikryl (RICE)
      17              : /// @date    2019-12-15
      18              : ///
      19              : // Overhead wires for Electric (equipped with elecHybrid device) vehicles (Overhead wire segments, overhead wire sections, traction substations)
      20              : /****************************************************************************/
      21              : #pragma once
      22              : #include <config.h>
      23              : 
      24              : #include <list>
      25              : #include <string>
      26              : #include <iostream>
      27              : #include <fstream>
      28              : #include <sstream>
      29              : #include <microsim/MSStoppingPlace.h>
      30              : #include <utils/common/Named.h>
      31              : #include <utils/vehicle/SUMOVehicle.h>
      32              : #include <utils/common/WrappingCommand.h>
      33              : #include <utils/traction_wire/Circuit.h>
      34              : 
      35              : // Resistivity of Cu is 1.69*10^-8 Ohm*m. A cross-section S of the overhead wire used in Pilsen is 150 mm^2. So the "resistivity/S" is 0.000113 Ohm/m.
      36              : const double WIRE_RESISTIVITY = (double)2 * 0.000113;
      37              : 
      38              : // Conversion macros
      39              : #define WATTHR2JOULE(_x) ((_x)*3600.0)
      40              : #define JOULE2WATTHR(_x) ((_x)/3600.0)
      41              : #define WATTHR2WATT(_x) ((_x)*3600.0/TS)
      42              : #define WATT2WATTHR(_x) ((_x)*TS/3600.0)
      43              : 
      44              : // ===========================================================================
      45              : // class declarations
      46              : // ===========================================================================
      47              : class MSLane;
      48              : class MSBusStop;
      49              : class OptionsCont;
      50              : class MSDevice_ElecHybrid;
      51              : class MSTractionSubstation;
      52              : class Named;
      53              : 
      54              : 
      55              : // ===========================================================================
      56              : // class definitions
      57              : // ===========================================================================
      58              : /**
      59              : * @class MSOverheadWire
      60              : * @brief Definition of overhead wire segment
      61              : */
      62              : 
      63              : class MSOverheadWire : public MSStoppingPlace {
      64              : public:
      65              : 
      66              :     /// @brief constructor
      67              :     MSOverheadWire(const std::string& overheadWireSegmentID, MSLane& lane, double startPos, double endPos,
      68              :                    bool voltageSource);
      69              : 
      70              :     /// @brief destructor
      71              :     ~MSOverheadWire();
      72              : 
      73              :     /// @brief Get overhead wire's voltage
      74              :     double getVoltage() const;
      75              : 
      76              :     /// @brief Set overhead wire's voltage
      77              :     void setVoltage(double voltage);
      78              : 
      79              :     /// @brief enable or disable charging vehicle
      80              :     void setChargingVehicle(bool value);
      81              : 
      82              :     /** @brief Check if a vehicle is inside in  the Charge Station
      83              :     * @param[in] position Position of vehicle in the LANE
      84              :     * @return true if is between StartPostion and EndPostion
      85              :     */
      86              :     bool vehicleIsInside(const double position) const;
      87              : 
      88              :     /// @brief Return true if in the current time step charging station is charging a vehicle
      89              :     bool isCharging() const;
      90              : 
      91              :     void addVehicle(SUMOVehicle& veh);
      92              : 
      93              :     void eraseVehicle(SUMOVehicle& veh);
      94              : 
      95              :     int getElecHybridCount() const {
      96           32 :         return (int)myChargingVehicles.size();
      97              :     }
      98              : 
      99              :     const std::vector<SUMOVehicle*>& getChargingVehicles() const {
     100              :         return myChargingVehicles;
     101              :     }
     102              : 
     103              :     double getTotalCharged() const {
     104            0 :         return myTotalCharge;
     105              :     }
     106              : 
     107              :     /// @brief add charge value for output
     108              :     void addChargeValueForOutput(double WCharged, MSDevice_ElecHybrid* elecHybrid, bool ischarging = 1);
     109              : 
     110              :     /// @brief write overhead wire segment values
     111              :     void writeOverheadWireSegmentOutput(OutputDevice& output);
     112              : 
     113              :     std::string getOverheadWireSegmentName();
     114              : 
     115              :     MSTractionSubstation* getTractionSubstation() const {
     116         3190 :         return myTractionSubstation;
     117              :     }
     118              : 
     119              :     void setTractionSubstation(MSTractionSubstation* substation) {
     120          118 :         myTractionSubstation = substation;
     121              :     }
     122              : 
     123              :     Circuit* getCircuit() const;
     124              : 
     125              :     void setCircuitStartNodePos(Node* node) {
     126           38 :         myCircuitStartNodePos = node;
     127           15 :     }
     128              : 
     129              :     void setCircuitEndNodePos(Node* node) {
     130           38 :         myCircuitEndNodePos = node;
     131            4 :     }
     132              : 
     133              :     void setCircuitElementPos(Element* element) {
     134           38 :         myCircuitElementPos = element;
     135              :     }
     136              : 
     137              :     Node* getCircuitStartNodePos() const {
     138           71 :         return myCircuitStartNodePos;
     139              :     }
     140              : 
     141              :     Node* getCircuitEndNodePos() const {
     142          106 :         return myCircuitEndNodePos;
     143              :     }
     144              : 
     145              :     Element* getCircuitElementPos() const {
     146              :         return myCircuitElementPos;
     147              :     }
     148              : 
     149              :     bool isThereVoltageSource() const {
     150           38 :         return myVoltageSource;
     151              :     }
     152              : 
     153              :     void lock() const;
     154              :     void unlock() const;
     155              : 
     156              : protected:
     157              : 
     158              :     /// @brief struct to save information for the overhead wire segment output
     159              :     struct Charge {
     160              :         /// @brief constructor
     161          710 :         Charge(SUMOTime _timeStep, std::string _vehicleID, std::string _vehicleType, std::string _status,
     162              :                double _WCharged, double _actualBatteryCapacity, double _maxBatteryCapacity, double _voltage,
     163          710 :                double _totalEnergyCharged) :
     164          710 :             timeStep(_timeStep),
     165          710 :             vehicleID(_vehicleID),
     166          710 :             vehicleType(_vehicleType),
     167          710 :             status(_status),
     168          710 :             WCharged(_WCharged),
     169          710 :             actualBatteryCapacity(_actualBatteryCapacity),
     170          710 :             maxBatteryCapacity(_maxBatteryCapacity),
     171          710 :             voltage(_voltage),
     172          710 :             totalEnergyCharged(_totalEnergyCharged) {}
     173              : 
     174              :         // @brief vehicle TimeStep
     175              :         SUMOTime timeStep;
     176              :         // @brief vehicle ID
     177              :         std::string vehicleID;
     178              :         // @brief vehicle Type
     179              :         std::string vehicleType;
     180              :         /// @brief status
     181              :         std::string status;
     182              :         // @brief W charged
     183              :         double WCharged;
     184              :         // @brief actual battery capacity AFTER charging
     185              :         double actualBatteryCapacity;
     186              :         // @brief battery max capacity
     187              :         double maxBatteryCapacity;
     188              :         // @brief current charging power of charging station
     189              :         double voltage;
     190              :         // @brief current efficiency of charging station
     191              :         double chargingEfficiency;
     192              :         // @brief current energy charged by charging stations AFTER charging
     193              :         double totalEnergyCharged;
     194              :     };
     195              : 
     196              :     /** @brief A class for sorting vehicle on lane under the overhead wire segment */
     197              :     class vehicle_position_sorter {
     198              :     public:
     199              :         /// @brief Constructor
     200              :         explicit vehicle_position_sorter() { }
     201              : 
     202              :         /// @brief Sorting function; compares RODFRouteDesc::distance2Last
     203              :         int operator()(SUMOVehicle* v1, SUMOVehicle* v2) {
     204           50 :             return v1->getPositionOnLane() > v2->getPositionOnLane();
     205              :         }
     206              :     };
     207              : 
     208              :     void static writeVehicle(OutputDevice& out, const std::vector<Charge>& chargeSteps, int iStart, int iEnd, double charged);
     209              : 
     210              :     /// @brief Overhead wire's voltage
     211              :     double myVoltage;
     212              : 
     213              :     /// @brief Check if in the current TimeStep overheadWireSegment is charging a vehicle
     214              :     bool myChargingVehicle;
     215              : 
     216              :     /// @brief total energy charged by this charging station
     217              :     double myTotalCharge;
     218              : 
     219              :     /// @brief map with the charges of this charging station (key = vehicleID)
     220              :     std::map<std::string, std::vector<Charge> > myChargeValues;
     221              :     /// @brief order vehicles by time of first charge
     222              :     std::vector<std::string> myChargedVehicles;
     223              : 
     224              :     std::vector<SUMOVehicle*> myChargingVehicles;
     225              : 
     226              :     /// @brief Parameter, Pointer to the electrical substation (by default is nullptr)
     227              :     MSTractionSubstation* myTractionSubstation;
     228              : 
     229              :     bool myVoltageSource;
     230              : 
     231              :     Element* myCircuitElementPos;
     232              :     Node* myCircuitStartNodePos;
     233              :     Node* myCircuitEndNodePos;
     234              : 
     235              : private:
     236              :     /// @brief Invalidated copy constructor.
     237              :     MSOverheadWire(const MSOverheadWire&);
     238              : 
     239              :     /// @brief Invalidated assignment operator.
     240              :     MSOverheadWire& operator=(const MSOverheadWire&);
     241              : };
     242              : 
     243              : 
     244              : /**
     245              : * @class MSTractionSubstation
     246              : * @brief Traction substation powering one or more overhead wire sections
     247              : */
     248              : class MSTractionSubstation : public Named {
     249              : public:
     250              : 
     251              :     /// @brief Constructor instantiates a substation providing certain voltage and a maximum current
     252              :     MSTractionSubstation(const std::string& substationId, double voltage, double currentLimit);
     253              : 
     254              :     /// @brief destructor
     255              :     ~MSTractionSubstation();
     256              : 
     257              :     Circuit* getCircuit() const {
     258         1604 :         return myCircuit;
     259              :     }
     260              :     void addOverheadWireSegmentToCircuit(MSOverheadWire* newOverheadWireSegment);
     261              : 
     262              :     void addOverheadWireClampToCircuit(const std::string id, MSOverheadWire* startSegment, MSOverheadWire* endSegment);
     263              : 
     264              :     void eraseOverheadWireSegmentFromCircuit(MSOverheadWire* oldWireSegment);
     265              : 
     266              :     void writeOut();
     267              :     std::size_t numberOfOverheadSegments() const {
     268              :         return myOverheadWireSegments.size();
     269              :     }
     270              : 
     271              :     /// @brief enable or disable charging vehicle
     272              :     void setChargingVehicle(bool value);
     273              : 
     274              :     /// @brief Return true if in the current time step the substation (overhead wire section) is charging a vehicle
     275              :     bool isCharging() const;
     276              : 
     277              :     void increaseElecHybridCount();
     278              : 
     279              :     void decreaseElecHybridCount();
     280              : 
     281              :     void addForbiddenLane(MSLane* lane);
     282              : 
     283              :     bool isForbidden(const MSLane* lane);
     284              : 
     285              :     void addClamp(const std::string& id, MSOverheadWire* startPos, MSOverheadWire* endPos);
     286              : 
     287              :     int getElecHybridCount() const {
     288           16 :         return myElecHybridCount;
     289              :     }
     290              : 
     291              :     void addVehicle(MSDevice_ElecHybrid* elecHybrid);
     292              : 
     293              :     void eraseVehicle(MSDevice_ElecHybrid* elecHybrid);
     294              : 
     295              :     double getSubstationVoltage() const {
     296            6 :         return mySubstationVoltage;
     297              :     }
     298              : 
     299              :     bool isAnySectionPreviouslyDefined();
     300              : 
     301              :     void addSolvingCircuitToEndOfTimestepEvents();
     302              :     SUMOTime solveCircuit(SUMOTime currentTime);
     303              : 
     304              :     /// @brief add charge value for output
     305              :     void addChargeValueForOutput(double energy, double current, double alpha, Circuit::alphaFlag alphaReason);
     306              : 
     307              :     /// @brief write traction substation values
     308              :     void writeTractionSubstationOutput(OutputDevice& output);
     309              : 
     310              : protected:
     311              :     /// @brief struct to save information for the traction substation output
     312              :     struct chargeTS {
     313              :         /// @brief constructor
     314          180 :         chargeTS(SUMOTime _timeStep, std::string _substationID, std::string _vehicleIDs, double _energy,
     315              :                  double _current, std::string _currentsString, double _voltage, std::string _status,
     316          180 :                  int _numVehicle, int _numVoltageSources, double _alpha, Circuit::alphaFlag _alphaReason) :
     317          180 :             timeStep(_timeStep),
     318          180 :             substationID(_substationID),
     319          180 :             vehicleIDs(_vehicleIDs),
     320          180 :             energy(_energy),
     321          180 :             current(_current),
     322          180 :             currentsString(_currentsString),
     323          180 :             voltage(_voltage),
     324          180 :             status(_status),
     325          180 :             numVehicles(_numVehicle),
     326          180 :             numVoltageSources(_numVoltageSources),
     327          180 :             alpha(_alpha),
     328          180 :             alphaReason(_alphaReason) {}
     329              : 
     330              :         // @brief vehicle TimeStep
     331              :         SUMOTime timeStep;
     332              :         // @brief substation ID
     333              :         std::string substationID;
     334              :         // @brief vehicle IDs
     335              :         std::string vehicleIDs;
     336              :         // @brief total power from voltage sources
     337              :         double energy;
     338              :         //@brief total current through voltage sources
     339              :         double current;
     340              :         // @brief list of all voltage currents
     341              :         std::string currentsString;
     342              :         //@brief voltage of voltage sources
     343              :         double voltage;
     344              :         /// @brief status
     345              :         std::string status;
     346              :         //@brief number of vehicles connected to the circuit
     347              :         int numVehicles;
     348              :         //@brief number of votlage sources connected to the section
     349              :         int numVoltageSources;
     350              :         //@brief best alpha scaling value
     351              :         double alpha;
     352              :         Circuit::alphaFlag alphaReason;
     353              :     };
     354              :     std::vector<chargeTS> myChargeValues;
     355              : 
     356              : public:
     357              :     //preparation of overhead wire clamp
     358            6 :     struct OverheadWireClamp {
     359              :         // @todo: 'MSTractionSubstation::overheadWireClamp' : no appropriate default constructor available
     360              :         // provide default constructor for vector construction below
     361              :         OverheadWireClamp() :
     362              :             id("undefined"),
     363              :             start(nullptr),
     364              :             end(nullptr),
     365              :             usage(false) {}
     366              : 
     367           11 :         OverheadWireClamp(const std::string _id, MSOverheadWire* _start, MSOverheadWire* _end, bool _usage):
     368              :             id(_id),
     369           11 :             start(_start),
     370           11 :             end(_end),
     371           11 :             usage(_usage) {}
     372              : 
     373              :         const std::string id;
     374              :         MSOverheadWire* start;
     375              :         MSOverheadWire* end;
     376              :         bool usage;
     377              :     };
     378              : 
     379              :     /// @brief Find an overhead wire clamp by its ID
     380              :     OverheadWireClamp* findClamp(std::string id);
     381              : 
     382              : private:
     383              :     void addOverheadWireInnerSegmentToCircuit(MSOverheadWire* incomingSegment, MSOverheadWire* outgoingSegment,
     384              :             const MSLane* connection, const MSLane* frontConnection, const MSLane* behindConnection);
     385              : 
     386              : protected:
     387              :     /// @brief Check if in the current TimeStep substation (overhead wire section) is charging a vehicle
     388              :     bool myChargingVehicle;
     389              :     int myElecHybridCount;
     390              : 
     391              : private:
     392              :     double mySubstationVoltage;
     393              :     Circuit* myCircuit;
     394              :     std::vector<MSOverheadWire*> myOverheadWireSegments;
     395              :     std::vector<MSDevice_ElecHybrid*> myElecHybrid;
     396              :     std::vector<MSLane*> myForbiddenLanes;
     397              :     static Command* myCommandForSolvingCircuit;
     398              :     double myTotalEnergy;
     399              : 
     400              :     // RICE_TODO: Does this cause the "'MSTractionSubstation::overheadWireClamp' : no appropriate default
     401              :     // constructor available" error in MSVC2013?
     402              :     // This is probably an issue with gitHub build chain
     403              :     std::vector<OverheadWireClamp> myOverheadWireClamps;
     404              : 
     405              : };
        

Generated by: LCOV version 2.0-1