Eclipse SUMO - Simulation of Urban MObility
Loading...
Searching...
No Matches
MSCFModel_Rail.cpp
Go to the documentation of this file.
1/****************************************************************************/
2// Eclipse SUMO, Simulation of Urban MObility; see https://eclipse.dev/sumo
3// Copyright (C) 2012-2023 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/****************************************************************************/
19// <description missing>
20/****************************************************************************/
21#include <config.h>
22
23#include <iostream>
26#include <microsim/MSVehicle.h>
28#include "MSCFModel_Rail.h"
29
31 MSCFModel(vtype) {
32 const std::string trainType = vtype->getParameter().getCFParamString(SUMO_ATTR_TRAIN_TYPE, "NGT400");
33 if (trainType.compare("RB425") == 0) {
35 } else if (trainType.compare("RB628") == 0) {
37 } else if (trainType.compare("NGT400") == 0) {
39 } else if (trainType.compare("NGT400_16") == 0) {
41 } else if (trainType.compare("ICE1") == 0) {
43 } else if (trainType.compare("REDosto7") == 0) {
45 } else if (trainType.compare("Freight") == 0) {
47 } else if (trainType.compare("ICE3") == 0) {
49 } else {
50 WRITE_ERRORF(TL("Unknown train type: %. Exiting!"), trainType);
51 throw ProcessError();
52 }
53 // override with user values
54 if (vtype->wasSet(VTYPEPARS_MAXSPEED_SET)) {
56 }
57 if (vtype->wasSet(VTYPEPARS_LENGTH_SET)) {
59 }
63 // update type parameters so they are shown correctly in the gui (if defaults from trainType are used)
64 const_cast<MSVehicleType*>(vtype)->setMaxSpeed(myTrainParams.vmax);
65 const_cast<MSVehicleType*>(vtype)->setLength(myTrainParams.length);
66
67}
68
70
71double MSCFModel_Rail::followSpeed(const MSVehicle* const veh, double speed, double gap,
72 double /* predSpeed */, double /* predMaxDecel*/, const MSVehicle* const /*pred*/, const CalcReason /*usage*/) const {
73
74 // followSpeed module is used for the simulation of moving block operations. The safety gap is chosen similar to the existing german
75 // system CIR-ELKE (based on LZB). Other implementations of moving block systems may differ, but for now no appropriate parameter
76 // can be set (would be per lane, not per train) -> hard-coded
77
78 // @note: default train minGap of 5 is already subtracted from gap
79 if (speed >= 30 / 3.6) {
80 // safety distance for higher speeds (>= 30 km/h)
81 gap = MAX2(0.0, gap + veh->getVehicleType().getMinGap() - 50);
82 }
83
84 const double vsafe = maximumSafeStopSpeed(gap, myDecel, speed, false, TS, false); // absolute breaking distance
85 const double vmin = minNextSpeed(speed, veh);
86 const double vmax = maxNextSpeed(speed, veh);
87
89 return MIN2(vsafe, vmax);
90 } else {
91 // ballistic
92 // XXX: the euler variant can break as strong as it wishes immediately! The ballistic cannot, refs. #2575.
93 return MAX2(MIN2(vsafe, vmax), vmin);
94 }
95}
96
97int
101
104 return new MSCFModel_Rail(vtype);
105}
106
107double MSCFModel_Rail::maxNextSpeed(double speed, const MSVehicle* const veh) const {
108
109 if (speed >= myTrainParams.vmax) {
110 return myTrainParams.vmax;
111 }
112
113 double targetSpeed = myTrainParams.vmax;
114
115 double res = getInterpolatedValueFromLookUpMap(speed, &(myTrainParams.resistance)); // kN
116
117 double slope = veh->getSlope();
118 double gr = myTrainParams.weight * GRAVITY * sin(DEG2RAD(slope)); //kN
119
120 double totalRes = res + gr; //kN
121
122 double trac = getInterpolatedValueFromLookUpMap(speed, &(myTrainParams.traction)); // kN
123
124 double a;
125 if (speed < targetSpeed) {
126 a = (trac - totalRes) / myTrainParams.rotWeight; //kN/t == N/kg
127 } else {
128 a = 0.;
129 if (totalRes > trac) {
130 a = (trac - totalRes) / myTrainParams.rotWeight; //kN/t == N/kg
131 }
132 }
133
134 double maxNextSpeed = speed + ACCEL2SPEED(a);
135
136// std::cout << veh->getID() << " speed: " << (speed*3.6) << std::endl;
137
138 return maxNextSpeed;
139}
140
141double MSCFModel_Rail::minNextSpeed(double speed, const MSVehicle* const veh) const {
142
143 const double slope = veh->getSlope();
144 const double gr = myTrainParams.weight * GRAVITY * sin(DEG2RAD(slope)); //kN
145 const double res = getInterpolatedValueFromLookUpMap(speed, &(myTrainParams.resistance)); // kN
146 const double totalRes = res + gr; //kN
147 const double a = myTrainParams.decl + totalRes / myTrainParams.rotWeight;
148 const double vMin = speed - ACCEL2SPEED(a);
150 return MAX2(vMin, 0.);
151 } else {
152 // NOTE: ballistic update allows for negative speeds to indicate a stop within the next timestep
153 return vMin;
154 }
155
156}
157
158
159double
160MSCFModel_Rail::minNextSpeedEmergency(double speed, const MSVehicle* const veh) const {
161 return minNextSpeed(speed, veh);
162}
163
164
165double MSCFModel_Rail::getInterpolatedValueFromLookUpMap(double speed, const LookUpMap* lookUpMap) const {
166 speed = speed * 3.6; // lookup values in km/h
167 std::map<double, double>::const_iterator low, prev;
168 low = lookUpMap->lower_bound(speed);
169
170 if (low == lookUpMap->end()) { //speed > max speed
171 return (lookUpMap->rbegin())->second;
172 }
173
174 if (low == lookUpMap->begin()) {
175 return low->second;
176 }
177
178 prev = low;
179 --prev;
180
181 double range = low->first - prev->first;
182 double dist = speed - prev->first;
183 assert(range > 0);
184 assert(dist > 0);
185
186 double weight = dist / range;
187
188 double res = (1 - weight) * prev->second + weight * low->second;
189
190 return res;
191
192}
193
194
195
196//void
197//MSCFModel_Rail::initVehicleVariables(const MSVehicle *const veh, MSCFModel_Rail::VehicleVariables *pVariables) const {
198//
199// pVariables->setInitialized();
200//
201//}
202
203double MSCFModel_Rail::getSpeedAfterMaxDecel(double /* speed */) const {
204
205// //TODO: slope not known here
206// double gr = 0; //trainParams.weight * GRAVITY * edge.grade
207//
208// double a = 0;//trainParams.decl - gr/trainParams.rotWeight;
209//
210// return speed + a * DELTA_T / 1000.;
211 WRITE_ERROR("function call not allowed for rail model. Exiting!");
212 throw ProcessError();
213}
214
219
220
221double MSCFModel_Rail::finalizeSpeed(MSVehicle* const veh, double vPos) const {
222 return MSCFModel::finalizeSpeed(veh, vPos);
223}
224
225double MSCFModel_Rail::freeSpeed(const MSVehicle* const /* veh */, double /* speed */, double dist, double targetSpeed,
226 const bool onInsertion, const CalcReason /*usage*/) const {
227
228// MSCFModel_Rail::VehicleVariables *vars = (MSCFModel_Rail::VehicleVariables *) veh->getCarFollowVariables();
229// if (vars->isNotYetInitialized()) {
230// initVehicleVariables(veh, vars);
231// }
232
233 //TODO: signals, coasting, ...
234
236 // adapt speed to succeeding lane, no reaction time is involved
237 // when breaking for y steps the following distance g is covered
238 // (drive with v in the final step)
239 // g = (y^2 + y) * 0.5 * b + y * v
240 // y = ((((sqrt((b + 2.0*v)*(b + 2.0*v) + 8.0*b*g)) - b)*0.5 - v)/b)
241 const double v = SPEED2DIST(targetSpeed);
242 if (dist < v) {
243 return targetSpeed;
244 }
245 const double b = ACCEL2DIST(myDecel);
246 const double y = MAX2(0.0, ((sqrt((b + 2.0 * v) * (b + 2.0 * v) + 8.0 * b * dist) - b) * 0.5 - v) / b);
247 const double yFull = floor(y);
248 const double exactGap = (yFull * yFull + yFull) * 0.5 * b + yFull * v + (y > yFull ? v : 0.0);
249 const double fullSpeedGain = (yFull + (onInsertion ? 1. : 0.)) * ACCEL2SPEED(myTrainParams.decl);
250 return DIST2SPEED(MAX2(0.0, dist - exactGap) / (yFull + 1)) + fullSpeedGain + targetSpeed;
251 } else {
252 WRITE_ERROR(TL("Anything else than semi implicit euler update is not yet implemented. Exiting!"));
253 throw ProcessError();
254 }
255}
256
257double MSCFModel_Rail::stopSpeed(const MSVehicle* const veh, const double speed, double gap, double decel, const CalcReason /*usage*/) const {
258 return MIN2(maximumSafeStopSpeed(gap, decel, speed, false, TS, false), maxNextSpeed(speed, veh));
259}
#define DEG2RAD(x)
Definition GeomHelper.h:35
#define GRAVITY
Definition GeomHelper.h:37
#define WRITE_ERRORF(...)
Definition MsgHandler.h:280
#define WRITE_ERROR(msg)
Definition MsgHandler.h:279
#define TL(string)
Definition MsgHandler.h:287
#define SPEED2DIST(x)
Definition SUMOTime.h:45
#define ACCEL2SPEED(x)
Definition SUMOTime.h:51
#define TS
Definition SUMOTime.h:42
#define DIST2SPEED(x)
Definition SUMOTime.h:47
#define ACCEL2DIST(x)
Definition SUMOTime.h:49
const long long int VTYPEPARS_MAXSPEED_SET
const long long int VTYPEPARS_LENGTH_SET
@ SUMO_TAG_CF_RAIL
@ SUMO_ATTR_TRAIN_TYPE
@ SUMO_ATTR_DECEL
@ SUMO_ATTR_EMERGENCYDECEL
T MIN2(T a, T b)
Definition StdDefs.h:76
T MAX2(T a, T b)
Definition StdDefs.h:82
const MSVehicleType & getVehicleType() const
Returns the vehicle's type definition.
TrainParams initICE3Params() const
TrainParams initNGT400_16Params() const
virtual ~MSCFModel_Rail()
TrainParams initREDosto7Params() const
MSCFModel::VehicleVariables * createVehicleVariables() const
Returns model specific values which are stored inside a vehicle and must be used with casting.
virtual double minNextSpeedEmergency(double speed, const MSVehicle *const veh=0) const
Returns the minimum speed after emergency braking, given the current speed (depends on the numerical ...
TrainParams initICE1Params() const
MSCFModel_Rail(const MSVehicleType *vtype)
Constructor.
double freeSpeed(const MSVehicle *const veh, double speed, double seen, double maxSpeed, const bool onInsertion, const CalcReason usage=CalcReason::CURRENT) const
Computes the vehicle's safe speed without a leader.
TrainParams initRB628Params() const
double getInterpolatedValueFromLookUpMap(double speed, const LookUpMap *lookUpMap) const
virtual MSCFModel * duplicate(const MSVehicleType *vtype) const
Duplicates the car-following model.
virtual int getModelID() const
Returns the model's ID; the XML-Tag number is used.
double getSpeedAfterMaxDecel(double v) const
Returns the velocity after maximum deceleration.
TrainParams myTrainParams
virtual double minNextSpeed(double speed, const MSVehicle *const veh) const
Returns the minimum speed given the current speed (depends on the numerical update scheme and its ste...
double followSpeed(const MSVehicle *const veh, double speed, double gap2pred, double predSpeed, double predMaxDecel, const MSVehicle *const pred=0, const CalcReason usage=CalcReason::CURRENT) const
Computes the vehicle's follow speed (no dawdling)
TrainParams initRB425Params() const
TrainParams initFreightParams() const
virtual double maxNextSpeed(double speed, const MSVehicle *const veh) const
Returns the maximum speed given the current speed.
TrainParams initNGT400Params() const
std::map< double, double > LookUpMap
double finalizeSpeed(MSVehicle *const veh, double vPos) const
Applies interaction with stops and lane changing model influences. Called at most once per simulation...
double stopSpeed(const MSVehicle *const veh, const double speed, double gap, double decel, const CalcReason usage=CalcReason::CURRENT) const
Computes the vehicle's safe speed for approaching a non-moving obstacle (no dawdling)
The car-following model abstraction.
Definition MSCFModel.h:55
virtual void setEmergencyDecel(double decel)
Sets a new value for maximal physically possible deceleration [m/s^2].
Definition MSCFModel.h:544
virtual double finalizeSpeed(MSVehicle *const veh, double vPos) const
Applies interaction with stops and lane changing model influences. Called at most once per simulation...
virtual void setMaxDecel(double decel)
Sets a new value for maximal comfortable deceleration [m/s^2].
Definition MSCFModel.h:536
CalcReason
What the return value of stop/follow/free-Speed is used for.
Definition MSCFModel.h:77
double myDecel
The vehicle's maximum deceleration [m/s^2].
Definition MSCFModel.h:695
double maximumSafeStopSpeed(double gap, double decel, double currentSpeed, bool onInsertion=false, double headway=-1, bool relaxEmergency=true) const
Returns the maximum next velocity for stopping within gap.
static bool gSemiImplicitEulerUpdate
Definition MSGlobals.h:53
Representation of a vehicle in the micro simulation.
Definition MSVehicle.h:77
double getSlope() const
Returns the slope of the road at vehicle's position in degrees.
The car-following model and parameter.
double getMaxSpeed() const
Get vehicle's (technical) maximum speed [m/s].
double getMinGap() const
Get the free space in front of vehicles of this class.
double getLength() const
Get vehicle's length [m].
bool wasSet(int what) const
Returns whether the given parameter was set.
const SUMOVTypeParameter & getParameter() const
double getCFParam(const SumoXMLAttr attr, const double defaultValue) const
Returns the named value from the map, or the default if it is not contained there.
std::string getCFParamString(const SumoXMLAttr attr, const std::string defaultValue) const
Returns the named value from the map, or the default if it is not contained there.