Eclipse SUMO - Simulation of Urban MObility
MSCFModel_Krauss.cpp
Go to the documentation of this file.
1 /****************************************************************************/
2 // Eclipse SUMO, Simulation of Urban MObility; see https://eclipse.dev/sumo
3 // Copyright (C) 2001-2024 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 /****************************************************************************/
22 // Krauss car-following model, with acceleration decrease and faster start
23 /****************************************************************************/
24 #include <config.h>
25 
26 #include <microsim/MSVehicle.h>
27 #include <microsim/MSLane.h>
28 #include <microsim/MSGlobals.h>
29 #include "MSCFModel_Krauss.h"
32 
33 
34 
35 // ===========================================================================
36 // DEBUG constants
37 // ===========================================================================
38 //#define DEBUG_COND (true)
39 #define DEBUG_COND (veh->isSelected())
40 #define DEBUG_DRIVER_ERRORS
41 
43  : accelDawdle(1e6), updateOffset(SIMSTEP % dawdleStep + DELTA_T) { }
44 
45 // ===========================================================================
46 // method definitions
47 // ===========================================================================
49  MSCFModel_KraussOrig1(vtype),
51  if (myDawdleStep % DELTA_T != 0) {
53  if (rem < DELTA_T / 2) {
54  myDawdleStep += -rem;
55  } else {
56  myDawdleStep += DELTA_T - rem;
57  }
58  WRITE_WARNINGF(TL("Rounding 'sigmaStep' to % for vType '%'"), STEPS2TIME(myDawdleStep), vtype->getID());
59 
60  }
61 }
62 
63 
65 
66 
67 double
68 MSCFModel_Krauss::patchSpeedBeforeLC(const MSVehicle* veh, double vMin, double vMax) const {
69  const double sigma = (veh->passingMinor()
71  : myDawdle);
72  double vDawdle;
73  if (myDawdleStep > DELTA_T) {
75  if (SIMSTEP % myDawdleStep == vars->updateOffset) {
76  const double vD = MAX2(vMin, dawdle2(vMax, sigma, veh->getRNG()));
77  const double a1 = SPEED2ACCEL(vMax - veh->getSpeed());
78  const double a2 = SPEED2ACCEL(vD - vMax);
79  const double accelMax = (veh->getLane()->getVehicleMaxSpeed(veh) - veh->getSpeed()) / STEPS2TIME(myDawdleStep);
80  // avoid exceeding maxSpeed before the next sigmaStep
81  vars->accelDawdle = MIN2(a1, accelMax) + a2;
82  vDawdle = veh->getSpeed() + ACCEL2SPEED(vars->accelDawdle);
83  //std::cout << SIMTIME << " v=" << veh->getSpeed() << " updated vD=" << vD<< " a1=" << a1 << " a2=" << a2 << " aM=" << accelMax << " accelDawdle=" << vars->accelDawdle << " vDawdle=" << vDawdle << "\n";
84  } else {
85  const double safeAccel = SPEED2ACCEL(vMax - veh->getSpeed());
86  const double accel = MIN2(safeAccel, vars->accelDawdle);
87  vDawdle = MAX2(vMin, MIN2(vMax, veh->getSpeed() + ACCEL2SPEED(accel)));
88  //std::cout << SIMTIME << " v=" << veh->getSpeed() << " safeAccel=" << safeAccel << " accel=" << accel << " vDawdle=" << vDawdle << "\n";
89  }
90  } else {
91  vDawdle = MAX2(vMin, dawdle2(vMax, sigma, veh->getRNG()));
92  //const double accel1 = SPEED2ACCEL(vMax - veh->getSpeed());
93  //const double accel2 = SPEED2ACCEL(vDawdle - vMax);
94  //std::cout << SIMTIME << " v=" << veh->getSpeed() << " updated vDawdle=" << vDawdle << " a1=" << accel1 << " a2=" << accel2 << " accelDawdle=" << SPEED2ACCEL(vDawdle - veh->getSpeed()) << "\n";
95  }
96  return vDawdle;
97 }
98 
99 
100 double
101 MSCFModel_Krauss::stopSpeed(const MSVehicle* const veh, const double speed, double gap, double decel, const CalcReason usage) const {
102  // NOTE: This allows return of smaller values than minNextSpeed().
103  // Only relevant for the ballistic update: We give the argument headway=veh->getActionStepLengthSecs(), to assure that
104  // the stopping position is approached with a uniform deceleration also for tau!=veh->getActionStepLengthSecs().
105  applyHeadwayPerceptionError(veh, speed, gap);
106  const bool relaxEmergency = usage != FUTURE; // do not relax insertionStopSpeed
107  return MIN2(maximumSafeStopSpeed(gap, decel, speed, false, veh->getActionStepLengthSecs(), relaxEmergency), maxNextSpeed(speed, veh));
108 }
109 
110 
111 double
112 MSCFModel_Krauss::followSpeed(const MSVehicle* const veh, double speed, double gap, double predSpeed, double predMaxDecel, const MSVehicle* const pred, const CalcReason /*usage*/) const {
113  //gDebugFlag1 = DEBUG_COND;
114  applyHeadwayAndSpeedDifferencePerceptionErrors(veh, speed, gap, predSpeed, predMaxDecel, pred);
115  //gDebugFlag1 = DEBUG_COND; // enable for DEBUG_EMERGENCYDECEL
116  const double vsafe = maximumSafeFollowSpeed(gap, speed, predSpeed, predMaxDecel);
117  //gDebugFlag1 = false;
118  const double vmin = minNextSpeedEmergency(speed);
119  const double vmax = maxNextSpeed(speed, veh);
121  return MIN2(vsafe, vmax);
122  } else {
123  // ballistic
124  // XXX: the euler variant can break as strong as it wishes immediately! The ballistic cannot, refs. #2575.
125  return MAX2(MIN2(vsafe, vmax), vmin);
126  }
127 }
128 
129 double
130 MSCFModel_Krauss::dawdle2(double speed, double sigma, SumoRNG* rng) const {
132  // in case of the ballistic update, negative speeds indicate
133  // a desired stop before the completion of the next timestep.
134  // We do not allow dawdling to overwrite this indication
135  if (speed < 0) {
136  return speed;
137  }
138  }
139  // generate random number out of [0,1)
140  const double random = RandHelper::rand(rng);
141  // Dawdle.
142  if (speed < myAccel) {
143  // we should not prevent vehicles from driving just due to dawdling
144  // if someone is starting, he should definitely start
145  // (but what about slow-to-start?)!!!
146  speed -= ACCEL2SPEED(sigma * speed * random);
147  } else {
148  speed -= ACCEL2SPEED(sigma * myAccel * random);
149  }
150  return MAX2(0., speed);
151 }
152 
153 
154 MSCFModel*
156  return new MSCFModel_Krauss(vtype);
157 }
158 
159 
160 /****************************************************************************/
long long int SUMOTime
Definition: GUI.h:35
#define WRITE_WARNINGF(...)
Definition: MsgHandler.h:296
#define TL(string)
Definition: MsgHandler.h:315
SUMOTime DELTA_T
Definition: SUMOTime.cpp:38
#define STEPS2TIME(x)
Definition: SUMOTime.h:55
#define SIMSTEP
Definition: SUMOTime.h:61
#define ACCEL2SPEED(x)
Definition: SUMOTime.h:51
#define TS
Definition: SUMOTime.h:42
#define TIME2STEPS(x)
Definition: SUMOTime.h:57
#define SPEED2ACCEL(x)
Definition: SUMOTime.h:53
@ SUMO_ATTR_SIGMA_STEP
@ SUMO_ATTR_JM_SIGMA_MINOR
T MIN2(T a, T b)
Definition: StdDefs.h:76
T MAX2(T a, T b)
Definition: StdDefs.h:82
SumoRNG * getRNG() const
const MSVehicleType & getVehicleType() const
Returns the vehicle's type definition.
double accelDawdle
the accleration due to dawdling
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 safe speed (no dawdling) this uses the maximumSafeFollowSpeed.
MSCFModel * duplicate(const MSVehicleType *vtype) const
Duplicates the car-following model.
double patchSpeedBeforeLC(const MSVehicle *veh, double vMin, double vMax) const
apply custom speed adaptations within the given speed bounds
double dawdle2(double speed, double sigma, SumoRNG *rng) const
Applies driver imperfection (dawdling / sigma)
~MSCFModel_Krauss()
Destructor.
MSCFModel_Krauss(const MSVehicleType *vtype)
Constructor.
double stopSpeed(const MSVehicle *const veh, const double speed, double gap2pred, double decel, const CalcReason usage=CalcReason::CURRENT) const
Computes the vehicle's safe speed for approaching a non-moving obstacle (no dawdling) this uses the m...
SUMOTime myDawdleStep
The vehicle's update period for dawdling.
The original Krauss (1998) car-following model and parameter.
virtual double vsafe(double gap, double predSpeed, double predMaxDecel) const
Returns the "safe" velocity.
double myDawdle
The vehicle's dawdle-parameter. 0 for no dawdling, 1 for max.
The car-following model abstraction.
Definition: MSCFModel.h:55
virtual double maxNextSpeed(double speed, const MSVehicle *const veh) const
Returns the maximum speed given the current speed.
Definition: MSCFModel.cpp:292
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 ...
Definition: MSCFModel.cpp:309
virtual std::string getParameter(const MSVehicle *veh, const std::string &key) const
try to get the given parameter for this carFollowingModel
Definition: MSCFModel.h:646
void applyHeadwayPerceptionError(const MSVehicle *const veh, double speed, double &gap) const
Overwrites gap by the perceived value obtained from the vehicle's driver state.
Definition: MSCFModel.cpp:1099
void applyHeadwayAndSpeedDifferencePerceptionErrors(const MSVehicle *const veh, double speed, double &gap, double &predSpeed, double predMaxDecel, const MSVehicle *const pred) const
Overwrites gap2pred and predSpeed by the perceived values obtained from the vehicle's driver state,...
Definition: MSCFModel.cpp:1063
double maximumSafeFollowSpeed(double gap, double egoSpeed, double predSpeed, double predMaxDecel, bool onInsertion=false) const
Returns the maximum safe velocity for following the given leader.
Definition: MSCFModel.cpp:922
CalcReason
What the return value of stop/follow/free-Speed is used for.
Definition: MSCFModel.h:77
@ FUTURE
the return value is used for calculating future speeds
Definition: MSCFModel.h:81
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.
Definition: MSCFModel.cpp:774
double myAccel
The vehicle's maximum acceleration [m/s^2].
Definition: MSCFModel.h:698
static bool gSemiImplicitEulerUpdate
Definition: MSGlobals.h:53
double getVehicleMaxSpeed(const SUMOTrafficObject *const veh) const
Returns the lane's maximum speed, given a vehicle's speed limit adaptation.
Definition: MSLane.h:566
Representation of a vehicle in the micro simulation.
Definition: MSVehicle.h:77
double getActionStepLengthSecs() const
Returns the vehicle's action step length in secs, i.e. the interval between two action points.
Definition: MSVehicle.h:536
bool passingMinor() const
decide whether the vehicle is passing a minor link or has comitted to do so
Definition: MSVehicle.cpp:7321
MSCFModel::VehicleVariables * getCarFollowVariables() const
Returns the vehicle's car following model variables.
Definition: MSVehicle.h:995
double getSpeed() const
Returns the vehicle's current speed.
Definition: MSVehicle.h:493
const MSLane * getLane() const
Returns the lane the vehicle is on.
Definition: MSVehicle.h:584
The car-following model and parameter.
Definition: MSVehicleType.h:63
const std::string & getID() const
Returns the name of the vehicle type.
Definition: MSVehicleType.h:91
const SUMOVTypeParameter & getParameter() const
static double rand(SumoRNG *rng=nullptr)
Returns a random real number in [0, 1)
Definition: RandHelper.cpp:94
double getJMParam(const SumoXMLAttr attr, const double defaultValue) const
Returns the named value from the map, or the default if it is not contained there.