61 MSLane*
const lane,
const double length,
const bool doAdd,
63 MSMoveReminder(
"meandata_" + (lane == nullptr ?
"NULL" : lane->getID()), lane, doAdd),
67 travelledDistance(0) {}
76#ifdef DEBUG_NOTIFY_ENTER
77 std::cout <<
"\n" <<
SIMTIME <<
" MSMeanData_Net::MSLaneMeanDataValues: veh '" << veh.
getID() <<
"' enters lane '" << enteredLane->
getID() <<
"'" << std::endl;
82 return myParent ==
nullptr || myParent->vehicleApplies(veh);
92 double leaveSpeed = newSpeed, leaveSpeedFront = newSpeed;
95 double timeOnLane =
TS;
96 double frontOnLane = oldPos > myLaneLength ? 0. :
TS;
100 double timeBeforeEnter = 0.;
101 double timeBeforeEnterBack = 0.;
102 double timeBeforeLeaveFront = newPos <= myLaneLength ?
TS : 0.;
103 double timeBeforeLeave =
TS;
106 if (oldPos < 0 && newPos >= 0) {
109 timeOnLane =
TS - timeBeforeEnter;
110 frontOnLane = timeOnLane;
118 if (oldBackPos < 0. && newBackPos > 0.) {
120 }
else if (newBackPos <= 0) {
121 timeBeforeEnterBack =
TS;
123 timeBeforeEnterBack = 0.;
127 if (newBackPos > myLaneLength
128 && oldBackPos <= myLaneLength) {
132 const double timeAfterLeave =
TS - timeBeforeLeave;
133 timeOnLane -= timeAfterLeave;
136 if (fabs(timeOnLane) < NUMERICAL_EPS) {
143 if (newPos > myLaneLength && oldPos <= myLaneLength) {
147 const double timeAfterLeave =
TS - timeBeforeLeaveFront;
148 frontOnLane -= timeAfterLeave;
150 if (fabs(frontOnLane) < NUMERICAL_EPS) {
156 assert(frontOnLane <=
TS);
157 assert(timeOnLane <=
TS);
159 if (timeOnLane < 0) {
163 if (timeOnLane == 0) {
167#ifdef DEBUG_NOTIFY_MOVE
168 std::stringstream ss;
170 <<
"lane length: " << myLaneLength
171 <<
"\noldPos: " << oldPos
172 <<
"\nnewPos: " << newPos
173 <<
"\noldPosBack: " << oldBackPos
174 <<
"\nnewPosBack: " << newBackPos
175 <<
"\ntimeBeforeEnter: " << timeBeforeEnter
176 <<
"\ntimeBeforeEnterBack: " << timeBeforeEnterBack
177 <<
"\ntimeBeforeLeaveFront: " << timeBeforeLeaveFront
178 <<
"\ntimeBeforeLeave: " << timeBeforeLeave;
179 if (!(timeBeforeLeave >=
MAX2(timeBeforeEnterBack, timeBeforeLeaveFront))
180 || !(timeBeforeEnter <=
MIN2(timeBeforeEnterBack, timeBeforeLeaveFront))) {
183 std::cout << ss.str() << std::endl;
188 assert(timeBeforeEnter <=
MIN2(timeBeforeEnterBack, timeBeforeLeaveFront));
189 assert(timeBeforeLeave >=
MAX2(timeBeforeEnterBack, timeBeforeLeaveFront));
193 double lengthOnLaneAtStepStart =
MAX2(0.,
MIN4(myLaneLength, vehLength, vehLength - (oldPos - myLaneLength), oldPos));
195 double lengthOnLaneAtStepEnd =
MAX2(0.,
MIN4(myLaneLength, vehLength, vehLength - (newPos - myLaneLength), newPos));
196 double integratedLengthOnLane = 0.;
197 if (timeBeforeEnterBack < timeBeforeLeaveFront) {
202 integratedLengthOnLane += (timeBeforeEnterBack - timeBeforeEnter) * (lengthOnLaneAtBackEnter + lengthOnLaneAtStepStart) * 0.5;
205 integratedLengthOnLane += (timeBeforeLeaveFront - timeBeforeEnterBack) * vehLength;
207 integratedLengthOnLane += (timeBeforeLeave - timeBeforeLeaveFront) * (vehLength + lengthOnLaneAtStepEnd) * 0.5;
208 }
else if (timeBeforeEnterBack >= timeBeforeLeaveFront) {
211 double lengthOnLaneAtLeaveFront;
212 if (timeBeforeLeaveFront == timeBeforeEnter) {
214 lengthOnLaneAtLeaveFront = lengthOnLaneAtStepStart;
215 }
else if (timeBeforeLeaveFront == timeBeforeLeave) {
217 lengthOnLaneAtLeaveFront = lengthOnLaneAtStepEnd;
219 lengthOnLaneAtLeaveFront = myLaneLength;
221#ifdef DEBUG_NOTIFY_MOVE
222 std::cout <<
"lengthOnLaneAtLeaveFront=" << lengthOnLaneAtLeaveFront << std::endl;
225 integratedLengthOnLane += (timeBeforeLeaveFront - timeBeforeEnter) * (lengthOnLaneAtLeaveFront + lengthOnLaneAtStepStart) * 0.5;
227 integratedLengthOnLane += (timeBeforeEnterBack - timeBeforeLeaveFront) * lengthOnLaneAtLeaveFront;
229 integratedLengthOnLane += (timeBeforeLeave - timeBeforeEnterBack) * (lengthOnLaneAtLeaveFront + lengthOnLaneAtStepEnd) * 0.5;
232 double meanLengthOnLane = integratedLengthOnLane /
TS;
233#ifdef DEBUG_NOTIFY_MOVE
234 std::cout <<
"Calculated mean length on lane '" << myLane->getID() <<
"' in last step as " << meanLengthOnLane
235 <<
"\nlengthOnLaneAtStepStart=" << lengthOnLaneAtStepStart <<
", lengthOnLaneAtStepEnd=" << lengthOnLaneAtStepEnd <<
", integratedLengthOnLane=" << integratedLengthOnLane
244 :
MAX2(0.,
MIN2(newPos, myLaneLength) -
MAX2(oldPos, 0.));
254 notifyMoveInternal(veh, frontOnLane, timeOnLane, (enterSpeed + leaveSpeedFront) / 2., (enterSpeed + leaveSpeed) / 2., travelledDistanceFrontOnLane, travelledDistanceVehicleOnLane, meanLengthOnLane);
270 return sampleSeconds == 0;
281 return sampleSeconds;
297 std::list<TrackerEntry*>::iterator i;
298 for (i = myCurrentData.begin(); i != myCurrentData.end(); i++) {
315 if (myCurrentData.begin() != myCurrentData.end()) {
317 myCurrentData.pop_front();
320 myCurrentData.push_back(
new TrackerEntry(myParent->createValues(myLane, myLaneLength,
false)));
327 myCurrentData.front()->myValues->
addTo(val);
333 myTrackedData[&veh]->myValues->notifyMoveInternal(veh, frontOnLane, timeOnLane, meanSpeedFrontOnLane, meanSpeedVehicleOnLane, travelledDistanceFrontOnLane, travelledDistanceVehicleOnLane, meanLengthOnLane);
340 myTrackedData[&veh]->myNumVehicleLeft++;
342 return myTrackedData[&veh]->myValues->notifyLeave(veh, lastPos, reason);
348#ifdef DEBUG_NOTIFY_ENTER
349 std::cout <<
"\n" <<
SIMTIME <<
" MSMeanData::MeanDataValueTracker: veh '" << veh.
getID() <<
"' enters lane '" << enteredLane->
getID() <<
"'" << std::endl;
356 if (myParent->vehicleApplies(veh) && myTrackedData.find(&veh) == myTrackedData.end()) {
357 myTrackedData[&veh] = myCurrentData.back();
358 myTrackedData[&veh]->myNumVehicleEntered++;
359 if (!myTrackedData[&veh]->myValues->notifyEnter(veh, reason)) {
360 myTrackedData[&veh]->myNumVehicleLeft++;
361 myTrackedData.erase(&veh);
372 return myCurrentData.front()->myValues->isEmpty();
378 long long int attributeMask,
381 const double speedLimit,
382 const double defaultTravelTime,
384 myCurrentData.front()->myValues->write(dev, attributeMask, period, numLanes, speedLimit,
386 myCurrentData.front()->myNumVehicleEntered);
393 for (std::list<TrackerEntry*>::const_iterator it = myCurrentData.begin(); it != myCurrentData.end(); ++it) {
394 if ((*it)->myNumVehicleEntered == (*it)->myNumVehicleLeft) {
406 return myCurrentData.front()->myValues->getSamples();
415 const bool useLanes,
const bool withEmpty,
416 const bool printDefaults,
const bool withInternal,
417 const bool trackVehicles,
419 const double maxTravelTime,
420 const double minSamples,
421 const std::string& vTypes,
422 const std::string& writeAttributes,
423 const std::vector<MSEdge*>& edges,
456 myMeasures.push_back(std::vector<MeanDataValues*>());
458 const std::vector<MSLane*>& lanes = edge->getLanes();
462 for (
MSLane*
const lane : lanes) {
463 data =
createValues(lane, lanes[0]->getLength(),
false);
466 while (s !=
nullptr) {
478 data =
createValues(
nullptr, lanes[0]->getLength(),
false);
483 while (s !=
nullptr) {
496 for (
MSLane*
const lane : lanes) {
499 lane->addMoveReminder(
myMeasures.back().back());
512 for (std::vector<std::vector<MeanDataValues*> >::const_iterator i =
myMeasures.begin(); i !=
myMeasures.end(); ++i) {
513 for (std::vector<MeanDataValues*>::const_iterator j = (*i).begin(); j != (*i).end(); ++j) {
524 MSEdgeVector::iterator edge =
myEdges.begin();
525 for (std::vector<std::vector<MeanDataValues*> >::const_iterator i =
myMeasures.begin(); i !=
myMeasures.end(); ++i, ++edge) {
528 while (s !=
nullptr) {
537 for (std::vector<std::vector<MeanDataValues*> >::const_iterator i =
myMeasures.begin(); i !=
myMeasures.end(); ++i) {
538 for (std::vector<MeanDataValues*>::const_iterator j = (*i).begin(); j != (*i).end(); ++j) {
547 return edge->
getID();
554 throw ProcessError(
TL(
"aggregated meanData output not yet implemented for trackVehicles"));
557 double edgeLengthSum = 0;
562 edgeLengthSum += edge->getLength();
563 laneNumber += edge->getNumDrivingLanes();
564 speedSum += edge->getSpeedLimit();
565 totalTT += edge->getLength() / edge->getSpeedLimit();
568 for (
const std::vector<MeanDataValues*>& edgeValues :
myMeasures) {
570 meanData->addTo(*sumData);
579 while (s !=
nullptr) {
597 const std::vector<MeanDataValues*>& edgeValues,
603 while (s !=
nullptr) {
623 std::vector<MeanDataValues*>::const_iterator lane;
627 for (lane = edgeValues.begin(); lane != edgeValues.end(); ++lane) {
628 if (!(*lane)->isEmpty()) {
637 for (lane = edgeValues.begin(); lane != edgeValues.end(); ++lane) {
644 meanData.
reset(
true);
658 meanData.
reset(
true);
662 for (lane = edgeValues.begin(); lane != edgeValues.end(); ++lane) {
664 meanData.
addTo(*sumData);
706 for (std::vector<std::vector<MeanDataValues*> >::const_iterator i =
myMeasures.begin(); i !=
myMeasures.end(); ++i) {
707 for (std::vector<MeanDataValues*>::const_iterator j = (*i).begin(); j != (*i).end(); ++j) {
718 const bool partialInterval = startTime <
myInitTime;
722 if (partialInterval) {
725 while (numReady-- > 0) {
735 MSEdgeVector::const_iterator edge =
myEdges.begin();
736 for (
const std::vector<MeanDataValues*>& measures :
myMeasures) {
737 writeEdge(dev, measures, *edge, startTime, stopTime);
763 long long int result = 0;
766 WRITE_ERRORF(
TL(
"Unknown attribute '%' to write in meanData '%'."), attrName,
id);
771 result |= ((
long long int)1 << attr);
776const std::vector<MSMeanData::MeanDataValues*>*
#define WRITE_ERRORF(...)
std::string time2string(SUMOTime t, bool humanReadable)
convert SUMOTime to string (independently of global format setting)
SumoXMLTag
Numbers representing SUMO-XML - element names.
@ SUMO_TAG_INTERVAL
an aggreagated-output interval
@ SUMO_TAG_LANE
begin/end of the description of a single lane
@ SUMO_TAG_EDGE
begin/end of the description of an edge
@ SUMO_ATTR_BEGIN
weights: time range begin
@ SUMO_ATTR_END
weights: time range end
@ SUMO_ATTR_SAMPLEDSECONDS
MSMeanData_Net.
T MIN4(T a, T b, T c, T d)
#define UNUSED_PARAMETER(x)
MESegment * getSegmentForEdge(const MSEdge &e, double pos=0)
Get the segment for a given edge at a given position.
A single mesoscopic segment (cell)
void addDetector(MSMoveReminder *data, int queueIndex=-1)
Adds a data collector for a detector to this segment.
void prepareDetectorForWriting(MSMoveReminder &data, int queueIndex=-1)
Removes a data collector for a detector from this segment.
MESegment * getNextSegment() const
Returns the following segment on the same edge (0 if it is the last).
static double speedAfterTime(const double t, const double oldSpeed, const double dist)
Calculates the speed after a time t \in [0,TS] given the initial speed and the distance traveled in a...
static double passingTime(const double lastPos, const double passedPos, const double currentPos, const double lastSpeed, const double currentSpeed)
Calculates the time at which the position passedPosition has been passed In case of a ballistic updat...
Base of value-generating classes (detectors)
bool detectPersons() const
const MSEdgeVector & getEdges() const
Returns loaded edges.
A road/street connecting two junctions.
int getNumDrivingLanes() const
return the number of lanes that permit non-weak modes if the edge allows non weak modes and the numbe...
double getSpeedLimit() const
Returns the speed limit of the edge @caution The speed limit of the first lane is retured; should pro...
double getLength() const
return the length of the edge
static MELoop * gMesoNet
mesoscopic simulation infrastructure
static bool gSemiImplicitEulerUpdate
static int gNumSimThreads
how many threads to use for simulation
Representation of a lane in the micro simulation.
double getSpeedLimit() const
Returns the lane's maximum allowed speed.
double getLength() const
Returns the lane's length.
Data structure for mean (aggregated) edge/lane values for tracked vehicles.
double getSamples() const
Returns the number of collected sample seconds.
MeanDataValueTracker(MSLane *const lane, const double length, const MSMeanData *const parent)
Constructor.
bool notifyLeave(SUMOTrafficObject &veh, double lastPos, MSMoveReminder::Notification reason, const MSLane *enteredLane=0)
Called if the vehicle leaves the reminder's lane.
void addTo(MSMeanData::MeanDataValues &val) const
Add the values of this to the given one and store them there.
void notifyMoveInternal(const SUMOTrafficObject &veh, const double frontOnLane, const double timeOnLane, const double meanSpeedFrontOnLane, const double meanSpeedVehicleOnLane, const double travelledDistanceFrontOnLane, const double travelledDistanceVehicleOnLane, const double meanLengthOnLane)
Internal notification about the vehicle moves.
virtual ~MeanDataValueTracker()
Destructor.
void write(OutputDevice &dev, long long int attributeMask, const SUMOTime period, const int numLanes, const double speedLimit, const double defaultTravelTime, const int numVehicles=-1) const
Writes output values into the given stream.
bool notifyEnter(SUMOTrafficObject &veh, MSMoveReminder::Notification reason, const MSLane *enteredLane=0)
Computes current values and adds them to their sums.
std::list< TrackerEntry * > myCurrentData
The currently active meandata "intervals".
bool isEmpty() const
Returns whether any data was collected.
void reset(bool afterWrite)
Resets values so they may be used for the next interval.
Data structure for mean (aggregated) edge/lane values.
virtual void addTo(MeanDataValues &val) const =0
Add the values of this to the given one and store them there.
virtual bool notifyLeave(SUMOTrafficObject &veh, double lastPos, MSMoveReminder::Notification reason, const MSLane *enteredLane=0)
Called if the vehicle leaves the reminder's lane.
MeanDataValues(MSLane *const lane, const double length, const bool doAdd, const MSMeanData *const parent)
Constructor.
virtual void update()
Called if a per timestep update is needed. Default does nothing.
virtual bool isEmpty() const
Returns whether any data was collected.
virtual void write(OutputDevice &dev, long long int attributeMask, const SUMOTime period, const int numLanes, const double speedLimit, const double defaultTravelTime, const int numVehicles=-1) const =0
Writes output values into the given stream.
bool notifyMove(SUMOTrafficObject &veh, double oldPos, double newPos, double newSpeed)
Checks whether the reminder still has to be notified about the vehicle moves.
virtual ~MeanDataValues()
Destructor.
virtual void reset(bool afterWrite=false)=0
Resets values so they may be used for the next interval.
virtual bool notifyEnter(SUMOTrafficObject &veh, MSMoveReminder::Notification reason, const MSLane *enteredLane=0)
Called if the vehicle enters the reminder's lane.
virtual double getSamples() const
Returns the number of collected sample seconds.
Data collector for edges/lanes.
virtual MSMeanData::MeanDataValues * createValues(MSLane *const lane, const double length, const bool doAdd) const =0
Create an instance of MeanDataValues.
const bool myAggregate
whether the data for all edges shall be aggregated
void writeXMLOutput(OutputDevice &dev, SUMOTime startTime, SUMOTime stopTime)
Writes collected values into the given stream.
const bool myDumpInternal
Whether internal lanes/edges shall be written.
const SUMOTime myDumpBegin
The first and the last time step to write information (-1 indicates always)
virtual void detectorUpdate(const SUMOTime step)
Updates the detector.
virtual ~MSMeanData()
Destructor.
void writeAggregated(OutputDevice &dev, SUMOTime startTime, SUMOTime stopTime)
Writes aggregate of all edge values into the given stream.
void init()
Adds the value collectors to all relevant edges.
const double myMinSamples
the minimum sample seconds
void resetOnly(SUMOTime stopTime)
Resets network value in order to allow processing of the next interval.
const long long int myWrittenAttributes
bit mask for checking attributes to be written
const bool myPrintDefaults
Whether empty lanes/edges shall be written.
std::map< const MSEdge *, int > myEdgeIndex
The index in myEdges / myMeasures.
const bool myAmEdgeBased
Information whether the output shall be edge-based (not lane-based)
SUMOTime myInitTime
time at which init was called();
const double myMaxTravelTime
the maximum travel time to write
std::list< std::pair< SUMOTime, SUMOTime > > myPendingIntervals
The intervals for which output still has to be generated (only in the tracking case)
const std::vector< MeanDataValues * > * getEdgeValues(const MSEdge *edge) const
void writeEdge(OutputDevice &dev, const std::vector< MeanDataValues * > &edgeValues, const MSEdge *const edge, SUMOTime startTime, SUMOTime stopTime)
Writes edge values into the given stream.
virtual std::string getEdgeID(const MSEdge *const edge)
Return the relevant edge id.
static long long int initWrittenAttributes(const std::string writeAttributes, const std::string &id)
virtual void writeXMLDetectorProlog(OutputDevice &dev) const
Opens the XML-output using "netstats" as root element.
const bool myDumpEmpty
Whether empty lanes/edges shall be written.
MSEdgeVector myEdges
The corresponding first edges.
MSMeanData(const std::string &id, const SUMOTime dumpBegin, const SUMOTime dumpEnd, const bool useLanes, const bool withEmpty, const bool printDefaults, const bool withInternal, const bool trackVehicles, const int detectPersons, const double minSamples, const double maxTravelTime, const std::string &vTypes, const std::string &writeAttributes, const std::vector< MSEdge * > &edges, bool aggregate)
Constructor.
virtual void openInterval(OutputDevice &dev, const SUMOTime startTime, const SUMOTime stopTime)
Writes the interval opener.
std::vector< std::vector< MeanDataValues * > > myMeasures
Value collectors; sorted by edge, then by lane.
virtual bool writePrefix(OutputDevice &dev, const MeanDataValues &values, const SumoXMLTag tag, const std::string id) const
Checks for emptiness and writes prefix into the given stream.
const bool myTrackVehicles
Whether vehicles are tracked.
Something on a lane to be noticed about vehicle movement.
void setDescription(const std::string &description)
Notification
Definition of a vehicle state.
@ NOTIFICATION_SEGMENT
The vehicle changes the segment (meso only)
@ NOTIFICATION_JUNCTION
The vehicle arrived at a junction.
const MSLane * getLane() const
Returns the lane the reminder works on.
static MSNet * getInstance()
Returns the pointer to the unique instance of MSNet (singleton).
SUMOTime getCurrentTimeStep() const
Returns the current simulation step.
virtual bool skipFinalReset() const
gui may prevent final meanData reset to keep live data visible
MSEdgeControl & getEdgeControl()
Returns the edge control.
double getLength() const
Get vehicle's length [m].
std::string myID
The name of the object.
const std::string & getID() const
Returns the id.
Static storage of an output device and its base (abstract) implementation.
OutputDevice & writeAttr(const SumoXMLAttr attr, const T &val)
writes a named attribute
OutputDevice & openTag(const std::string &xmlElement)
Opens an XML tag.
bool closeTag(const std::string &comment="")
Closes the most recently opened tag and optionally adds a comment.
bool writeXMLHeader(const std::string &rootElement, const std::string &schemaFile, std::map< SumoXMLAttr, std::string > attrs=std::map< SumoXMLAttr, std::string >(), bool includeConfig=true)
Writes an XML header with optional configuration.
OutputDevice & writeOptionalAttr(const SumoXMLAttr attr, const T &val, long long int attributeMask)
writes a named attribute unless filtered
Representation of a vehicle, person, or container.
virtual const MSVehicleType & getVehicleType() const =0
Returns the object's "vehicle" type.
virtual double getPreviousSpeed() const =0
Returns the object's previous speed.
virtual bool hasArrived() const =0
Returns whether this object has arrived.
static SequentialStringBijection Attrs
The names of SUMO-XML attributes for use in netbuild.
A scoped lock which only triggers on condition.
int get(const std::string &str) const
std::vector< std::string > getVector()
return vector of strings