예제 #1
0
void
MSRailSignal::collectConflictLinks(MSLane* toLane, double length,
                                   std::vector<MSLane*>& backwardBlock,
                                   std::vector<MSLink*>& conflictLinks,
                                   LaneSet& visited,
                                   bool checkFoes) {
    while (toLane != nullptr) {
        //std::cout << "collectConflictLinks " << getID() << " toLane=" << toLane->getID() << " length=" << length
        //    << " backward=" << toString(backwardBlock)
        //    << " conflictLinks=" << conflictLinks.size()
        //    << " visited=" << visited.size()
        //    << " checkFoes=" << checkFoes
        //    << "\n";
        const auto& incomingLaneInfos = toLane->getIncomingLanes();
        MSLane* orig = toLane;
        toLane = nullptr;
        for (const auto& ili : incomingLaneInfos) {
            if (ili.viaLink->getDirection() == LINKDIR_TURN) {
                continue;
            }
            if (visited.count(ili.lane) != 0) {
                continue;
            }
            if (ili.viaLink->getTLLogic() != nullptr) {
                conflictLinks.push_back(ili.viaLink);
                continue;
            }
            backwardBlock.push_back(ili.lane);
            visited.insert(ili.lane);
            length += orig->getLength();
            if (length > MAX_BLOCK_LENGTH) {
                if (myNumWarnings < MAX_SIGNAL_WARNINGS) {
                    WRITE_WARNING("incoming conflict block after rail signal junction '" + getID() +
                                  "' exceeds maximum length (stopped searching after lane '" + orig->getID() + "' (length=" + toString(length) + "m).");
                }
                myNumWarnings++;
                return;
            }
            if (toLane == nullptr) {
                toLane = ili.lane;
            } else {
                collectConflictLinks(ili.lane, length, backwardBlock, conflictLinks, visited, false);
            }
        }
        if (checkFoes && orig->isInternal()) {
            // check for crossed tracks
            MSLink* link = orig->getIncomingLanes().front().viaLink;
            if (link->getDirection() != LINKDIR_TURN) {
                for (const MSLane* foeConst : link->getFoeLanes()) {
                    MSLane* foe = const_cast<MSLane*>(foeConst);
                    if (visited.count(foe) == 0) {
                        backwardBlock.push_back(foe);
                        visited.insert(foe);
                        collectConflictLinks(foe, length, backwardBlock, conflictLinks, visited, false);
                    }
                }
            }
        }
    }
}
예제 #2
0
const std::vector<MSLane*>
MSLogicJunction::getInternalLanes() const {
    // Besides the lanes im myInternal lanes, which are only the last parts of the connections,
    // this collects all lanes on the junction
    std::vector<MSLane*> allInternalLanes;
    for (std::vector<MSLane*>::const_iterator i = myInternalLanes.begin(); i != myInternalLanes.end(); ++i) {
        MSLane* l = *i;
        while (l != nullptr) {
            allInternalLanes.push_back(l);
            const std::vector<MSLane::IncomingLaneInfo> incoming = l->getIncomingLanes();
            if (incoming.size() == 0) {
                break;
            }
            assert(l->getIncomingLanes().size() == 1);
            l = l->getIncomingLanes()[0].lane;
            if (!l->isInternal()) {
                break;
            }
        }
    }
    return allInternalLanes;
}
예제 #3
0
std::pair<MSVehicle * const, SUMOReal>
MSLane::getFollowerOnConsecutive(SUMOReal dist, SUMOReal seen, SUMOReal leaderSpeed, SUMOReal backOffset) const {
    // ok, a vehicle has not noticed the lane about itself;
    //  iterate as long as necessary to search for an approaching one
    std::set<MSLane*> visited;
    std::vector<std::pair<MSVehicle *, SUMOReal> > possible;
    std::vector<MSLane::IncomingLaneInfo> newFound;
    std::vector<MSLane::IncomingLaneInfo> toExamine = myIncomingLanes;
    while (toExamine.size()!=0) {
        for (std::vector<MSLane::IncomingLaneInfo>::iterator i=toExamine.begin(); i!=toExamine.end(); ++i) {
            /*
            if ((*i).viaLink->getState()==MSLink::LINKSTATE_TL_RED) {
                continue;
            }
            */
            MSLane *next = (*i).lane;
            if (next->getFirstVehicle()!=0) {
                MSVehicle * v = (MSVehicle*) next->getFirstVehicle();
                SUMOReal agap = (*i).length - v->getPositionOnLane() + backOffset;
                if (!v->getCarFollowModel().hasSafeGap(v->getCarFollowModel().maxNextSpeed(v->getSpeed()), agap, leaderSpeed, v->getLane().getMaxSpeed())) {
                    possible.push_back(std::make_pair(v, (*i).length-v->getPositionOnLane()+seen));
                }
            } else {
                if ((*i).length+seen<dist) {
                    const std::vector<MSLane::IncomingLaneInfo> &followers = next->getIncomingLanes();
                    for (std::vector<MSLane::IncomingLaneInfo>::const_iterator j=followers.begin(); j!=followers.end(); ++j) {
                        if (visited.find((*j).lane)==visited.end()) {
                            visited.insert((*j).lane);
                            MSLane::IncomingLaneInfo ili;
                            ili.lane = (*j).lane;
                            ili.length = (*j).length + (*i).length;
                            ili.viaLink = (*j).viaLink;
                            newFound.push_back(ili);
                        }
                    }
                }
            }
        }
        toExamine.clear();
        swap(newFound, toExamine);
    }
    if (possible.size()==0) {
        return std::pair<MSVehicle * const, SUMOReal>(0, -1);
    }
    sort(possible.begin(), possible.end(), by_second_sorter());
    return *(possible.begin());
}