87 #define DEBUG_COND (isSelected())
89 #define DEBUG_COND2(obj) ((obj != 0 && (obj)->isSelected()))
130 if (nextIsMyVehicles()) {
131 if (myI1 != myI1End) {
132 return myLane->myVehicles[myI1];
133 }
else if (myI3 != myI3End) {
134 return myLane->myTmpVehicles[myI3];
136 assert(myI2 == myI2End);
140 return myLane->myPartialVehicles[myI2];
151 if (myI1 == myI1End && myI3 == myI3End) {
152 if (myI2 != myI2End) {
158 if (myI2 == myI2End) {
161 MSVehicle* cand = myI1 == myI1End ? myLane->myTmpVehicles[myI3] : myLane->myVehicles[myI1];
169 if (cand->
getPositionOnLane() < myLane->myPartialVehicles[myI2]->getPositionOnLane(myLane)) {
172 return !myDownstream;
186 int index,
bool isRampAccel,
187 const std::string& type) :
212 mySimulationTask(*this, 0),
217 assert(
myRNGs.size() > 0);
270 veh->addReminder(rem);
282 std::cout <<
SIMTIME <<
" setPartialOccupation. lane=" <<
getID() <<
" veh=" << v->
getID() <<
"\n";
302 std::cout <<
SIMTIME <<
" resetPartialOccupation. lane=" <<
getID() <<
" veh=" << v->
getID() <<
"\n";
322 std::cout <<
SIMTIME <<
" setManeuverReservation. lane=" <<
getID() <<
" veh=" << v->
getID() <<
"\n";
333 std::cout <<
SIMTIME <<
" resetManeuverReservation(): lane=" <<
getID() <<
" veh=" << v->
getID() <<
"\n";
374 if (leader ==
nullptr) {
379 leader = leaderInfo.first;
385 if (leader ==
nullptr) {
391 if (leaderBack >= frontGapNeeded) {
392 pos =
MIN2(pos, leaderBack - frontGapNeeded);
406 bool adaptableSpeed =
true;
415 if (missingRearGap > 0) {
416 if (minPos + missingRearGap <=
myLength) {
423 return isInsertionSuccess(&veh, mspeed, minPos + missingRearGap, posLat, adaptableSpeed, notification);
428 return isInsertionSuccess(&veh, mspeed, minPos, posLat, adaptableSpeed, notification);
435 const double speed = adaptableSpeed ? leader->
getSpeed() : mspeed;
437 if (leaderPos >= frontGapNeeded) {
447 MSLane::VehCont::iterator predIt =
myVehicles.begin();
458 double speed = mspeed;
459 if (adaptableSpeed && leader !=
nullptr) {
465 if (leader !=
nullptr) {
468 frontMax = leaderRearPos - frontGapNeeded;
476 if (frontMax > minPos && backMin + POSITION_EPS < frontMax) {
478 if (
isInsertionSuccess(&veh, speed, backMin + POSITION_EPS, posLat, adaptableSpeed, notification)) {
519 if (last !=
nullptr) {
567 bool patchSpeed =
true;
584 for (
int i = 0; i < 10; i++) {
616 for (
int i = 0; i < 10; i++) {
648 double dist = speed * relevantDelay / (double)
DELTA_T;
650 if (leaderInfo.first !=
nullptr) {
654 dist =
MIN2(dist, leaderInfo.second - frontGapNeeded);
665 MSLane::checkFailure(
const MSVehicle* aVehicle,
double& speed,
double& dist,
const double nspeed,
const bool patchSpeed,
const std::string errorMsg)
const {
666 if (nspeed < speed) {
668 speed =
MIN2(nspeed, speed);
670 }
else if (speed > 0) {
674 if (emergencyBrakeGap <= dist) {
682 if (errorMsg !=
"") {
683 WRITE_ERROR(
"Vehicle '" + aVehicle->
getID() +
"' will not be able to depart using the given velocity (" + errorMsg +
")!");
695 double speed,
double pos,
double posLat,
bool patchSpeed,
699 WRITE_WARNINGF(
"Invalid departPos % given for vehicle '%'. Inserting at lane end instead.",
700 pos, aVehicle->
getID());
704 #ifdef DEBUG_INSERTION
706 std::cout <<
"\nIS_INSERTION_SUCCESS\n"
708 <<
" veh '" << aVehicle->
getID() <<
"'\n";
716 std::vector<MSLane*>::const_iterator ri = bestLaneConts.begin();
723 bool hadRailSignal =
false;
730 if (nextStop.
lane ==
this) {
731 std::stringstream msg;
732 msg <<
"scheduled stop on lane '" <<
myID <<
"' too close";
733 const double distToStop = nextStop.
pars.
endPos - pos;
735 patchSpeed, msg.str())) {
745 MSLane* currentLane =
this;
748 while ((seen < dist || (isRail && !hadRailSignal)) && ri != bestLaneConts.end()) {
750 std::vector<MSLink*>::const_iterator link =
succLinkSec(*aVehicle, nRouteSuccs, *currentLane, bestLaneConts);
758 patchSpeed,
"arrival speed too low")) {
773 if (isRail && !hadRailSignal) {
774 std::string constraintInfo;
777 #ifdef DEBUG_INSERTION
779 std::cout <<
" insertion constraint at link " << (*link)->getDescription() <<
" not cleared \n";
785 hadRailSignal |= (*link)->getTLLogic() !=
nullptr;
788 cfModel.
getMaxDecel(), 0, posLat,
nullptr,
false, aVehicle)
789 || !(*link)->havePriority()) {
791 std::string errorMsg =
"";
792 const LinkState state = (*link)->getState();
798 errorMsg =
"unpriorised junction too close";
799 }
else if ((*link)->getTLLogic() !=
nullptr && !(*link)->getTLLogic()->getsMajorGreen((*link)->getTLIndex())) {
801 errorMsg =
"tlLogic '" + (*link)->getTLLogic()->getID() +
"' link " +
toString((*link)->getTLIndex()) +
" never switches to 'G'";
805 patchSpeed, errorMsg)) {
809 #ifdef DEBUG_INSERTION
811 std::cout <<
"trying insertion before minor link: "
812 <<
"insertion speed = " << speed <<
" dist=" << dist
818 #ifdef DEBUG_INSERTION
820 std::cout <<
" oncoming rail traffic at link " << (*link)->getDescription() <<
"\n";
828 nextLane = (*link)->getViaLaneOrLane();
830 if (nextLane !=
nullptr) {
841 if (nextStop.
lane == nextLane) {
842 std::stringstream msg;
843 msg <<
"scheduled stop on lane '" << nextStop.
lane->
getID() <<
"' too close";
844 const double distToStop = seen + nextStop.
pars.
endPos;
846 patchSpeed, msg.str())) {
857 #ifdef DEBUG_INSERTION
859 <<
" leader on lane '" << nextLane->
getID() <<
"': " << leaders.
toString() <<
" nspeed=" << nspeed <<
"\n";
863 #ifdef DEBUG_INSERTION
865 <<
" isInsertionSuccess lane=" <<
getID()
866 <<
" veh=" << aVehicle->
getID()
868 <<
" posLat=" << posLat
869 <<
" patchSpeed=" << patchSpeed
870 <<
" speed=" << speed
871 <<
" nspeed=" << nspeed
872 <<
" nextLane=" << nextLane->
getID()
875 <<
" failed (@641)!\n";
885 if (nspeed < speed) {
891 WRITE_WARNINGF(
"Vehicle '%' is inserted too fast and will violate the speed limit on a lane '%'.",
895 WRITE_ERROR(
"Vehicle '" + aVehicle->
getID() +
"' will not be able to depart using the given velocity (slow lane ahead)!");
905 if ((*link)->hasApproachingFoe(arrivalTime, leaveTime, speed, cfModel.
getMaxDecel())) {
913 currentLane = nextLane;
914 if ((*link)->getViaLane() ==
nullptr) {
928 #ifdef DEBUG_INSERTION
930 <<
" isInsertionSuccess lane=" <<
getID()
931 <<
" veh=" << aVehicle->
getID()
933 <<
" posLat=" << posLat
934 <<
" patchSpeed=" << patchSpeed
935 <<
" speed=" << speed
936 <<
" nspeed=" << nspeed
937 <<
" nextLane=" << nextLane->
getID()
938 <<
" leaders=" << leaders.
toString()
939 <<
" failed (@700)!\n";
943 #ifdef DEBUG_INSERTION
945 <<
" speed = " << speed
946 <<
" nspeed = " << nspeed
951 for (
int i = 0; i < followers.
numSublanes(); ++i) {
952 const MSVehicle* follower = followers[i].first;
953 if (follower !=
nullptr) {
955 if (followers[i].second < backGapNeeded) {
957 #ifdef DEBUG_INSERTION
959 <<
" isInsertionSuccess lane=" <<
getID()
960 <<
" veh=" << aVehicle->
getID()
962 <<
" posLat=" << posLat
963 <<
" patchSpeed=" << patchSpeed
964 <<
" speed=" << speed
965 <<
" nspeed=" << nspeed
966 <<
" follower=" << follower->
getID()
967 <<
" backGapNeeded=" << backGapNeeded
968 <<
" gap=" << followers[i].second
969 <<
" failure (@719)!\n";
981 #ifdef DEBUG_INSERTION
986 if (shadowLane !=
nullptr) {
988 for (
int i = 0; i < shadowFollowers.
numSublanes(); ++i) {
989 const MSVehicle* follower = shadowFollowers[i].first;
990 if (follower !=
nullptr) {
992 if (shadowFollowers[i].second < backGapNeeded) {
994 #ifdef DEBUG_INSERTION
996 <<
" isInsertionSuccess shadowlane=" << shadowLane->
getID()
997 <<
" veh=" << aVehicle->
getID()
999 <<
" posLat=" << posLat
1000 <<
" patchSpeed=" << patchSpeed
1001 <<
" speed=" << speed
1002 <<
" nspeed=" << nspeed
1003 <<
" follower=" << follower->
getID()
1004 <<
" backGapNeeded=" << backGapNeeded
1005 <<
" gap=" << shadowFollowers[i].second
1006 <<
" failure (@812)!\n";
1015 if (veh !=
nullptr) {
1018 if (gap < gapNeeded) {
1020 #ifdef DEBUG_INSERTION
1022 <<
" isInsertionSuccess shadowlane=" << shadowLane->
getID()
1023 <<
" veh=" << aVehicle->
getID()
1025 <<
" posLat=" << posLat
1026 <<
" patchSpeed=" << patchSpeed
1027 <<
" speed=" << speed
1028 <<
" nspeed=" << nspeed
1029 <<
" leader=" << veh->
getID()
1030 <<
" gapNeeded=" << gapNeeded
1032 <<
" failure (@842)!\n";
1043 if (missingRearGap > 0) {
1045 #ifdef DEBUG_INSERTION
1047 <<
" isInsertionSuccess lane=" <<
getID()
1048 <<
" veh=" << aVehicle->
getID()
1050 <<
" posLat=" << posLat
1051 <<
" patchSpeed=" << patchSpeed
1052 <<
" speed=" << speed
1053 <<
" nspeed=" << nspeed
1054 <<
" missingRearGap=" << missingRearGap
1055 <<
" failure (@728)!\n";
1062 #ifdef DEBUG_INSERTION
1064 <<
" isInsertionSuccess lane=" <<
getID()
1065 <<
" veh=" << aVehicle->
getID()
1067 <<
" posLat=" << posLat
1068 <<
" patchSpeed=" << patchSpeed
1069 <<
" speed=" << speed
1070 <<
" nspeed=" << nspeed
1071 <<
" failed (@733)!\n";
1077 return v->getPositionOnLane() >= pos;
1079 #ifdef DEBUG_INSERTION
1081 <<
" isInsertionSuccess lane=" <<
getID()
1082 <<
" veh=" << aVehicle->
getID()
1084 <<
" posLat=" << posLat
1085 <<
" patchSpeed=" << patchSpeed
1086 <<
" speed=" << speed
1087 <<
" nspeed=" << nspeed
1091 <<
"\n leaders=" << leaders.
toString()
1107 return v->getPositionOnLane() >= pos;
1114 double nspeed = speed;
1115 #ifdef DEBUG_INSERTION
1117 std::cout <<
SIMTIME <<
" safeInsertionSpeed veh=" << veh->
getID() <<
" speed=" << speed <<
"\n";
1122 if (leader !=
nullptr) {
1127 nspeed =
MIN2(nspeed,
1129 #ifdef DEBUG_INSERTION
1131 std::cout <<
" leader=" << leader->
getID() <<
" nspeed=" << nspeed <<
"\n";
1146 int freeSublanes = 1;
1151 while (freeSublanes > 0 && veh !=
nullptr) {
1152 #ifdef DEBUG_PLAN_MOVE
1155 std::cout <<
" getLastVehicleInformation lane=" <<
getID() <<
" minPos=" << minPos <<
" veh=" << veh->
getID() <<
" pos=" << veh->
getPositionOnLane(
this) <<
"\n";
1160 freeSublanes = leaderTmp.
addLeader(veh,
true, vehLatOffset);
1161 #ifdef DEBUG_PLAN_MOVE
1163 std::cout <<
" latOffset=" << vehLatOffset <<
" newLeaders=" << leaderTmp.
toString() <<
"\n";
1169 if (ego ==
nullptr && minPos == 0) {
1177 #ifdef DEBUG_PLAN_MOVE
1206 int freeSublanes = 1;
1208 while (freeSublanes > 0 && veh !=
nullptr) {
1209 #ifdef DEBUG_PLAN_MOVE
1211 std::cout <<
" veh=" << veh->
getID() <<
" pos=" << veh->
getPositionOnLane(
this) <<
" maxPos=" << maxPos <<
"\n";
1218 #ifdef DEBUG_PLAN_MOVE
1220 std::cout <<
" veh=" << veh->
getID() <<
" latOffset=" << vehLatOffset <<
"\n";
1223 freeSublanes = followerTmp.
addLeader(veh,
true, vehLatOffset);
1227 if (ego ==
nullptr && maxPos == std::numeric_limits<double>::max()) {
1232 #ifdef DEBUG_PLAN_MOVE
1255 double cumulatedVehLength = 0.;
1259 VehCont::reverse_iterator veh =
myVehicles.rbegin();
1262 #ifdef DEBUG_PLAN_MOVE
1266 <<
" planMovements() lane=" <<
getID()
1274 #ifdef DEBUG_PLAN_MOVE
1276 std::cout <<
" plan move for: " << (*veh)->getID();
1280 #ifdef DEBUG_PLAN_MOVE
1282 std::cout <<
" leaders=" << leaders.
toString() <<
"\n";
1285 (*veh)->planMove(t, leaders, cumulatedVehLength);
1286 cumulatedVehLength += (*veh)->getVehicleType().getLengthWithGap();
1295 veh->setApproachingForAllLinks(t);
1304 bool nextToConsiderIsPartial;
1307 while (moreReservationsAhead || morePartialVehsAhead) {
1308 if ((!moreReservationsAhead || (*vehRes)->getPositionOnLane(
this) <= veh->
getPositionOnLane())
1309 && (!morePartialVehsAhead || (*vehPart)->getPositionOnLane(
this) <= veh->
getPositionOnLane())) {
1315 if (moreReservationsAhead && !morePartialVehsAhead) {
1316 nextToConsiderIsPartial =
false;
1317 }
else if (morePartialVehsAhead && !moreReservationsAhead) {
1318 nextToConsiderIsPartial =
true;
1320 assert(morePartialVehsAhead && moreReservationsAhead);
1322 nextToConsiderIsPartial = (*vehPart)->getPositionOnLane(
this) > (*vehRes)->getPositionOnLane(
this);
1325 if (nextToConsiderIsPartial) {
1326 const double latOffset = (*vehPart)->getLatOffset(
this);
1327 #ifdef DEBUG_PLAN_MOVE
1329 std::cout <<
" partial ahead: " << (*vehPart)->getID() <<
" latOffset=" << latOffset <<
"\n";
1333 ahead.
addLeader(*vehPart,
false, latOffset);
1338 const double latOffset = (*vehRes)->getLatOffset(
this);
1339 #ifdef DEBUG_PLAN_MOVE
1341 std::cout <<
" reservation ahead: " << (*vehRes)->getID() <<
" latOffset=" << latOffset <<
"\n";
1344 ahead.
addLeader(*vehRes,
false, latOffset);
1355 #ifdef DEBUG_COLLISIONS
1357 std::vector<const MSVehicle*> all;
1359 all.push_back(*last);
1361 std::cout <<
SIMTIME <<
" detectCollisions stage=" << stage <<
" lane=" <<
getID() <<
":\n"
1364 <<
" all=" <<
toString(all) <<
"\n"
1373 std::set<const MSVehicle*, ComparatorNumericalIdLess> toRemove;
1374 std::set<const MSVehicle*, ComparatorNumericalIdLess> toTeleport;
1377 #ifdef DEBUG_JUNCTION_COLLISIONS
1379 std::cout <<
SIMTIME <<
" detect junction Collisions stage=" << stage <<
" lane=" <<
getID() <<
":\n"
1386 const std::vector<const MSLane*>& foeLanes =
myLinks.front()->getFoeLanes();
1393 for (
const MSLane*
const foeLane : foeLanes) {
1394 #ifdef DEBUG_JUNCTION_COLLISIONS
1396 std::cout <<
" foeLane " << foeLane->getID()
1397 <<
" foeVehs=" <<
toString(foeLane->myVehicles)
1398 <<
" foePart=" <<
toString(foeLane->myPartialVehicles) <<
"\n";
1403 const MSVehicle*
const victim = *it_veh;
1404 if (victim == collider) {
1408 #ifdef DEBUG_JUNCTION_COLLISIONS
1411 <<
" bound=" << colliderBoundary <<
" foeBound=" << victim->
getBoundingBox()
1426 foeLane->handleCollisionBetween(timestep, stage, victim, collider, -1, 0, toRemove, toTeleport);
1435 if (
myLinks.front()->getWalkingAreaFoe() !=
nullptr) {
1438 if (
myLinks.front()->getWalkingAreaFoeExit() !=
nullptr) {
1449 VehCont::reverse_iterator lastVeh =
myVehicles.rend() - 1;
1450 for (VehCont::reverse_iterator pred =
myVehicles.rbegin(); pred != lastVeh; ++pred) {
1451 VehCont::reverse_iterator veh = pred + 1;
1462 double high = (*veh)->getPositionOnLane(
this);
1463 double low = (*veh)->getBackPositionOnLane(
this);
1475 double low2 =
myLength - (*veh2)->getPositionOnLane(bidiLane);
1476 double high2 =
myLength - (*veh2)->getBackPositionOnLane(bidiLane);
1482 if (!(high < low2 || high2 < low)) {
1483 #ifdef DEBUG_COLLISIONS
1485 std::cout <<
SIMTIME <<
" bidi-collision veh=" << (*veh)->getID() <<
" bidiVeh=" << (*veh2)->getID()
1486 <<
" vehFurther=" <<
toString((*veh)->getFurtherLanes())
1487 <<
" high=" << high <<
" low=" << low <<
" high2=" << high2 <<
" low2=" << low2 <<
"\n";
1494 std::swap(victim, collider);
1516 if (lead == follow) {
1532 #ifdef DEBUG_PEDESTRIAN_COLLISIONS
1534 std::cout <<
SIMTIME <<
" detect pedestrian collisions stage=" << stage <<
" lane=" <<
getID() <<
"\n";
1544 #ifdef DEBUG_PEDESTRIAN_COLLISIONS
1546 std::cout <<
SIMTIME <<
" back=" << back <<
" right=" << right <<
" person=" <<
Named::getIDSecure(leader.first) <<
" dist=" << leader.second <<
"\n";
1549 if (leader.first != 0 && leader.second < length) {
1552 WRITE_WARNINGF(
"Vehicle '%' collision with person '%', lane='%', gap=%, time=%, stage=%.",
1561 for (std::set<const MSVehicle*, ComparatorNumericalIdLess>::iterator it = toRemove.begin(); it != toRemove.end(); ++it) {
1565 if (toTeleport.count(veh) > 0) {
1577 SUMOTime timestep,
const std::string& stage) {
1579 #ifdef DEBUG_PEDESTRIAN_COLLISIONS
1581 std::cout <<
SIMTIME <<
" detect pedestrian junction collisions stage=" << stage <<
" lane=" <<
getID() <<
" foeLane=" << foeLane->
getID() <<
"\n";
1585 for (std::vector<MSTransportable*>::const_iterator it_p = persons.begin(); it_p != persons.end(); ++it_p) {
1586 #ifdef DEBUG_PEDESTRIAN_COLLISIONS
1588 std::cout <<
" collider=" << collider->
getID()
1589 <<
" ped=" << (*it_p)->getID()
1590 <<
" colliderBoundary=" << colliderBoundary
1591 <<
" pedBoundary=" << (*it_p)->getBoundingBox()
1595 if (colliderBoundary.
overlapsWith((*it_p)->getBoundingBox())
1597 std::string collisionType =
"junctionPedestrian";
1599 collisionType =
"crossing";
1601 collisionType =
"walkingarea";
1605 WRITE_WARNINGF(
"Vehicle '%' collision with person '%', lane='%', time=%, stage=%.",
1617 std::set<const MSVehicle*, ComparatorNumericalIdLess>& toRemove,
1618 std::set<const MSVehicle*, ComparatorNumericalIdLess>& toTeleport)
const {
1625 if (collider == victim) {
1631 const bool bothOpposite = victimOpposite && colliderOpposite;
1633 std::swap(victim, collider);
1647 }
else if (colliderOpposite) {
1651 #ifdef DEBUG_COLLISIONS
1654 <<
" thisLane=" <<
getID()
1655 <<
" collider=" << collider->
getID()
1656 <<
" victim=" << victim->
getID()
1657 <<
" colOpposite=" << colliderOpposite
1658 <<
" vicOpposite=" << victimOpposite
1661 <<
" colPos=" << colliderPos
1662 <<
" vicBack=" << victimBack
1666 <<
" minGapFactor=" << minGapFactor
1671 if (gap < -NUMERICAL_EPS) {
1676 if (latGap + NUMERICAL_EPS > 0) {
1683 && victim->
getLane() !=
this) {
1687 #ifdef DEBUG_COLLISIONS
1689 std::cout <<
SIMTIME <<
" detectedCollision gap=" << gap <<
" latGap=" << latGap <<
"\n";
1701 double gap,
double latGap, std::set<const MSVehicle*, ComparatorNumericalIdLess>& toRemove,
1702 std::set<const MSVehicle*, ComparatorNumericalIdLess>& toTeleport)
const {
1708 ?
"frontal collision"
1709 : (
isInternal() ?
"junction collision" :
"collision"));
1712 std::swap(collider, victim);
1714 std::string prefix =
"Vehicle '" + collider->
getID() +
"'; " + collisionType +
" with vehicle '" + victim->
getID() ;
1719 std::string dummyError;
1725 double victimSpeed = victim->
getSpeed();
1726 double colliderSpeed = collider->
getSpeed();
1729 if (collisionAngle < 45) {
1731 colliderSpeed =
MIN2(colliderSpeed, victimSpeed);
1732 }
else if (collisionAngle < 135) {
1749 ((
MSBaseVehicle*)victim)->addStop(stop, dummyError, 0,
true);
1758 ((
MSBaseVehicle*)collider)->addStop(stop, dummyError, 0,
true);
1769 prefix =
"Teleporting vehicle '" + collider->
getID() +
"'; " + collisionType +
" with vehicle '" + victim->
getID() ;
1770 toRemove.insert(collider);
1771 toTeleport.insert(collider);
1774 prefix =
"Removing " + collisionType +
" participants: vehicle '" + collider->
getID() +
"', vehicle '" + victim->
getID();
1775 bool removeCollider =
true;
1776 bool removeVictim =
true;
1780 toRemove.insert(victim);
1782 if (removeCollider) {
1783 toRemove.insert(collider);
1785 if (!removeVictim) {
1786 if (!removeCollider) {
1787 prefix =
"Keeping remote-controlled " + collisionType +
" participants: vehicle '" + collider->
getID() +
"', vehicle '" + victim->
getID();
1789 prefix =
"Removing " + collisionType +
" participant: vehicle '" + collider->
getID() +
"', keeping remote-controlled vehicle '" + victim->
getID();
1791 }
else if (!removeCollider) {
1792 prefix =
"Keeping remote-controlled " + collisionType +
" participant: vehicle '" + collider->
getID() +
"', removing vehicle '" + victim->
getID();
1800 if (collisionType ==
"frontal collision") {
1801 collisionType =
"frontal";
1802 }
else if (collisionType ==
"junction collision") {
1803 collisionType =
"junction";
1808 +
"', lane='" +
getID()
1812 +
" stage=" + stage +
".");
1817 #ifdef DEBUG_COLLISIONS
1819 toRemove.erase(collider);
1820 toTeleport.erase(collider);
1823 toRemove.erase(victim);
1824 toTeleport.erase(victim);
1844 #ifdef DEBUG_EXEC_MOVE
1846 std::cout <<
SIMTIME <<
" veh " << veh->
getID() <<
" has arrived." << std::endl;
1851 }
else if (target !=
nullptr && moved) {
1873 WRITE_WARNINGF(
"Teleporting vehicle '%'; beyond end of lane, target lane='%', time=%.",
1880 WRITE_WARNINGF(
"Removing vehicle '%' after earlier collision, lane='%', time=%.",
1885 WRITE_WARNINGF(
"Teleporting vehicle '%' after earlier collision, lane='%', time=%.",
1899 i = VehCont::reverse_iterator(
myVehicles.erase(i.base()));
1911 if (r1 || r2 || r3) {
1913 const bool minorLink = !wrongLane && (link !=
myLinks.end()) && !((*link)->havePriority());
1914 const std::string reason = (wrongLane ?
" (wrong lane)" : (minorLink ?
" (yield)" :
" (jam)"));
1918 WRITE_WARNINGF(
"Teleporting vehicle '%'; waited too long" + reason
1919 + (r2 ?
" (highway)" :
"")
1920 + (r3 ?
" (disconnected)" :
"")
1924 }
else if (minorLink) {
1978 const MSLane* firstInternal =
this;
1980 while (pred !=
nullptr && pred->
isInternal()) {
1981 firstInternal = pred;
1985 return firstInternal;
1992 DictType::iterator it =
myDict.find(
id);
1993 if (it ==
myDict.end()) {
1995 myDict.insert(DictType::value_type(
id, ptr));
2004 DictType::iterator it =
myDict.find(
id);
2005 if (it ==
myDict.end()) {
2015 for (DictType::iterator i =
myDict.begin(); i !=
myDict.end(); ++i) {
2024 for (DictType::iterator i =
myDict.begin(); i !=
myDict.end(); ++i) {
2025 into.push_back((*i).first);
2030 template<
class RTREE>
void
2032 for (DictType::iterator i =
myDict.begin(); i !=
myDict.end(); ++i) {
2036 const float cmin[2] = {(float) b.
xmin(), (float) b.
ymin()};
2037 const float cmax[2] = {(float) b.
xmax(), (float) b.
ymax()};
2038 into.Insert(cmin, cmax, l);
2042 template void MSLane::fill<NamedRTree>(
NamedRTree& into);
2063 return (link !=
myLinks.end());
2073 assert(veh->getLane() ==
this);
2087 #ifdef DEBUG_VEHICLE_CONTAINER
2105 #ifdef DEBUG_CONTEXT
2107 std::cout <<
"sortManeuverReservations on lane " <<
getID()
2112 #ifdef DEBUG_CONTEXT
2164 std::vector<MSLink*>::const_iterator
2166 const MSLane& succLinkSource,
const std::vector<MSLane*>& conts) {
2169 if (nRouteEdge ==
nullptr) {
2171 return succLinkSource.
myLinks.end();
2175 assert(succLinkSource.
myLinks.size() == 1);
2178 return succLinkSource.
myLinks.begin();
2189 if (nRouteSuccs < (
int)conts.size()) {
2191 for (std::vector<MSLink*>::const_iterator link = succLinkSource.
myLinks.begin(); link != succLinkSource.
myLinks.end(); ++link) {
2192 if ((*link)->getLane() !=
nullptr && (*link)->getLane()->myEdge == nRouteEdge && (*link)->getLane()->allowsVehicleClass(veh.
getVehicleType().
getVehicleClass())) {
2194 if ((*link)->getLane() == conts[nRouteSuccs]) {
2201 return succLinkSource.
myLinks.end();
2204 #ifdef DEBUG_NO_CONNECTION
2206 WRITE_WARNING(
"Could not find connection between lane " + succLinkSource.
getID() +
" and lane " + conts[nRouteSuccs]->getID() +
2209 return succLinkSource.
myLinks.end();
2217 if ((
internal && l->getViaLane() == target) || (!
internal && l->getLane() == target)) {
2228 if (l->getLane() == target) {
2229 return l->getViaLane();
2241 const MSLane*
internal =
this;
2243 assert(lane !=
nullptr);
2247 assert(lane !=
nullptr);
2283 assert(remVehicle->
getLane() ==
this);
2285 if (remVehicle == *it) {
2320 }
else if (!approachingEdge->
isInternal() && warnMultiCon) {
2323 WRITE_WARNINGF(
"Lane '%' is approached multiple times from edge '%'. This may cause collisions.",
2332 std::map<MSEdge*, std::vector<MSLane*> >::const_iterator i =
myApproachingLanes.find(edge);
2336 const std::vector<MSLane*>& lanes = (*i).second;
2337 return std::find(lanes.begin(), lanes.end(), lane) != lanes.end();
2348 const MSVehicle* v = followerInfo.first;
2367 std::pair<MSVehicle* const, double>
2368 MSLane::getLeader(
const MSVehicle* veh,
const double vehPos,
const std::vector<MSLane*>& bestLaneConts,
double dist,
bool checkTmpVehicles)
const {
2371 #ifdef DEBUG_CONTEXT
2376 if (checkTmpVehicles) {
2383 #ifdef DEBUG_CONTEXT
2385 std::cout << std::setprecision(
gPrecision) <<
" getLeader lane=" <<
getID() <<
" ego=" << veh->
getID() <<
" egoPos=" << vehPos <<
" pred=" << pred->
getID() <<
" predPos=" << pred->
getPositionOnLane() <<
"\n";
2399 #ifdef DEBUG_CONTEXT
2401 std::cout <<
" getLeader lane=" <<
getID() <<
" ego=" << veh->
getID() <<
" egoPos=" << vehPos
2411 if (bestLaneConts.size() > 0) {
2417 #ifdef DEBUG_CONTEXT
2419 std::cout <<
" getLeader lane=" <<
getID() <<
" seen=" << seen <<
" dist=" << dist <<
"\n";
2423 return std::pair<MSVehicle* const, double>(
static_cast<MSVehicle*
>(
nullptr), -1);
2427 return std::make_pair(
static_cast<MSVehicle*
>(
nullptr), -1);
2432 std::pair<MSVehicle* const, double>
2434 const std::vector<MSLane*>& bestLaneConts)
const {
2435 #ifdef DEBUG_CONTEXT
2437 std::cout <<
" getLeaderOnConsecutive lane=" <<
getID() <<
" ego=" << veh.
getID() <<
" seen=" << seen <<
" dist=" << dist <<
" conts=" <<
toString(bestLaneConts) <<
"\n";
2441 return std::make_pair(
static_cast<MSVehicle*
>(
nullptr), -1);
2449 #ifdef DEBUG_CONTEXT
2456 return std::pair<MSVehicle* const, double>(pred, gap);
2459 #ifdef DEBUG_CONTEXT
2464 const MSLane* nextLane =
this;
2468 std::vector<MSLink*>::const_iterator link =
succLinkSec(veh, view, *nextLane, bestLaneConts);
2470 #ifdef DEBUG_CONTEXT
2472 std::cout <<
" cannot continue after nextLane=" << nextLane->
getID() <<
"\n";
2479 const bool laneChanging = veh.
getLane() !=
this;
2482 if (linkLeaders.size() > 0) {
2483 std::pair<MSVehicle*, double> result;
2484 double shortestGap = std::numeric_limits<double>::max();
2485 for (
auto ll : linkLeaders) {
2486 double gap = ll.vehAndGap.second;
2488 if (lVeh !=
nullptr) {
2492 #ifdef DEBUG_CONTEXT
2495 <<
" isLeader=" << veh.
isLeader(*link, lVeh)
2496 <<
" gap=" << ll.vehAndGap.second
2497 <<
" gap+brakeing=" << gap
2502 if (lVeh !=
nullptr && !laneChanging && !veh.
isLeader(*link, lVeh)) {
2505 if (gap < shortestGap) {
2507 result = ll.vehAndGap;
2510 if (shortestGap != std::numeric_limits<double>::max()) {
2511 #ifdef DEBUG_CONTEXT
2513 std::cout <<
" found linkLeader after nextLane=" << nextLane->
getID() <<
"\n";
2520 bool nextInternal = (*link)->getViaLane() !=
nullptr;
2521 nextLane = (*link)->getViaLaneOrLane();
2522 if (nextLane ==
nullptr) {
2527 if (leader !=
nullptr) {
2528 #ifdef DEBUG_CONTEXT
2530 std::cout <<
" found leader " << leader->
getID() <<
" on nextLane=" << nextLane->
getID() <<
"\n";
2535 return std::make_pair(leader, leaderDist);
2542 if (!nextInternal) {
2545 }
while (seen <= dist || nextLane->
isInternal());
2546 #ifdef DEBUG_CONTEXT
2549 return std::make_pair(
static_cast<MSVehicle*
>(
nullptr), -1);
2553 std::pair<MSVehicle* const, double>
2555 #ifdef DEBUG_CONTEXT
2557 std::cout <<
SIMTIME <<
" getCriticalLeader. lane=" <<
getID() <<
" veh=" << veh.
getID() <<
"\n";
2561 std::pair<MSVehicle*, double> result = std::make_pair(
static_cast<MSVehicle*
>(
nullptr), -1);
2562 double safeSpeed = std::numeric_limits<double>::max();
2567 const MSLane* nextLane =
this;
2571 std::vector<MSLink*>::const_iterator link =
succLinkSec(veh, view, *nextLane, bestLaneConts);
2577 #ifdef DEBUG_CONTEXT
2583 #ifdef DEBUG_CONTEXT
2588 for (MSLink::LinkLeaders::const_iterator it = linkLeaders.begin(); it != linkLeaders.end(); ++it) {
2589 const MSVehicle* leader = (*it).vehAndGap.first;
2590 if (leader !=
nullptr && leader != result.first) {
2594 const double tmpSpeed = veh.
getSafeFollowSpeed((*it).vehAndGap, seen, nextLane, (*it).distToCrossing);
2595 #ifdef DEBUG_CONTEXT
2597 std::cout <<
" linkLeader=" << leader->
getID() <<
" gap=" << result.second <<
" tmpSpeed=" << tmpSpeed <<
" safeSpeed=" << safeSpeed <<
"\n";
2600 if (tmpSpeed < safeSpeed) {
2601 safeSpeed = tmpSpeed;
2602 result = (*it).vehAndGap;
2606 bool nextInternal = (*link)->getViaLane() !=
nullptr;
2607 nextLane = (*link)->getViaLaneOrLane();
2608 if (nextLane ==
nullptr) {
2612 if (leader !=
nullptr && leader != result.first) {
2615 if (tmpSpeed < safeSpeed) {
2616 safeSpeed = tmpSpeed;
2617 result = std::make_pair(leader, gap);
2628 if (!nextInternal) {
2631 }
while (seen <= dist || nextLane->
isInternal());
2641 for (MSEdgeVector::iterator i = pred.begin(); i != pred.end();) {
2650 if (pred.size() != 0) {
2652 MSEdge* best = *pred.begin();
2674 if (&(cand.lane->getEdge()) == &fromEdge) {
2699 #ifdef DEBUG_LANE_SORTER
2715 std::vector<MSLink*> candidateLinks =
myLinks;
2718 MSLane* best = (*candidateLinks.begin())->getViaLaneOrLane();
2719 #ifdef DEBUG_LANE_SORTER
2720 std::cout <<
"\nBest successor lane for lane '" <<
myID <<
"': '" << best->
getID() <<
"'" << std::endl;
2730 if (pred ==
nullptr) {
2738 const std::vector<std::pair<const MSLane*, const MSEdge*> >
2740 std::vector<std::pair<const MSLane*, const MSEdge*> > result;
2742 assert(link->getLane() !=
nullptr);
2743 result.push_back(std::make_pair(link->getLane(), link->getViaLane() ==
nullptr ?
nullptr : &link->getViaLane()->getEdge()));
2748 std::vector<const MSLane*>
2750 std::vector<const MSLane*> result = {};
2752 for (std::vector<MSLane*>::const_iterator it_lane = (*it).second.begin(); it_lane != (*it).second.end(); ++it_lane) {
2753 if (!((*it_lane)->isInternal())) {
2754 result.push_back(*it_lane);
2778 for (std::vector<MSLink*>::const_iterator i =
myLinks.begin(); i !=
myLinks.end(); ++i) {
2779 if ((*i)->getLane()->getEdge().isCrossing()) {
2780 return (
int)(i -
myLinks.begin());
2824 wtime += (*i)->getWaitingSeconds();
2837 for (VehCont::const_iterator i = vehs.begin(); i != vehs.end(); ++i) {
2838 v += (*i)->getSpeed();
2856 v += veh->getSpeed();
2875 for (MSLane::VehCont::const_iterator i = vehs.begin(); i != vehs.end(); ++i) {
2876 ret += (*i)->getCO2Emissions();
2887 for (MSLane::VehCont::const_iterator i = vehs.begin(); i != vehs.end(); ++i) {
2888 ret += (*i)->getCOEmissions();
2899 for (MSLane::VehCont::const_iterator i = vehs.begin(); i != vehs.end(); ++i) {
2900 ret += (*i)->getPMxEmissions();
2911 for (MSLane::VehCont::const_iterator i = vehs.begin(); i != vehs.end(); ++i) {
2912 ret += (*i)->getNOxEmissions();
2923 for (MSLane::VehCont::const_iterator i = vehs.begin(); i != vehs.end(); ++i) {
2924 ret += (*i)->getHCEmissions();
2935 for (MSLane::VehCont::const_iterator i = vehs.begin(); i != vehs.end(); ++i) {
2936 ret += (*i)->getFuelConsumption();
2947 for (MSLane::VehCont::const_iterator i = vehs.begin(); i != vehs.end(); ++i) {
2948 ret += (*i)->getElectricityConsumption();
2959 if (vehs.size() == 0) {
2963 for (MSLane::VehCont::const_iterator i = vehs.begin(); i != vehs.end(); ++i) {
2964 double sv = (*i)->getHarmonoise_NoiseEmissions();
2965 ret += (double) pow(10., (sv / 10.));
2998 myLaneDir(e->getLanes()[0]->
getShape().angleAt2D(0)) {
3009 if (ae1 !=
nullptr && ae1->size() != 0) {
3019 if (ae2 !=
nullptr && ae2->size() != 0) {
3039 myLaneDir(targetLane->
getShape().angleAt2D(0)) {}
3057 #ifdef DEBUG_LANE_SORTER
3058 std::cout <<
"\nincoming_lane_priority sorter()\n"
3059 <<
"noninternal predecessor for lane '" << laneInfo1.
lane->
getID()
3060 <<
"': '" << noninternal1->
getID() <<
"'\n"
3061 <<
"noninternal predecessor for lane '" << laneInfo2.
lane->
getID()
3062 <<
"': '" << noninternal2->
getID() <<
"'\n";
3070 bool priorized1 =
true;
3071 bool priorized2 =
true;
3073 #ifdef DEBUG_LANE_SORTER
3074 std::cout <<
"FoeLinks of '" << noninternal1->
getID() <<
"'" << std::endl;
3077 #ifdef DEBUG_LANE_SORTER
3078 std::cout << foeLink->getLaneBefore()->getID() << std::endl;
3080 if (foeLink == link2) {
3086 #ifdef DEBUG_LANE_SORTER
3087 std::cout <<
"FoeLinks of '" << noninternal2->
getID() <<
"'" << std::endl;
3090 #ifdef DEBUG_LANE_SORTER
3091 std::cout << foeLink->getLaneBefore()->getID() << std::endl;
3094 if (foeLink == link1) {
3102 if (priorized1 != priorized2) {
3116 myLaneDir(sourceLane->
getShape().angleAt2D(0)) {}
3122 if (target2 ==
nullptr) {
3125 if (target1 ==
nullptr) {
3129 #ifdef DEBUG_LANE_SORTER
3130 std::cout <<
"\noutgoing_lane_priority sorter()\n"
3131 <<
"noninternal successors for lane '" << myLane->
getID()
3132 <<
"': '" << target1->
getID() <<
"' and "
3133 <<
"'" << target2->
getID() <<
"'\n";
3140 if (priority1 != priority2) {
3141 return priority1 > priority2;
3167 if (link->getApproaching().size() > 0) {
3176 const bool toRailJunction =
myLinks.size() > 0 && (
3179 const bool hasVehicles =
myVehicles.size() > 0;
3188 if (toRailJunction) {
3190 if (link->getApproaching().size() > 0) {
3193 for (
auto item : link->getApproaching()) {
3204 if (item.second.latOffset != 0) {
3236 for (
const std::string&
id : vehIds) {
3276 bool allSublanes,
double searchDist,
bool ignoreMinorLinks)
const {
3283 #ifdef DEBUG_CONTEXT
3285 std::cout <<
SIMTIME <<
" getFollowers lane=" <<
getID() <<
" ego=" << ego->
getID()
3286 <<
" backOffset=" << backOffset <<
" pos=" << egoPos
3287 <<
" allSub=" << allSublanes <<
" searchDist=" << searchDist <<
" ignoreMinor=" << ignoreMinorLinks
3288 <<
" egoLatDist=" << egoLatDist
3289 <<
" getOppositeLeaders=" << getOppositeLeaders
3297 #ifdef DEBUG_CONTEXT
3307 #ifdef DEBUG_CONTEXT
3309 std::cout <<
" (1) added veh=" << veh->
getID() <<
" latOffset=" << latOffset <<
" result=" << result.
toString() <<
"\n";
3314 #ifdef DEBUG_CONTEXT
3316 std::cout <<
" result.numFreeSublanes=" << result.
numFreeSublanes() <<
"\n";
3324 if (searchDist == -1) {
3326 #ifdef DEBUG_CONTEXT
3328 std::cout <<
" computed searchDist=" << searchDist <<
"\n";
3332 std::set<const MSEdge*> egoFurther;
3334 egoFurther.insert(&further->getEdge());
3344 std::vector<MSLane::IncomingLaneInfo> newFound;
3346 while (toExamine.size() != 0) {
3347 for (std::vector<MSLane::IncomingLaneInfo>::iterator it = toExamine.begin(); it != toExamine.end(); ++it) {
3348 MSLane* next = (*it).lane;
3352 #ifdef DEBUG_CONTEXT
3354 std::cout <<
" next=" << next->
getID() <<
" seen=" << (*it).length <<
" first=" << first.
toString() <<
" firstFront=" << firstFront.
toString() <<
" backOffset=" << backOffset <<
"\n";
3358 if (backOffset + (*it).length - next->
getLength() < 0
3359 && egoFurther.count(&next->
getEdge()) != 0
3365 for (
const auto& ll : linkLeaders) {
3366 if (ll.vehAndGap.first !=
nullptr) {
3367 const bool egoIsLeader = ll.vehAndGap.first->isLeader((*it).viaLink, ego);
3370 const double gap = (egoIsLeader
3371 ? -ll.vehAndGap.second - ll.vehAndGap.first->getVehicleType().getLengthWithGap() - ego->
getVehicleType().
getMinGap()
3374 #ifdef DEBUG_CONTEXT
3376 std::cout <<
SIMTIME <<
" ego=" << ego->
getID() <<
" link=" << (*it).viaLink->getViaLaneOrLane()->getID()
3378 <<
" gap=" << ll.vehAndGap.second <<
" dtC=" << ll.distToCrossing
3379 <<
" egoIsLeader=" << egoIsLeader <<
" gap2=" << gap
3386 #ifdef DEBUG_CONTEXT
3393 const MSVehicle* v = first[i] == ego ? firstFront[i] : first[i];
3396 if (v !=
nullptr && v != ego) {
3403 agap = (*it).length - next->
getLength() + backOffset
3406 #ifdef DEBUG_CONTEXT
3408 std::cout <<
" agap1=" << agap <<
"\n";
3415 if (v !=
nullptr && v != ego) {
3423 if (!(*it).viaLink->havePriority() && !ego->
onFurtherEdge(&(*it).lane->getEdge())
3428 agap =
MAX2(agap, 0.0);
3432 #ifdef DEBUG_CONTEXT
3439 if ((*it).length < searchDist) {
3440 const std::vector<MSLane::IncomingLaneInfo>& followers = next->
getIncomingLanes();
3441 for (std::vector<MSLane::IncomingLaneInfo>::const_iterator j = followers.begin(); j != followers.end(); ++j) {
3442 if (visited.find((*j).lane) == visited.end() && (((*j).viaLink->havePriority() && !(*j).viaLink->isTurnaround()) || !ignoreMinorLinks)) {
3443 visited.insert((*j).lane);
3445 ili.
lane = (*j).lane;
3446 ili.
length = (*j).length + (*it).length;
3448 newFound.push_back(ili);
3454 swap(newFound, toExamine);
3466 bool oppositeDirection)
const {
3480 #ifdef DEBUG_CONTEXT
3485 const MSLane* nextLane =
this;
3490 bool nextInternal =
false;
3491 if (oppositeDirection) {
3492 if (view >= (
int)bestLaneConts.size()) {
3495 nextLane = bestLaneConts[view];
3497 std::vector<MSLink*>::const_iterator link =
succLinkSec(*ego, view, *nextLane, bestLaneConts);
3503 if (linkLeaders.size() > 0) {
3507 if (veh != 0 && (ego->
isLeader(*link, veh)
3513 #ifdef DEBUG_CONTEXT
3515 std::cout <<
" linkleader=" << veh->
getID() <<
" gap=" << ll.
vehAndGap.second <<
"\n";
3520 #ifdef DEBUG_CONTEXT
3526 nextInternal = (*link)->getViaLane() !=
nullptr;
3527 nextLane = (*link)->getViaLaneOrLane();
3528 if (nextLane ==
nullptr) {
3534 #ifdef DEBUG_CONTEXT
3536 std::cout <<
SIMTIME <<
" getLeadersOnConsecutive lane=" <<
getID() <<
" nextLane=" << nextLane->
getID() <<
" leaders=" << leaders.
toString() <<
"\n";
3541 for (
int i = 0; i < iMax; ++i) {
3543 if (veh !=
nullptr) {
3544 #ifdef DEBUG_CONTEXT
3560 if (!nextInternal) {
3564 #ifdef DEBUG_CONTEXT
3574 #ifdef DEBUG_SURROUNDING
3576 std::cout <<
" addLeaders lane=" <<
getID() <<
" veh=" << vehicle->
getID() <<
" vehPos=" << vehPos <<
" opposite=" << opposite <<
"\n";
3580 for (
int i = 0; i < aheadSamePos.
numSublanes(); ++i) {
3582 if (veh !=
nullptr && veh != vehicle) {
3584 #ifdef DEBUG_SURROUNDING
3595 double speed = vehicle->
getSpeed();
3599 #ifdef DEBUG_SURROUNDING
3601 std::cout <<
" aborting forward search. dist=" << dist <<
" seen=" << seen <<
"\n";
3606 #ifdef DEBUG_SURROUNDING
3608 std::cout <<
" add consecutive before=" << result.
toString() <<
" seen=" << seen <<
" dist=" << dist;
3613 #ifdef DEBUG_SURROUNDING
3615 std::cout <<
" upstreamOpposite=" <<
toString(bestLaneConts);
3623 #ifdef DEBUG_SURROUNDING
3625 std::cout <<
" after=" << result.
toString() <<
"\n";
3639 #ifdef DEBUG_CONTEXT
3641 std::cout <<
SIMTIME <<
" getPartialBehind lane=" <<
getID() <<
" ego=" << ego->
getID() <<
" found=" << veh->
getID() <<
"\n";
3647 #ifdef DEBUG_CONTEXT
3670 std::set<MSVehicle*>
3672 assert(checkedLanes !=
nullptr);
3673 if (checkedLanes->find(
this) != checkedLanes->end()) {
3674 #ifdef DEBUG_SURROUNDING
3675 std::cout <<
"Skipping previously scanned lane: " <<
getID() << std::endl;
3677 return std::set<MSVehicle*>();
3680 (*checkedLanes)[
this] = std::make_pair(
MAX2(0.0, startPos - upstreamDist),
MIN2(startPos + downstreamDist,
getLength()));
3682 #ifdef DEBUG_SURROUNDING
3683 std::cout <<
"Scanning on lane " <<
myID <<
"(downstr. " << downstreamDist <<
", upstr. " << upstreamDist <<
", startPos " << startPos <<
"): " << std::endl;
3686 if (startPos < upstreamDist) {
3689 MSLane* incoming = incomingInfo.lane;
3690 #ifdef DEBUG_SURROUNDING
3691 std::cout <<
"Checking on incoming: " << incoming->
getID() << std::endl;
3692 if (checkedLanes->find(incoming) != checkedLanes->end()) {
3693 std::cout <<
"Skipping previous: " << incoming->
getID() << std::endl;
3697 foundVehicles.insert(newVehs.begin(), newVehs.end());
3701 if (
getLength() < startPos + downstreamDist) {
3705 #ifdef DEBUG_SURROUNDING
3706 std::cout <<
"Checking on outgoing: " << l->getViaLaneOrLane()->getID() << std::endl;
3708 std::set<MSVehicle*> newVehs = l->getViaLaneOrLane()->getSurroundingVehicles(0.0, downstreamDist - (
myLength - startPos), upstreamDist, checkedLanes);
3709 foundVehicles.insert(newVehs.begin(), newVehs.end());
3712 #ifdef DEBUG_SURROUNDING
3713 std::cout <<
"On lane (2) " <<
myID <<
": \nFound vehicles: " << std::endl;
3715 std::cout << v->getID() <<
" pos = " << v->getPositionOnLane() << std::endl;
3718 return foundVehicles;
3722 std::set<MSVehicle*>
3724 std::set<MSVehicle*> res;
3727 if (!vehs.empty()) {
3729 if (veh->getPositionOnLane() >= a) {
3730 if (veh->getBackPositionOnLane() > b) {
3742 std::vector<const MSJunction*>
3745 std::vector<const MSJunction*> junctions;
3747 junctions.insert(junctions.end(), l->getJunction());
3753 std::vector<const MSLink*>
3755 #ifdef DEBUG_SURROUNDING
3756 std::cout <<
"getUpcoming links on lane '" <<
getID() <<
"' with pos=" << pos
3757 <<
" range=" << range << std::endl;
3760 std::vector<const MSLink*> links;
3763 const MSLane* lane =
this;
3766 std::vector<MSLane*>::const_iterator contLanesIt = contLanes.begin();
3770 const MSLink* link =
nullptr;
3772 assert(*contLanesIt ==
nullptr);
3774 links.insert(links.end(), link);
3779 assert(*(contLanesIt + 1) == lane);
3781 while (++contLanesIt != contLanes.end()) {
3785 #ifdef DEBUG_SURROUNDING
3786 std::cout <<
"Distance until end of lane '" << lane->
getID() <<
"' is " << dist <<
"." << std::endl;
3792 if (link !=
nullptr) {
3793 links.insert(links.end(), link);
3795 lane = *contLanesIt;
3821 std::pair<MSVehicle* const, double>
3826 #ifdef DEBUG_CONTEXT
3828 std::cout <<
" getFollower lane=" <<
getID() <<
" egoPos=" << egoPos <<
" pred=" << pred->
getID() <<
" predPos=" << pred->
getPositionOnLane(
this) <<
"\n";
3836 if (dist > 0 && backOffset > dist) {
3837 return std::make_pair(
nullptr, -1);
3841 return std::make_pair(
const_cast<MSVehicle*
>(result.first), result.second);
3844 std::pair<MSVehicle* const, double>
3846 #ifdef DEBUG_OPPOSITE
3848 <<
" ego=" << ego->
getID()
3852 <<
" oppositeDir=" << oppositeDir
3860 std::pair<MSVehicle* const, double> result =
getFollower(ego, egoPos + egoLength, dist,
true);
3861 if (result.first !=
nullptr) {
3863 if (result.first->getLaneChangeModel().isOpposite()) {
3864 result.second -= result.first->getVehicleType().getLength();
3872 std::pair<MSVehicle* const, double>
3874 #ifdef DEBUG_OPPOSITE
3876 <<
" ego=" << ego->
getID()
3886 std::pair<MSVehicle*, double> result =
getLeader(ego, vehPos, std::vector<MSLane*>());
3889 while (result.first ==
nullptr && dist > 0) {
3894 if (next ==
nullptr) {
3898 result = next->
getLeader(ego, vehPos, std::vector<MSLane*>());
3900 if (result.first !=
nullptr) {
3901 if (result.first->getLaneChangeModel().isOpposite()) {
3902 result.second -= result.first->getVehicleType().getLength();
3904 if (result.second > POSITION_EPS) {
3906 return std::make_pair(
static_cast<MSVehicle*
>(
nullptr), -1);
3917 const std::string action = oc.
getString(
"collision.action");
3918 if (action ==
"none") {
3920 }
else if (action ==
"warn") {
3922 }
else if (action ==
"teleport") {
3924 }
else if (action ==
"remove") {
3927 WRITE_ERROR(
"Invalid collision.action '" + action +
"'.");
3986 #ifdef DEBUG_INSERTION
3988 std::cout <<
SIMTIME <<
" check for pedestrians on lane=" <<
getID() <<
" pos=" << pos <<
"\n";
3993 if (leader.first != 0) {
3996 if (gap < 0 ||
checkFailure(aVehicle, speed, dist, stopSpeed, patchSpeed,
"")) {
3998 #ifdef DEBUG_INSERTION
4000 <<
" isInsertionSuccess lane=" <<
getID()
4001 <<
" veh=" << aVehicle->
getID()
4004 <<
" patchSpeed=" << patchSpeed
4005 <<
" speed=" << speed
4006 <<
" stopSpeed=" << stopSpeed
4007 <<
" pedestrianLeader=" << leader.first->getID()
4008 <<
" failed (@796)!\n";
4021 const int numRNGs = oc.
getInt(
"thread-rngs");
4022 const bool random = oc.
getBool(
"random");
4023 int seed = oc.
getInt(
"seed");
4025 for (
int i = 0; i < numRNGs; i++) {
4044 throw ProcessError(
"State was saved with more than " +
toString(
getNumRNGs()) +
" threads. Change the number of threads or do not load RNG state");
4053 if (bidiEdge ==
nullptr) {
4057 assert(bidiEdge->
getLanes().size() == 1);
4078 foundStopped =
true;
4079 const double lastBrakeGap = last->getCarFollowModel().brakeGap(last->getSpeed());
4080 const double ret = last->getBackPositionOnLane() + lastBrakeGap - lengths;
4083 lengths += last->getVehicleType().getLengthWithGap();
std::vector< MSEdge * > MSEdgeVector
std::pair< const MSVehicle *, double > CLeaderDist
std::pair< const MSPerson *, double > PersonDist
ConstMSEdgeVector::const_iterator MSRouteIterator
#define WRITE_WARNINGF(...)
#define WRITE_WARNING(msg)
std::string time2string(SUMOTime t)
convert SUMOTime to string
SUMOTime string2time(const std::string &r)
convert string to SUMOTime
const SVCPermissions SVCAll
all VClasses are allowed
bool isRailway(SVCPermissions permissions)
Returns whether an edge with the given permission is a railway edge.
@ SVC_SHIP
is an arbitrary ship
@ SVC_BICYCLE
vehicle is a bicycle
int SVCPermissions
bitset where each bit declares whether a certain SVC may use this edge/lane
const int STOP_DURATION_SET
@ GIVEN
The speed is given.
@ RANDOM
The lateral position is chosen randomly.
@ RIGHT
At the rightmost side of the lane.
@ GIVEN
The position is given.
@ DEFAULT
No information given; use default.
@ LEFT
At the leftmost side of the lane.
@ FREE
A free lateral position is chosen.
@ CENTER
At the center of the lane.
@ RANDOM_FREE
If a fixed number of random choices fails, a free lateral position is chosen.
@ RANDOM
The position is chosen randomly.
@ GIVEN
The position is given.
@ DEFAULT
No information given; use default.
@ STOP
depart position is endPos of first stop
@ FREE
A free position is chosen.
@ BASE
Back-at-zero position.
@ LAST
Insert behind the last vehicle as close as possible to still allow the specified departSpeed....
@ RANDOM_FREE
If a fixed number of random choices fails, a free position is chosen.
@ RANDOM
The speed is chosen randomly.
@ MAX
The maximum safe speed is used.
@ GIVEN
The speed is given.
@ LIMIT
The maximum lane speed is used (speedLimit)
@ DEFAULT
No information given; use default.
@ DESIRED
The maximum lane speed is used (speedLimit * speedFactor)
@ LAST
The speed of the last vehicle. Fallback to DepartSpeedDefinition::DESIRED if there is no vehicle on t...
@ AVG
The average speed on the lane. Fallback to DepartSpeedDefinition::DESIRED if there is no vehicle on t...
@ SUMO_TAG_LINK
Link information for state-saving.
@ SUMO_TAG_APPROACHING
Link-approaching vehicle information for state-saving.
@ SUMO_TAG_VIEWSETTINGS_VEHICLES
@ SUMO_TAG_LANE
begin/end of the description of a single lane
LinkState
The right-of-way state of a link between two lanes used when constructing a NBTrafficLightLogic,...
@ LINKSTATE_ALLWAY_STOP
This is an uncontrolled, all-way stop link.
@ LINKSTATE_STOP
This is an uncontrolled, minor link, has to stop.
@ LINKSTATE_EQUAL
This is an uncontrolled, right-before-left link.
@ LINKSTATE_DEADEND
This is a dead end link.
@ LINKSTATE_MINOR
This is an uncontrolled, minor link, has to brake.
@ SUMO_ATTR_ARRIVALSPEEDBRAKING
@ SUMO_ATTR_ARRIVALTIMEBRAKING
@ SUMO_ATTR_STATE
The state of a link.
int gPrecision
the precision for floating point outputs
bool gDebugFlag1
global utility flags for debugging
const double SUMO_const_haltingSpeed
the speed threshold at which vehicles are considered as halting
std::string toString(const T &t, std::streamsize accuracy=gPrecision)
A class that stores a 2D geometrical boundary.
double ymin() const
Returns minimum y-coordinate.
double xmin() const
Returns minimum x-coordinate.
Boundary & grow(double by)
extends the boundary by the given amount
double ymax() const
Returns maximum y-coordinate.
double xmax() const
Returns maximum x-coordinate.
Container & getContainer()
static double angleDiff(const double angle1, const double angle2)
Returns the difference of the second angle to the first angle in radiants.
static double sum(double val)
Computes the resulting noise.
bool hasBlueLight() const
MSLane * getShadowLane() const
Returns the lane the vehicle's shadow is on during continuous/sublane lane change.
bool isChangingLanes() const
return true if the vehicle currently performs a lane change maneuver
The base class for microscopic and mesoscopic vehicles.
double getImpatience() const
Returns this vehicles impatience.
const MSEdge * succEdge(int nSuccs) const
Returns the nSuccs'th successor of edge the vehicle is currently at.
virtual double getArrivalPos() const
Returns this vehicle's desired arrivalPos for its current route (may change on reroute)
const SUMOVehicleParameter & getParameter() const
Returns the vehicle's parameter (including departure definition)
double getChosenSpeedFactor() const
Returns the precomputed factor by which the driver wants to be faster than the speed limit.
bool isParking() const
Returns whether the vehicle is parking.
const MSEdge * getEdge() const
Returns the edge the vehicle is currently at.
bool hasDeparted() const
Returns whether this vehicle has already departed.
double basePos(const MSEdge *edge) const
departure position where the vehicle fits fully onto the edge (if possible)
const MSVehicleType & getVehicleType() const
Returns the vehicle's type definition.
bool hasStops() const
Returns whether the vehicle has to stop somewhere.
SUMOVehicleClass getVClass() const
Returns the vehicle's access class.
NumericalID getNumericalID() const
return the numerical ID which is only for internal usage
SUMOTime getDepartDelay() const
Returns the depart delay.
const MSRoute & getRoute() const
Returns the current route.
bool isStopped() const
Returns whether the vehicle is at a stop.
The car-following model abstraction.
virtual double getSecureGap(const MSVehicle *const, const MSVehicle *const, const double speed, const double leaderSpeed, const double leaderMaxDecel) const
Returns the minimum gap to reserve if the leader is braking at maximum (>=0)
double stopSpeed(const MSVehicle *const veh, const double speed, double gap) const
Computes the vehicle's safe speed for approaching a non-moving obstacle (no dawdling)
double getCollisionMinGapFactor() const
Get the factor of minGap that must be maintained to avoid a collision event.
double getEmergencyDecel() const
Get the vehicle type's maximal phisically possible deceleration [m/s^2].
virtual double insertionFollowSpeed(const MSVehicle *const veh, double speed, double gap2pred, double predSpeed, double predMaxDecel, const MSVehicle *const pred=0) const
Computes the vehicle's safe speed (no dawdling) This method is used during the insertion stage....
virtual double brakeGap(const double speed) const
Returns the distance the vehicle needs to halt including driver's reaction time tau (i....
virtual double freeSpeed(const MSVehicle *const veh, double speed, double seen, double maxSpeed, const bool onInsertion=false) const
Computes the vehicle's safe speed without a leader.
double getMaxDecel() const
Get the vehicle type's maximal comfortable deceleration [m/s^2].
virtual double insertionStopSpeed(const MSVehicle *const veh, double speed, double gap) const
Computes the vehicle's safe speed for approaching an obstacle at insertion without constraints due to...
std::string toString() const
print a debugging representation
int addFollower(const MSVehicle *veh, const MSVehicle *ego, double gap, double latOffset=0, int sublane=-1)
void gotActive(MSLane *l)
Informs the control that the given lane got active.
void needsVehicleIntegration(MSLane *const l)
A road/street connecting two junctions.
void changeLanes(SUMOTime t) const
Performs lane changing on this edge.
bool isCrossing() const
return whether this edge is a pedestrian crossing
int getPriority() const
Returns the priority of the edge.
const MSEdgeVector & getPredecessors() const
bool isWalkingArea() const
return whether this edge is walking area
const MSEdge * getNormalSuccessor() const
if this edge is an internal edge, return its first normal successor, otherwise the edge itself
const std::set< MSTransportable * > & getPersons() const
Returns this edge's persons set.
std::vector< MSTransportable * > getSortedPersons(SUMOTime timestep, bool includeRiding=false) const
Returns this edge's persons sorted by pos.
const std::vector< MSLane * > * allowedLanes(const MSEdge &destination, SUMOVehicleClass vclass=SVC_IGNORING) const
Get the allowed lanes to reach the destination-edge.
const std::vector< MSLane * > & getLanes() const
Returns this edge's lanes.
void recalcCache()
Recalculates the cached values.
bool isInternal() const
return whether this edge is an internal edge
bool isVaporizing() const
Returns whether vehicles on this edge shall be vaporized.
MSLane * parallelLane(const MSLane *const lane, int offset, bool includeOpposite=true) const
Returns the lane with the given offset parallel to the given lane one or 0 if it does not exist.
const std::string & getEdgeType() const
Returns the type of the edge.
const MSJunction * getToJunction() const
const MSEdge * getBidiEdge() const
return opposite superposable/congruent edge, if it exist and 0 else
static SUMOTime gTimeToTeleportDisconnected
static SUMOTime gTimeToGridlockHighways
static bool gRemoveGridlocked
static double gLateralResolution
static bool gClearState
whether the simulation is in the process of clearing state (MSNet::clearState)
static bool gComputeLC
whether the simulationLoop is in the lane changing phase
static int gNumSimThreads
how many threads to use for simulation
static bool gSublane
whether sublane simulation is enabled (sublane model or continuous lanechanging)
static SUMOTime gLaneChangeDuration
static bool gUnitTests
whether unit tests are being run
static SUMOTime gTimeToGridlock
void descheduleDeparture(const SUMOVehicle *veh)
stops trying to emit the given vehicle (and delete it)
SumoXMLNodeType getType() const
return the type of this Junction
AnyVehicleIterator is a structure, which manages the iteration through all vehicles on the lane,...
int myI2
index for myPartialVehicles
bool nextIsMyVehicles() const
int myI3
index for myTmpVehicles
int myDirection
index delta
AnyVehicleIterator & operator++()
const MSVehicle * operator*()
int myI3End
end index for myTmpVehicles
int myI1End
end index for myVehicles
int myI1
index for myVehicles
Sorts edges by their angle relative to the given edge (straight comes first)
by_connections_to_sorter(const MSEdge *const e)
constructor
int operator()(const MSEdge *const e1, const MSEdge *const e2) const
comparing operator
Sorts lanes (IncomingLaneInfos) by their priority or, if this doesn't apply, wrt. the angle differenc...
incoming_lane_priority_sorter(const MSLane *targetLane)
constructor
int operator()(const IncomingLaneInfo &lane1, const IncomingLaneInfo &lane2) const
comparing operator
Sorts lanes (their origin link) by the priority of their noninternal target edges or,...
outgoing_lane_priority_sorter(const MSLane *sourceLane)
constructor
int operator()(const MSLink *link1, const MSLink *link2) const
comparing operator
int operator()(MSVehicle *v1, MSVehicle *v2) const
Comparing operator.
Sorts vehicles by their position (descending)
int operator()(MSVehicle *v1, MSVehicle *v2) const
Comparing operator.
Representation of a lane in the micro simulation.
void addApproachingLane(MSLane *lane, bool warnMultiCon)
bool detectCollisionBetween(SUMOTime timestep, const std::string &stage, MSVehicle *collider, MSVehicle *victim, std::set< const MSVehicle *, ComparatorNumericalIdLess > &toRemove, std::set< const MSVehicle *, ComparatorNumericalIdLess > &toTeleport) const
detect whether there is a collision between the two vehicles
SVCPermissions myPermissions
The vClass permissions for this lane.
MSLane * myLogicalPredecessorLane
virtual void setJunctionApproaches(const SUMOTime t) const
Register junction approaches for all vehicles after velocities have been planned.
std::set< const MSBaseVehicle * > myParkingVehicles
double getPMxEmissions() const
Returns the sum of last step PMx emissions.
const std::vector< MSLink * > & getLinkCont() const
returns the container with all links !!!
bool checkForPedestrians(const MSVehicle *aVehicle, double &speed, double &dist, double pos, bool patchSpeed) const
check whether pedestrians on this lane interfere with vehicle insertion
double getNOxEmissions() const
Returns the sum of last step NOx emissions.
MSLane * getParallelLane(int offset, bool includeOpposite=true) const
Returns the lane with the given offset parallel to this one or 0 if it does not exist.
double myRightSideOnEdge
the combined width of all lanes with lower index on myEdge
const StopOffset & getLaneStopOffsets() const
Returns vehicle class specific stopOffsets.
MSLane(const std::string &id, double maxSpeed, double length, MSEdge *const edge, int numericalID, const PositionVector &shape, double width, SVCPermissions permissions, SVCPermissions changeLeft, SVCPermissions changeRight, int index, bool isRampAccel, const std::string &type)
Constructor.
virtual void removeParking(MSBaseVehicle *veh)
remove parking vehicle. This must be syncrhonized when running with GUI
virtual ~MSLane()
Destructor.
bool insertVehicle(MSVehicle &v)
Tries to insert the given vehicle.
const MSLeaderInfo getFirstVehicleInformation(const MSVehicle *ego, double latOffset, bool onlyFrontOnLane, double maxPos=std::numeric_limits< double >::max(), bool allowCached=true) const
analogue to getLastVehicleInformation but in the upstream direction
virtual void integrateNewVehicles()
Insert buffered vehicle into the real lane.
double myLength
Lane length [m].
bool isApproachedFrom(MSEdge *const edge)
double getNettoOccupancy() const
Returns the netto (excluding minGaps) occupancy of this lane during the last step (including minGaps)
virtual MSVehicle * removeVehicle(MSVehicle *remVehicle, MSMoveReminder::Notification notification, bool notify=true)
int getCrossingIndex() const
return the index of the link to the next crossing if this is walkingArea, else -1
PositionVector myShape
The shape of the lane.
std::map< long long, SVCPermissions > myPermissionChanges
const std::map< SUMOVehicleClass, double > * myRestrictions
The vClass speed restrictions for this lane.
virtual void incorporateVehicle(MSVehicle *veh, double pos, double speed, double posLat, const MSLane::VehCont::iterator &at, MSMoveReminder::Notification notification=MSMoveReminder::NOTIFICATION_DEPARTED)
Inserts the vehicle into this lane, and informs it about entering the network.
void initRestrictions()
initialized vClass-specific speed limits
std::vector< MSMoveReminder * > myMoveReminders
This lane's move reminder.
bool hasApproaching() const
void addParking(MSBaseVehicle *veh)
add parking vehicle. This should only used during state loading
VehCont myTmpVehicles
Container for lane-changing vehicles. After completion of lane-change- process, the containers will b...
double getDepartSpeed(const MSVehicle &veh, bool &patchSpeed)
void addNeigh(const std::string &id)
Adds a neighbor to this lane.
MSLeaderInfo myFollowerInfo
followers on all sublanes as seen by vehicles on consecutive lanes (cached)
bool checkFailure(const MSVehicle *aVehicle, double &speed, double &dist, const double nspeed, const bool patchSpeed, const std::string errorMsg) const
static SUMOTime myCollisionStopTime
static CollisionAction myCollisionAction
the action to take on collisions
MSLane * myCanonicalSuccessorLane
Main successor lane,.
SVCPermissions myChangeLeft
The vClass permissions for changing from this lane.
void getLeadersOnConsecutive(double dist, double seen, double speed, const MSVehicle *ego, const std::vector< MSLane * > &bestLaneConts, MSLeaderDistanceInfo &result, bool oppositeDirection=false) const
Returns the immediate leaders and the distance to them (as getLeaderOnConsecutive but for the sublane...
std::vector< IncomingLaneInfo > myIncomingLanes
All direct predecessor lanes.
AnyVehicleIterator anyVehiclesEnd() const
end iterator for iterating over all vehicles touching this lane in downstream direction
static void insertIDs(std::vector< std::string > &into)
Adds the ids of all stored lanes into the given vector.
bool hadPermissionChanges() const
void sortPartialVehicles()
sorts myPartialVehicles
MSVehicle * getFirstAnyVehicle() const
returns the first vehicle that is fully or partially on this lane
const MSLink * getEntryLink() const
Returns the entry link if this is an internal lane, else nullptr.
int getVehicleNumberWithPartials() const
Returns the number of vehicles on this lane (including partial occupators)
static bool myCheckJunctionCollisions
static void clear()
Clears the dictionary.
virtual void resetManeuverReservation(MSVehicle *v)
Unregisters a vehicle, which previously registered for maneuvering into this lane.
SVCPermissions myOriginalPermissions
The original vClass permissions for this lane (before temporary modifications)
MSEdge *const myEdge
The lane's edge, for routing only.
double myNettoVehicleLengthSum
The current length of all vehicles on this lane, excluding their minGaps.
static std::vector< MSLink * >::const_iterator succLinkSec(const SUMOVehicle &veh, int nRouteSuccs, const MSLane &succLinkSource, const std::vector< MSLane * > &conts)
double getMissingRearGap(const MSVehicle *leader, double backOffset, double leaderSpeed) const
return by how much further the leader must be inserted to avoid rear end collisions
std::vector< std::string > myNeighs
double myMaxSpeed
Lane-wide speedlimit [m/s].
std::pair< const MSPerson *, double > nextBlocking(double minPos, double minRight, double maxLeft, double stopTime=0) const
This is just a wrapper around MSPModel::nextBlocking. You should always check using hasPedestrians be...
void saveState(OutputDevice &out)
Saves the state of this lane into the given stream.
virtual const VehCont & getVehiclesSecure() const
Returns the vehicles container; locks it for microsimulation.
double getCO2Emissions() const
Returns the sum of last step CO2 emissions.
const MSLink * getLinkTo(const MSLane *const) const
returns the link to the given lane or nullptr, if it is not connected
int myRightmostSublane
the index of the rightmost sublane of this lane on myEdge
const bool myIsRampAccel
whether this lane is an acceleration lane
virtual void planMovements(const SUMOTime t)
Compute safe velocities for all vehicles based on positions and speeds from the last time step....
static void saveRNGStates(OutputDevice &out)
save random number generator states to the given output device
SUMOTime myFollowerInfoTime
time step for which myFollowerInfo was last updated
MSLeaderInfo myLeaderInfo
leaders on all sublanes as seen by approaching vehicles (cached)
bool isInsertionSuccess(MSVehicle *vehicle, double speed, double pos, double posLat, bool recheckNextLanes, MSMoveReminder::Notification notification)
Tries to insert the given vehicle with the given state (speed and pos)
void forceVehicleInsertion(MSVehicle *veh, double pos, MSMoveReminder::Notification notification, double posLat=0)
Inserts the given vehicle at the given position.
double getVehicleStopOffset(const MSVehicle *veh) const
Returns vehicle class specific stopOffset for the vehicle.
static void initCollisionOptions(const OptionsCont &oc)
int myNumericalID
Unique numerical ID (set on reading by netload)
VehCont myVehicles
The lane's vehicles. This container holds all vehicles that have their front (longitudinally) and the...
double getSpeedLimit() const
Returns the lane's maximum allowed speed.
MSLeaderInfo getPartialBeyond() const
get all vehicles that are inlapping from consecutive edges
std::vector< MSVehicle * > VehCont
Container for vehicles.
static DictType myDict
Static dictionary to associate string-ids with objects.
static void fill(RTREE &into)
Fills the given RTree with lane instances.
double safeInsertionSpeed(const MSVehicle *veh, double seen, const MSLeaderInfo &leaders, double speed)
return the maximum safe speed for insertion behind leaders (a negative value indicates that safe inse...
std::pair< MSVehicle *const, double > getFollower(const MSVehicle *ego, double egoPos, double dist, bool ignoreMinorLinks) const
Find follower vehicle for the given ego vehicle (which may be on the opposite direction lane)
std::vector< const MSJunction * > getUpcomingJunctions(double pos, double range, const std::vector< MSLane * > &contLanes) const
Returns all upcoming junctions within given range along the given (non-internal) continuation lanes m...
void addIncomingLane(MSLane *lane, MSLink *viaLink)
const MSEdge * getNextNormal() const
Returns the lane's follower if it is an internal lane, the edge of the lane otherwise.
void addLink(MSLink *link)
Delayed initialization.
std::set< MSVehicle * > getVehiclesInRange(const double a, const double b) const
Returns all vehicles on the lane overlapping with the interval [a,b].
void enteredByLaneChange(MSVehicle *v)
double getDepartPosLat(const MSVehicle &veh)
LinkState getIncomingLinkState() const
get the state of the link from the logical predecessor to this lane
void updateLengthSum()
updated current vehicle length sum (delayed to avoid lane-order-dependency)
static const long CHANGE_PERMISSIONS_PERMANENT
MSLane * getCanonicalPredecessorLane() const
void resetPermissions(long long transientID)
MSVehicle * getLastFullVehicle() const
returns the last vehicle for which this lane is responsible or 0
static void loadRNGState(int index, const std::string &state)
load random number generator state for the given rng index
const std::string myLaneType
the type of this lane
VehCont myManeuverReservations
The vehicles which registered maneuvering into the lane within their current action step....
void addLeaders(const MSVehicle *vehicle, double vehPos, MSLeaderDistanceInfo &result, bool oppositeDirection=false)
get leaders for ego on the given lane
static double myCheckJunctionCollisionMinGap
double getLength() const
Returns the lane's length.
double myBruttoVehicleLengthSum
The current length of all vehicles on this lane, including their minGaps.
std::vector< const MSLink * > getUpcomingLinks(double pos, double range, const std::vector< MSLane * > &contLanes) const
Returns all upcoming links within given range along the given (non-internal) continuation lanes measu...
const MSLane * getFirstInternalInConnection(double &offset) const
Returns 0 if the lane is not internal. Otherwise the first part of the connection (sequence of intern...
static int getNumRNGs()
return the number of RNGs
void handleCollisionBetween(SUMOTime timestep, const std::string &stage, const MSVehicle *collider, const MSVehicle *victim, double gap, double latGap, std::set< const MSVehicle *, ComparatorNumericalIdLess > &toRemove, std::set< const MSVehicle *, ComparatorNumericalIdLess > &toTeleport) const
take action upon collision
double getMaximumBrakeDist() const
compute maximum braking distance on this lane
const MSLane * getInternalFollowingLane(const MSLane *const) const
returns the internal lane leading to the given lane or nullptr, if there is none
static std::vector< SumoRNG > myRNGs
virtual void swapAfterLaneChange(SUMOTime t)
moves myTmpVehicles int myVehicles after a lane change procedure
std::pair< MSVehicle *const, double > getCriticalLeader(double dist, double seen, double speed, const MSVehicle &veh) const
Returns the most dangerous leader and the distance to him.
StopOffset myLaneStopOffset
const MSLeaderInfo getLastVehicleInformation(const MSVehicle *ego, double latOffset, double minPos=0, bool allowCached=true) const
Returns the last vehicles on the lane.
static void initRNGs(const OptionsCont &oc)
initialize rngs
std::set< MSVehicle * > getSurroundingVehicles(double startPos, double downstreamDist, double upstreamDist, std::shared_ptr< LaneCoverageInfo > checkedLanes) const
Returns all vehicles closer than downstreamDist along the road network starting on the given position...
void clearState()
Remove all vehicles before quick-loading state.
MSLane * myCanonicalPredecessorLane
Similar to LogicalPredecessorLane,.
bool myNeedsCollisionCheck
whether a collision check is currently needed
bool isLinkEnd(std::vector< MSLink * >::const_iterator &i) const
virtual double setPartialOccupation(MSVehicle *v)
Sets the information about a vehicle lapping into this lane.
double getVehicleMaxSpeed(const SUMOTrafficObject *const veh) const
Returns the lane's maximum speed, given a vehicle's speed limit adaptation.
double getRightSideOnEdge() const
std::pair< MSVehicle *const, double > getOppositeFollower(const MSVehicle *ego) const
bool hasPedestrians() const
whether the lane has pedestrians on it
const std::vector< std::pair< const MSLane *, const MSEdge * > > getOutgoingViaLanes() const
get the list of outgoing lanes
MSVehicle * getPartialBehind(const MSVehicle *ego) const
void setLaneStopOffset(const StopOffset &stopOffset)
Set vehicle class specific stopOffsets.
double myBruttoVehicleLengthSumToRemove
The length of all vehicles that have left this lane in the current step (this lane,...
void leftByLaneChange(MSVehicle *v)
MSLane * getCanonicalSuccessorLane() const
const std::vector< IncomingLaneInfo > & getIncomingLanes() const
std::vector< StopWatch< std::chrono::nanoseconds > > myStopWatch
void setPermissions(SVCPermissions permissions, long long transientID)
Sets the permissions to the given value. If a transientID is given, the permissions are recored as te...
const double myWidth
Lane width [m].
bool lastInsertion(MSVehicle &veh, double mspeed, double posLat, bool patchSpeed)
inserts vehicle as close as possible to the last vehicle on this lane (or at the end of the lane if t...
void changeLanes(const SUMOTime time)
double getOppositePos(double pos) const
return the corresponding position on the opposite lane
SVCPermissions myChangeRight
const double myLengthGeometryFactor
precomputed myShape.length / myLength
virtual void executeMovements(const SUMOTime t)
Executes planned vehicle movements with regards to right-of-way.
MSLane * getLogicalPredecessorLane() const
get the most likely precedecessor lane (sorted using by_connections_to_sorter). The result is cached ...
double getBruttoOccupancy() const
Returns the brutto (including minGaps) occupancy of this lane during the last step.
double getFuelConsumption() const
Returns the sum of last step fuel consumption.
AnyVehicleIterator anyVehiclesUpstreamEnd() const
end iterator for iterating over all vehicles touching this lane in upstream direction
int myIndex
The lane index.
double getMeanSpeedBike() const
get the mean speed of all bicycles on this lane
void updateLeaderInfo(const MSVehicle *veh, VehCont::reverse_iterator &vehPart, VehCont::reverse_iterator &vehRes, MSLeaderInfo &ahead) const
This updates the MSLeaderInfo argument with respect to the given MSVehicle. All leader-vehicles on th...
FXSynchQue< MSVehicle *, std::vector< MSVehicle * > > myVehBuffer
Buffer for vehicles that moved from their previous lane onto this one. Integrated after all vehicles ...
double getWaitingSeconds() const
Returns the overall waiting time on this lane.
void setMaxSpeed(double val)
Sets a new maximum speed for the lane (used by TraCI and MSCalibrator)
static bool dictionary(const std::string &id, MSLane *lane)
Static (sic!) container methods {.
void detectPedestrianJunctionCollision(const MSVehicle *collider, const PositionVector &colliderBoundary, const MSLane *foeLane, SUMOTime timestep, const std::string &stage)
detect whether a vehicle collids with pedestrians on the junction
virtual void detectCollisions(SUMOTime timestep, const std::string &stage)
Check if vehicles are too close.
std::vector< MSLink * > myLinks
MSLeaderDistanceInfo getFollowersOnConsecutive(const MSVehicle *ego, double backOffset, bool allSublanes, double searchDist=-1, bool ignoreMinorLinks=false) const
return the sublane followers with the largest missing rear gap among all predecessor lanes (within di...
MSVehicle * getLastAnyVehicle() const
returns the last vehicle that is fully or partially on this lane
VehCont myPartialVehicles
The lane's partial vehicles. This container holds all vehicles that are partially on this lane but wh...
double getElectricityConsumption() const
Returns the sum of last step electricity consumption.
void sortManeuverReservations()
sorts myManeuverReservations
MSEdge & getEdge() const
Returns the lane's edge.
const PositionVector & getShape() const
Returns this lane's shape.
AnyVehicleIterator anyVehiclesUpstreamBegin() const
begin iterator for iterating over all vehicles touching this lane in upstream direction
std::vector< const MSLane * > getNormalIncomingLanes() const
get the list of all direct (disregarding internal predecessors) non-internal predecessor lanes of thi...
virtual void resetPartialOccupation(MSVehicle *v)
Removes the information about a vehicle lapping into this lane.
AnyVehicleIterator anyVehiclesBegin() const
begin iterator for iterating over all vehicles touching this lane in downstream direction
double getHarmonoise_NoiseEmissions() const
Returns the sum of last step noise emissions.
std::pair< MSVehicle *const, double > getLeader(const MSVehicle *veh, const double vehPos, const std::vector< MSLane * > &bestLaneConts, double dist=-1, bool checkTmpVehicles=false) const
Returns the immediate leader of veh and the distance to veh starting on this lane.
static bool myExtrapolateSubstepDepart
MSLane * getOpposite() const
return the neighboring opposite direction lane for lane changing or nullptr
void setLength(double val)
Sets a new length for the lane (used by TraCI only)
std::map< MSEdge *, std::vector< MSLane * > > myApproachingLanes
All direct internal and direct (disregarding internal predecessors) non-internal predecessor lanes of...
virtual void releaseVehicles() const
Allows to use the container for microsimulation again.
bool mustCheckJunctionCollisions() const
whether this lane must check for junction collisions
virtual void setManeuverReservation(MSVehicle *v)
Registers the lane change intentions (towards this lane) for the given vehicle.
MSLane * getBidiLane() const
retrieve bidirectional lane or nullptr
static double myCollisionMinGapFactor
std::pair< MSVehicle *const, double > getLeaderOnConsecutive(double dist, double seen, double speed, const MSVehicle &veh, const std::vector< MSLane * > &bestLaneConts) const
Returns the immediate leader and the distance to him.
double getCOEmissions() const
Returns the sum of last step CO emissions.
SUMOTime myLeaderInfoTime
time step for which myLeaderInfo was last updated
@ COLLISION_ACTION_TELEPORT
@ COLLISION_ACTION_REMOVE
MSLane * getParallelOpposite() const
return the opposite direction lane of this lanes edge or nullptr
std::map< std::string, MSLane * > DictType
definition of the static dictionary type
std::pair< MSVehicle *const, double > getOppositeLeader(const MSVehicle *ego, double dist, bool oppositeDir) const
double getSpaceTillLastStanding(const MSVehicle *ego, bool &foundStopped) const
return the empty space up to the last standing vehicle or the empty space on the whole lane if no veh...
const MSLane * getNormalPredecessorLane() const
get normal lane leading to this internal lane, for normal lanes, the lane itself is returned
virtual bool appropriate(const MSVehicle *veh) const
double getWidth() const
Returns the lane's width.
bool freeInsertion(MSVehicle &veh, double speed, double posLat, MSMoveReminder::Notification notification=MSMoveReminder::NOTIFICATION_DEPARTED)
Tries to insert the given vehicle on any place.
virtual void addMoveReminder(MSMoveReminder *rem)
Add a move-reminder to move-reminder container.
double getMeanSpeed() const
Returns the mean speed on this lane.
double myNettoVehicleLengthSumToRemove
The length of all vehicles that have left this lane in the current step (this lane,...
void loadState(const std::vector< std::string > &vehIDs, MSVehicleControl &vc)
Loads the state of this segment with the given parameters.
double getHCEmissions() const
Returns the sum of last step HC emissions.
static CollisionAction getCollisionAction()
saves leader/follower vehicles and their distances relative to an ego vehicle
virtual std::string toString() const
print a debugging representation
CLeaderDist getClosest() const
return vehicle with the smalles gap
virtual int addLeader(const MSVehicle *veh, double gap, double latOffset=0, int sublane=-1)
virtual int addLeader(const MSVehicle *veh, bool beyond, double latOffset=0)
int numFreeSublanes() const
virtual std::string toString() const
print a debugging representation
LinkState getState() const
Returns the current state of the link.
MSLane * getLane() const
Returns the connected lane.
std::vector< LinkLeader > LinkLeaders
double getInternalLengthsAfter() const
Returns the cumulative length of all internal lanes after this link.
const std::vector< MSLink * > & getFoeLinks() const
Something on a lane to be noticed about vehicle movement.
Notification
Definition of a vehicle state.
@ NOTIFICATION_ARRIVED
The vehicle arrived at its destination (is deleted)
@ NOTIFICATION_TELEPORT_ARRIVED
The vehicle was teleported out of the net.
@ NOTIFICATION_DEPARTED
The vehicle has departed (was inserted into the network)
@ NOTIFICATION_VAPORIZED_VAPORIZER
The vehicle got vaporized with a vaporizer.
@ NOTIFICATION_VAPORIZED_COLLISION
The vehicle got removed by a collision.
@ NOTIFICATION_LOAD_STATE
The vehicle has been loaded from a state file.
@ NOTIFICATION_TELEPORT
The vehicle is being teleported.
The simulated network and simulation perfomer.
@ COLLISION
The vehicle is involved in a collision.
static MSNet * getInstance()
Returns the pointer to the unique instance of MSNet (singleton).
static const std::string STAGE_MOVEMENTS
MSVehicleControl & getVehicleControl()
Returns the vehicle control.
SUMOTime getCurrentTimeStep() const
Returns the current simulation step.
const std::map< SUMOVehicleClass, double > * getRestrictions(const std::string &id) const
Returns the restrictions for an edge type If no restrictions are present, 0 is returned.
MSEdgeControl & getEdgeControl()
Returns the edge control.
MSInsertionControl & getInsertionControl()
Returns the insertion control.
void informVehicleStateListener(const SUMOVehicle *const vehicle, VehicleState to, const std::string &info="")
Informs all added listeners about a vehicle's state change.
bool hasPersons() const
Returns whether persons are simulated.
virtual MSTransportableControl & getPersonControl()
Returns the person control.
bool registerCollision(const SUMOTrafficObject *collider, const SUMOTrafficObject *victim, const std::string &collisionType, const MSLane *lane, double pos)
register collision and return whether it was the first one involving these vehicles
virtual bool hasPedestrians(const MSLane *lane)
whether the given lane has pedestrians on it
virtual PersonDist nextBlocking(const MSLane *lane, double minPos, double minRight, double maxLeft, double stopTime=0)
returns the next pedestrian beyond minPos that is laterally between minRight and maxLeft or 0
static bool hasOncomingRailTraffic(MSLink *link)
static bool hasInsertionConstraint(MSLink *link, const MSVehicle *veh, std::string &info)
const MSEdge * getLastEdge() const
returns the destination edge
MSRouteIterator begin() const
Returns the begin of the list of edges to pass.
const MSLane * lane
The lane to stop at (microsim only)
double getEndPos(const SUMOVehicle &veh) const
return halting position for upcoming stop;
const SUMOVehicleParameter::Stop pars
The stop parameter.
MSPModel * getMovementModel()
Returns the default movement model for this kind of transportables.
bool isRemoteAffected(SUMOTime t) const
The class responsible for building and deletion of vehicles.
void registerTeleportYield()
register one non-collision-related teleport
double getMinDeceleration() const
return the minimum deceleration capability for all vehicles that ever entered the network
SUMOVehicle * getVehicle(const std::string &id) const
Returns the vehicle with the given id.
void registerTeleportJam()
register one non-collision-related teleport
double getMaxSpeedFactor() const
return the maximum speed factor for all vehicles that ever entered the network
void scheduleVehicleRemoval(SUMOVehicle *veh, bool checkDuplicate=false)
Removes a vehicle after it has ended.
void registerTeleportWrongLane()
register one non-collision-related teleport
void registerCollision(bool teleport)
registers one collision-related teleport
Representation of a vehicle in the micro simulation.
double getRightSideOnEdge(const MSLane *lane=0) const
Get the vehicle's lateral position on the edge of the given lane (or its current edge if lane == 0)
double getSafeFollowSpeed(const std::pair< const MSVehicle *, double > leaderInfo, const double seen, const MSLane *const lane, double distToCrossing) const
compute safe speed for following the given leader
void updateBestLanes(bool forceRebuild=false, const MSLane *startLane=0)
computes the best lanes to use in order to continue the route
bool isOnRoad() const
Returns the information whether the vehicle is on a road (is simulated)
PositionVector getBoundingPoly(double offset=0) const
get bounding polygon
void setTentativeLaneAndPosition(MSLane *lane, double pos, double posLat=0)
set tentative lane and position during insertion to ensure that all cfmodels work (some of them requi...
SUMOTime getWaitingTime() const
Returns the SUMOTime waited (speed was lesser than 0.1m/s)
const std::vector< MSLane * > & getFurtherLanes() const
void enterLaneAtInsertion(MSLane *enteredLane, double pos, double speed, double posLat, MSMoveReminder::Notification notification)
Update when the vehicle enters a new lane in the emit step.
bool isFrontOnLane(const MSLane *lane) const
Returns the information whether the front of the vehicle is on the given lane.
MSAbstractLaneChangeModel & getLaneChangeModel()
MSLane * getMutableLane() const
Returns the lane the vehicle is on Non const version indicates that something volatile is going on.
const std::vector< MSLane * > getUpstreamOppositeLanes() const
Returns the sequence of opposite lanes corresponding to past lanes.
PositionVector getBoundingBox(double offset=0) const
get bounding rectangle
Position getPosition(const double offset=0) const
Return current position (x/y, cartesian)
const std::vector< MSLane * > & getBestLanesContinuation() const
Returns the best sequence of lanes to continue the route starting at myLane.
bool ignoreCollision() const
whether this vehicle is except from collision checks
void onRemovalFromNet(const MSMoveReminder::Notification reason)
Called when the vehicle is removed from the network.
bool resumeFromStopping()
double getBackPositionOnLane(const MSLane *lane) const
Get the vehicle's position relative to the given lane.
void leaveLane(const MSMoveReminder::Notification reason, const MSLane *approachedLane=0)
Update of members if vehicle leaves a new lane in the lane change step or at arrival.
double getLatOffset(const MSLane *lane) const
Get the offset that that must be added to interpret myState.myPosLat for the given lane.
bool hasArrived() const
Returns whether this vehicle has already arived (reached the arrivalPosition on its final edge)
bool isLeader(const MSLink *link, const MSVehicle *veh) const
whether the given vehicle must be followed at the given junction
SUMOTime collisionStopTime() const
Returns the remaining time a vehicle needs to stop due to a collision. A negative value indicates tha...
bool executeMove()
Executes planned vehicle movements with regards to right-of-way.
Influencer & getInfluencer()
double getRightSideOnLane() const
Get the vehicle's lateral position on the lane:
double getLateralPositionOnLane() const
Get the vehicle's lateral position on the lane.
double getSpeed() const
Returns the vehicle's current speed.
const std::vector< LaneQ > & getBestLanes() const
Returns the description of best lanes to use in order to continue the route.
double processNextStop(double currentVelocity)
Processes stops, returns the velocity needed to reach the stop.
double getPositionOnLane() const
Get the vehicle's position along the lane.
const MSLane * getLane() const
Returns the lane the vehicle is on.
const MSCFModel & getCarFollowModel() const
Returns the vehicle's car following model definition.
bool onFurtherEdge(const MSEdge *edge) const
whether this vehicle has its back (and no its front) on the given edge
double getLateralOverlap() const
return the amount by which the vehicle extends laterally outside it's primary lane
double getAngle() const
Returns the vehicle's direction in radians.
bool hasInfluencer() const
whether the vehicle is individually influenced (via TraCI or special parameters)
void executeFractionalMove(double dist)
move vehicle forward by the given distance during insertion
double getCenterOnEdge(const MSLane *lane=0) const
Get the vehicle's lateral position on the edge of the given lane (or its current edge if lane == 0)
static MSVehicleTransfer * getInstance()
Returns the instance of this object.
void add(const SUMOTime t, MSVehicle *veh)
Adds a vehicle to this transfer object.
double getLengthWithGap() const
Get vehicle's length including the minimum gap [m].
double getWidth() const
Get the width which vehicles of this class shall have when being drawn.
SUMOVehicleClass getVehicleClass() const
Get this vehicle type's vehicle class.
double getMinGap() const
Get the free space in front of vehicles of this class.
double getLength() const
Get vehicle's length [m].
Base class for objects which have an id.
std::string myID
The name of the object.
static std::string getIDSecure(const T *obj, const std::string &fallBack="NULL")
get an identifier for Named-like object which may be Null
const std::string & getID() const
Returns the id.
A RT-tree for efficient storing of SUMO's Named objects.
A storage for options typed value containers)
double getFloat(const std::string &name) const
Returns the double-value of the named option (only for Option_Float)
int getInt(const std::string &name) const
Returns the int-value of the named option (only for Option_Integer)
std::string getString(const std::string &name) const
Returns the string-value of the named option (only for Option_String)
bool getBool(const std::string &name) const
Returns the boolean-value of the named option (only for Option_Bool)
Static storage of an output device and its base (abstract) implementation.
OutputDevice & openTag(const std::string &xmlElement)
Opens an XML tag.
OutputDevice & writeAttr(const SumoXMLAttr attr, const T &val)
writes a named attribute
bool closeTag(const std::string &comment="")
Closes the most recently opened tag and optionally adds a comment.
void unsetParameter(const std::string &key)
Removes a parameter.
virtual void setParameter(const std::string &key, const std::string &value)
Sets a parameter.
double distanceTo2D(const Position &p2) const
returns the euclidean distance in the x-y-plane
bool overlapsWith(const AbstractPoly &poly, double offset=0) const
Returns the information whether the given polygon overlaps with this.
Boundary getBoxBoundary() const
Returns a boundary enclosing this list of lines.
double angleAt2D(int pos) const
get angle in certain position of position vector
static void loadState(const std::string &state, SumoRNG *rng=nullptr)
load rng state from string
static void initRand(SumoRNG *which=nullptr, const bool random=false, const int seed=23423)
Initialises the random number generator with hardware randomness or seed.
static std::string saveState(SumoRNG *rng=nullptr)
save rng state to string
static double rand(SumoRNG *rng=nullptr)
Returns a random real number in [0, 1)
virtual const MSVehicleType & getVehicleType() const =0
Returns the object's "vehicle" type.
Representation of a vehicle.
virtual const MSEdge * succEdge(int nSuccs) const =0
Returns the nSuccs'th successor of edge the vehicle is currently at.
Definition of vehicle stop (position and duration)
std::string lane
The lane to stop at.
double startPos
The stopping position start.
int parametersSet
Information for the output which parameter were set.
double endPos
The stopping position end.
SUMOTime duration
The stopping duration.
Structure representing possible vehicle parameter.
double departPosLat
(optional) The lateral position the vehicle shall depart from
ArrivalSpeedDefinition arrivalSpeedProcedure
Information how the vehicle's end speed shall be chosen.
double departSpeed
(optional) The initial speed of the vehicle
DepartPosLatDefinition departPosLatProcedure
Information how the vehicle shall choose the lateral departure position.
double departPos
(optional) The position the vehicle shall depart from
DepartSpeedDefinition departSpeedProcedure
Information how the vehicle's initial speed shall be chosen.
double arrivalSpeed
(optional) The final speed of the vehicle (not used yet)
DepartPosDefinition departPosProcedure
Information how the vehicle shall choose the departure position.
A scoped lock which only triggers on condition.
bool isDefined() const
check if stopOffset was defined
SVCPermissions getPermissions() const
get permissions
double getOffset() const
get offset
std::pair< MSVehicle *, double > vehAndGap