SUMO - Simulation of Urban MObility

RODFNet.cpp

Go to the documentation of this file.
00001 /****************************************************************************/
00010 // A DFROUTER-network
00011 /****************************************************************************/
00012 // SUMO, Simulation of Urban MObility; see http://sumo.sourceforge.net/
00013 // Copyright (C) 2001-2012 DLR (http://www.dlr.de/) and contributors
00014 /****************************************************************************/
00015 //
00016 //   This file is part of SUMO.
00017 //   SUMO is free software: you can redistribute it and/or modify
00018 //   it under the terms of the GNU General Public License as published by
00019 //   the Free Software Foundation, either version 3 of the License, or
00020 //   (at your option) any later version.
00021 //
00022 /****************************************************************************/
00023 // ===========================================================================
00024 // included modules
00025 // ===========================================================================
00026 #ifdef _MSC_VER
00027 #include <windows_config.h>
00028 #else
00029 #include <config.h>
00030 #endif
00031 
00032 #include <iostream>
00033 #include <map>
00034 #include <vector>
00035 #include <iterator>
00036 #include "RODFNet.h"
00037 #include "RODFDetector.h"
00038 #include "RODFRouteDesc.h"
00039 #include "RODFDetectorFlow.h"
00040 #include "RODFEdge.h"
00041 #include <cmath>
00042 #include <utils/common/MsgHandler.h>
00043 #include <utils/common/ToString.h>
00044 #include <utils/common/UtilExceptions.h>
00045 #include <utils/geom/GeomHelper.h>
00046 
00047 #ifdef CHECK_MEMORY_LEAKS
00048 #include <foreign/nvwa/debug_new.h>
00049 #endif // CHECK_MEMORY_LEAKS
00050 
00051 
00052 // ===========================================================================
00053 // method definitions
00054 // ===========================================================================
00055 RODFNet::RODFNet(bool amInHighwayMode)
00056     : RONet(), myAmInHighwayMode(amInHighwayMode),
00057       mySourceNumber(0), mySinkNumber(0), myInBetweenNumber(0), myInvalidNumber(0) {
00058     myDisallowedEdges = OptionsCont::getOptions().getStringVector("disallowed-edges");
00059     myKeepTurnarounds = OptionsCont::getOptions().getBool("keep-turnarounds");
00060 }
00061 
00062 
00063 RODFNet::~RODFNet() {
00064 }
00065 
00066 
00067 void
00068 RODFNet::buildApproachList() {
00069     const std::map<std::string, ROEdge*> &edges = getEdgeMap();
00070     for (std::map<std::string, ROEdge*>::const_iterator rit = edges.begin(); rit != edges.end(); ++rit) {
00071         ROEdge* ce = (*rit).second;
00072         unsigned int i = 0;
00073         unsigned int length_size = ce->getNoFollowing();
00074         for (i = 0; i < length_size; i++) {
00075             ROEdge* help = ce->getFollower(i);
00076             if (find(myDisallowedEdges.begin(), myDisallowedEdges.end(), help->getID()) != myDisallowedEdges.end()) {
00077                 // edges in sinks will not be used
00078                 continue;
00079             }
00080             if (!myKeepTurnarounds && help->getToNode() == ce->getFromNode()) {
00081                 // do not use turnarounds
00082                 continue;
00083             }
00084             // add the connection help->ce to myApproachingEdges
00085             if (myApproachingEdges.find(help) == myApproachingEdges.end()) {
00086                 myApproachingEdges[help] = std::vector<ROEdge*>();
00087             }
00088             myApproachingEdges[help].push_back(ce);
00089             // add the connection ce->help to myApproachingEdges
00090             if (myApproachedEdges.find(ce) == myApproachedEdges.end()) {
00091                 myApproachedEdges[ce] = std::vector<ROEdge*>();
00092             }
00093             myApproachedEdges[ce].push_back(help);
00094         }
00095     }
00096 }
00097 
00098 
00099 void
00100 RODFNet::buildDetectorEdgeDependencies(RODFDetectorCon& detcont) const {
00101     myDetectorsOnEdges.clear();
00102     myDetectorEdges.clear();
00103     const std::vector<RODFDetector*> &dets = detcont.getDetectors();
00104     {
00105         for (std::vector<RODFDetector*>::const_iterator i = dets.begin(); i != dets.end(); ++i) {
00106             ROEdge* e = getDetectorEdge(**i);
00107 
00108             if (myDetectorsOnEdges.find(e) == myDetectorsOnEdges.end()) {
00109                 myDetectorsOnEdges[e] = std::vector<std::string>();
00110             }
00111             myDetectorsOnEdges[e].push_back((*i)->getID());
00112 
00113             myDetectorEdges[(*i)->getID()] = e;
00114         }
00115     }
00116 }
00117 
00118 
00119 void
00120 RODFNet::computeTypes(RODFDetectorCon& detcont,
00121                       bool sourcesStrict) const {
00122     PROGRESS_BEGIN_MESSAGE("Computing detector types");
00123     const std::vector< RODFDetector*> &dets = detcont.getDetectors();
00124     // build needed information. first
00125     buildDetectorEdgeDependencies(detcont);
00126     // compute detector types then
00127     {
00128         for (std::vector< RODFDetector*>::const_iterator i = dets.begin(); i != dets.end(); ++i) {
00129             if (isSource(**i, detcont, sourcesStrict)) {
00130                 (*i)->setType(SOURCE_DETECTOR);
00131                 mySourceNumber++;
00132             }
00133             if (isDestination(**i, detcont)) {
00134                 (*i)->setType(SINK_DETECTOR);
00135                 mySinkNumber++;
00136             }
00137             if ((*i)->getType() == TYPE_NOT_DEFINED) {
00138                 (*i)->setType(BETWEEN_DETECTOR);
00139                 myInBetweenNumber++;
00140             }
00141         }
00142     }
00143     // recheck sources
00144     {
00145         for (std::vector< RODFDetector*>::const_iterator i = dets.begin(); i != dets.end(); ++i) {
00146             if ((*i)->getType() == SOURCE_DETECTOR && isFalseSource(**i, detcont)) {
00147                 (*i)->setType(DISCARDED_DETECTOR);
00148                 myInvalidNumber++;
00149                 mySourceNumber--;
00150             }
00151         }
00152     }
00153     // print results
00154     PROGRESS_DONE_MESSAGE();
00155     WRITE_MESSAGE("Computed detector types:");
00156     WRITE_MESSAGE(" " + toString(mySourceNumber) + " source detectors");
00157     WRITE_MESSAGE(" " + toString(mySinkNumber) + " sink detectors");
00158     WRITE_MESSAGE(" " + toString(myInBetweenNumber) + " in-between detectors");
00159     WRITE_MESSAGE(" " + toString(myInvalidNumber) + " invalid detectors");
00160 }
00161 
00162 
00163 bool
00164 RODFNet::hasInBetweenDetectorsOnly(ROEdge* edge,
00165                                    const RODFDetectorCon& detectors) const {
00166     assert(myDetectorsOnEdges.find(edge) != myDetectorsOnEdges.end());
00167     const std::vector<std::string> &detIDs = myDetectorsOnEdges.find(edge)->second;
00168     std::vector<std::string>::const_iterator i;
00169     for (i = detIDs.begin(); i != detIDs.end(); ++i) {
00170         const RODFDetector& det = detectors.getDetector(*i);
00171         if (det.getType() != BETWEEN_DETECTOR) {
00172             return false;
00173         }
00174     }
00175     return true;
00176 }
00177 
00178 
00179 bool
00180 RODFNet::hasSourceDetector(ROEdge* edge,
00181                            const RODFDetectorCon& detectors) const {
00182     assert(myDetectorsOnEdges.find(edge) != myDetectorsOnEdges.end());
00183     const std::vector<std::string> &detIDs = myDetectorsOnEdges.find(edge)->second;
00184     std::vector<std::string>::const_iterator i;
00185     for (i = detIDs.begin(); i != detIDs.end(); ++i) {
00186         const RODFDetector& det = detectors.getDetector(*i);
00187         if (det.getType() == SOURCE_DETECTOR) {
00188             return true;
00189         }
00190     }
00191     return false;
00192 }
00193 
00194 
00195 
00196 void
00197 RODFNet::computeRoutesFor(ROEdge* edge, RODFRouteDesc& base, int /*no*/,
00198                           bool keepUnfoundEnds,
00199                           bool keepShortestOnly,
00200                           std::vector<ROEdge*> &/*visited*/,
00201                           const RODFDetector& det, RODFRouteCont& into,
00202                           const RODFDetectorCon& detectors,
00203                           int maxFollowingLength,
00204                           std::vector<ROEdge*> &seen) const {
00205     std::vector<RODFRouteDesc> unfoundEnds;
00206     std::priority_queue<RODFRouteDesc, std::vector<RODFRouteDesc>, DFRouteDescByTimeComperator> toSolve;
00207     std::map<ROEdge*, std::vector<ROEdge*> > dets2Follow;
00208     dets2Follow[edge] = std::vector<ROEdge*>();
00209     base.passedNo = 0;
00210     SUMOReal minDist = OptionsCont::getOptions().getFloat("min-route-length");
00211     toSolve.push(base);
00212     while (!toSolve.empty()) {
00213         RODFRouteDesc current = toSolve.top();
00214         toSolve.pop();
00215         ROEdge* last = *(current.edges2Pass.end() - 1);
00216         if (hasDetector(last)) {
00217             if (dets2Follow.find(last) == dets2Follow.end()) {
00218                 dets2Follow[last] = std::vector<ROEdge*>();
00219             }
00220             for (std::vector<ROEdge*>::reverse_iterator i = current.edges2Pass.rbegin() + 1; i != current.edges2Pass.rend(); ++i) {
00221                 if (hasDetector(*i)) {
00222                     dets2Follow[*i].push_back(last);
00223                     break;
00224                 }
00225             }
00226         }
00227 
00228         // do not process an edge twice
00229         if (find(seen.begin(), seen.end(), last) != seen.end() && keepShortestOnly) {
00230             continue;
00231         }
00232         seen.push_back(last);
00233         // end if the edge has no further connections
00234         if (!hasApproached(last)) {
00235             // ok, no further connections to follow
00236             current.factor = 1.;
00237             SUMOReal cdist = current.edges2Pass[0]->getFromNode()->getPosition().distanceTo(current.edges2Pass.back()->getToNode()->getPosition());
00238             if (minDist < cdist) {
00239                 into.addRouteDesc(current);
00240             }
00241             continue;
00242         }
00243         // check for passing detectors:
00244         //  if the current last edge is not the one the detector is placed on ...
00245         bool addNextNoFurther = false;
00246         if (last != getDetectorEdge(det)) {
00247             // ... if there is a detector ...
00248             if (hasDetector(last)) {
00249                 if (!hasInBetweenDetectorsOnly(last, detectors)) {
00250                     // ... and it's not an in-between-detector
00251                     // -> let's add this edge and the following, but not any further
00252                     addNextNoFurther = true;
00253                     current.lastDetectorEdge = last;
00254                     current.duration2Last = (SUMOTime) current.duration_2;
00255                     current.distance2Last = current.distance;
00256                     current.endDetectorEdge = last;
00257                     if (hasSourceDetector(last, detectors)) {
00259                     }
00260                     current.factor = 1.;
00261                     SUMOReal cdist = current.edges2Pass[0]->getFromNode()->getPosition().distanceTo(current.edges2Pass.back()->getToNode()->getPosition());
00262                     if (minDist < cdist) {
00263                         into.addRouteDesc(current);
00264                     }
00265                     continue;
00266                 } else {
00267                     // ... if it's an in-between-detector
00268                     // -> mark the current route as to be continued
00269                     current.passedNo = 0;
00270                     current.duration2Last = (SUMOTime) current.duration_2;
00271                     current.distance2Last = current.distance;
00272                     current.lastDetectorEdge = last;
00273                 }
00274             }
00275         }
00276         // check for highway off-ramps
00277         if (myAmInHighwayMode) {
00278             // if it's beside the highway...
00279             if (last->getSpeed() < 19.4 && last != getDetectorEdge(det)) {
00280                 // ... and has more than one following edge
00281                 if (myApproachedEdges.find(last)->second.size() > 1) {
00282                     // -> let's add this edge and the following, but not any further
00283                     addNextNoFurther = true;
00284                 }
00285 
00286             }
00287         }
00288         // check for missing end connections
00289         if (!addNextNoFurther) {
00290             // ... if this one would be processed, but already too many edge
00291             //  without a detector occured
00292             if (current.passedNo > maxFollowingLength) {
00293                 // mark not to process any further
00294                 WRITE_WARNING("Could not close route for '" + det.getID() + "'");
00295                 unfoundEnds.push_back(current);
00296                 current.factor = 1.;
00297                 SUMOReal cdist = current.edges2Pass[0]->getFromNode()->getPosition().distanceTo(current.edges2Pass.back()->getToNode()->getPosition());
00298                 if (minDist < cdist) {
00299                     into.addRouteDesc(current);
00300                 }
00301                 continue;
00302             }
00303         }
00304         // ... else: loop over the next edges
00305         const std::vector<ROEdge*> &appr  = myApproachedEdges.find(last)->second;
00306         bool hadOne = false;
00307         for (size_t i = 0; i < appr.size(); i++) {
00308             if (find(current.edges2Pass.begin(), current.edges2Pass.end(), appr[i]) != current.edges2Pass.end()) {
00309                 // do not append an edge twice (do not build loops)
00310                 continue;
00311             }
00312             RODFRouteDesc t(current);
00313             t.duration_2 += (appr[i]->getLength() / appr[i]->getSpeed()); 
00314             t.distance += appr[i]->getLength();
00315             t.edges2Pass.push_back(appr[i]);
00316             if (!addNextNoFurther) {
00317                 t.passedNo = t.passedNo + 1;
00318                 toSolve.push(t);
00319             } else {
00320                 if (!hadOne) {
00321                     t.factor = (SUMOReal) 1. / (SUMOReal) appr.size();
00322                     SUMOReal cdist = current.edges2Pass[0]->getFromNode()->getPosition().distanceTo(current.edges2Pass.back()->getToNode()->getPosition());
00323                     if (minDist < cdist) {
00324                         into.addRouteDesc(t);
00325                     }
00326                     hadOne = true;
00327                 }
00328             }
00329         }
00330     }
00331     //
00332     if (!keepUnfoundEnds) {
00333         std::vector<RODFRouteDesc>::iterator i;
00334         std::vector<const ROEdge*> lastDetEdges;
00335         for (i = unfoundEnds.begin(); i != unfoundEnds.end(); ++i) {
00336             if (find(lastDetEdges.begin(), lastDetEdges.end(), (*i).lastDetectorEdge) == lastDetEdges.end()) {
00337                 lastDetEdges.push_back((*i).lastDetectorEdge);
00338             } else {
00339                 bool ok = into.removeRouteDesc(*i);
00340                 assert(ok);
00341             }
00342         }
00343     } else {
00344         // !!! patch the factors
00345     }
00346     while (!toSolve.empty()) {
00347 //        RODFRouteDesc d = toSolve.top();
00348         toSolve.pop();
00349 //        delete d;
00350     }
00351 }
00352 
00353 
00354 void
00355 RODFNet::buildRoutes(RODFDetectorCon& detcont, bool allEndFollower,
00356                      bool keepUnfoundEnds, bool includeInBetween,
00357                      bool keepShortestOnly, int maxFollowingLength) const {
00358     // build needed information first
00359     buildDetectorEdgeDependencies(detcont);
00360     // then build the routes
00361     std::map<ROEdge*, RODFRouteCont* > doneEdges;
00362     const std::vector< RODFDetector*> &dets = detcont.getDetectors();
00363     for (std::vector< RODFDetector*>::const_iterator i = dets.begin(); i != dets.end(); ++i) {
00364         if ((*i)->getType() != SOURCE_DETECTOR) {
00365             // do not build routes for other than sources
00366             //continue;
00367         }
00368         ROEdge* e = getDetectorEdge(**i);
00369         if (doneEdges.find(e) != doneEdges.end()) {
00370             // use previously build routes
00371             (*i)->addRoutes(new RODFRouteCont(*doneEdges[e]));
00372             continue;
00373         }
00374         std::vector<ROEdge*> seen;
00375         RODFRouteCont* routes = new RODFRouteCont();
00376         doneEdges[e] = routes;
00377         RODFRouteDesc rd;
00378         rd.edges2Pass.push_back(e);
00379         rd.duration_2 = (e->getLength() / e->getSpeed()); 
00380         rd.endDetectorEdge = 0;
00381         rd.lastDetectorEdge = 0;
00382         rd.distance = e->getLength();
00383         rd.distance2Last = 0;
00384         rd.duration2Last = 0;
00385 
00386         rd.overallProb = 0;
00387 
00388         std::vector<ROEdge*> visited;
00389         visited.push_back(e);
00390         computeRoutesFor(e, rd, 0, keepUnfoundEnds, keepShortestOnly,
00391                          visited, **i, *routes, detcont, maxFollowingLength, seen);
00392         if (allEndFollower) {
00393             routes->addAllEndFollower();
00394         }
00396         (*i)->addRoutes(routes);
00397 
00398         // add routes to in-between detectors if wished
00399         if (includeInBetween) {
00400             // go through the routes
00401             const std::vector<RODFRouteDesc> &r = routes->get();
00402             for (std::vector<RODFRouteDesc>::const_iterator j = r.begin(); j != r.end(); ++j) {
00403                 const RODFRouteDesc& mrd = *j;
00404                 SUMOReal duration = mrd.duration_2;
00405                 SUMOReal distance = mrd.distance;
00406                 // go through each route's edges
00407                 std::vector<ROEdge*>::const_iterator routeend = mrd.edges2Pass.end();
00408                 for (std::vector<ROEdge*>::const_iterator k = mrd.edges2Pass.begin(); k != routeend; ++k) {
00409                     // check whether any detectors lies on the current edge
00410                     if (myDetectorsOnEdges.find(*k) == myDetectorsOnEdges.end()) {
00411                         duration -= (*k)->getLength() / (*k)->getSpeed();
00412                         distance -= (*k)->getLength();
00413                         continue;
00414                     }
00415                     // get the detectors
00416                     const std::vector<std::string> &dets = myDetectorsOnEdges.find(*k)->second;
00417                     // go through the detectors
00418                     for (std::vector<std::string>::const_iterator l = dets.begin(); l != dets.end(); ++l) {
00419                         const RODFDetector& m = detcont.getDetector(*l);
00420                         if (m.getType() == BETWEEN_DETECTOR) {
00421                             RODFRouteDesc nrd;
00422                             copy(k, routeend, back_inserter(nrd.edges2Pass));
00423                             nrd.duration_2 = duration;
00424                             nrd.endDetectorEdge = mrd.endDetectorEdge;
00425                             nrd.lastDetectorEdge = mrd.lastDetectorEdge;
00426                             nrd.distance = distance;
00427                             nrd.distance2Last = mrd.distance2Last;
00428                             nrd.duration2Last = mrd.duration2Last;
00429                             nrd.overallProb = mrd.overallProb;
00430                             nrd.factor = mrd.factor;
00431                             ((RODFDetector&) m).addRoute(nrd);
00432                         }
00433                     }
00434                     duration -= (*k)->getLength() / (*k)->getSpeed();
00435                     distance -= (*k)->getLength();
00436                 }
00437             }
00438         }
00439 
00440     }
00441 }
00442 
00443 
00444 void
00445 RODFNet::revalidateFlows(const RODFDetector* detector,
00446                          RODFDetectorFlows& flows,
00447                          SUMOTime startTime, SUMOTime endTime,
00448                          SUMOTime stepOffset) {
00449     {
00450         if (flows.knows(detector->getID())) {
00451             const std::vector<FlowDef> &detFlows = flows.getFlowDefs(detector->getID());
00452             for (std::vector<FlowDef>::const_iterator j = detFlows.begin(); j != detFlows.end(); ++j) {
00453                 if ((*j).qPKW > 0 || (*j).qLKW > 0) {
00454                     return;
00455                 }
00456             }
00457         }
00458     }
00459     // ok, there is no information for the whole time;
00460     //  lets find preceding detectors and rebuild the flows if possible
00461     WRITE_WARNING("Detector '" + detector->getID() + "' has no flows.\n Trying to rebuild.");
00462     // go back and collect flows
00463     std::vector<ROEdge*> previous;
00464     {
00465         std::vector<IterationEdge> missing;
00466         IterationEdge ie;
00467         ie.depth = 0;
00468         ie.edge = getDetectorEdge(*detector);
00469         missing.push_back(ie);
00470         bool maxDepthReached = false;
00471         while (!missing.empty() && !maxDepthReached) {
00472             IterationEdge last = missing.back();
00473             missing.pop_back();
00474             std::vector<ROEdge*> approaching = myApproachingEdges[last.edge];
00475             for (std::vector<ROEdge*>::const_iterator j = approaching.begin(); j != approaching.end(); ++j) {
00476                 if (hasDetector(*j)) {
00477                     previous.push_back(*j);
00478                 } else {
00479                     ie.depth = last.depth + 1;
00480                     ie.edge = *j;
00481                     missing.push_back(ie);
00482                     if (ie.depth > 5) {
00483                         maxDepthReached = true;
00484                     }
00485                 }
00486             }
00487         }
00488         if (maxDepthReached) {
00489             WRITE_WARNING(" Could not build list of previous flows.");
00490         }
00491     }
00492     // Edges with previous detectors are now in "previous";
00493     //  compute following
00494     std::vector<ROEdge*> latter;
00495     {
00496         std::vector<IterationEdge> missing;
00497         for (std::vector<ROEdge*>::const_iterator k = previous.begin(); k != previous.end(); ++k) {
00498             IterationEdge ie;
00499             ie.depth = 0;
00500             ie.edge = *k;
00501             missing.push_back(ie);
00502         }
00503         bool maxDepthReached = false;
00504         while (!missing.empty() && !maxDepthReached) {
00505             IterationEdge last = missing.back();
00506             missing.pop_back();
00507             std::vector<ROEdge*> approached = myApproachedEdges[last.edge];
00508             for (std::vector<ROEdge*>::const_iterator j = approached.begin(); j != approached.end(); ++j) {
00509                 if (*j == getDetectorEdge(*detector)) {
00510                     continue;
00511                 }
00512                 if (hasDetector(*j)) {
00513                     latter.push_back(*j);
00514                 } else {
00515                     IterationEdge ie;
00516                     ie.depth = last.depth + 1;
00517                     ie.edge = *j;
00518                     missing.push_back(ie);
00519                     if (ie.depth > 5) {
00520                         maxDepthReached = true;
00521                     }
00522                 }
00523             }
00524         }
00525         if (maxDepthReached) {
00526             WRITE_WARNING(" Could not build list of latter flows.");
00527             return;
00528         }
00529     }
00530     // Edges with latter detectors are now in "latter";
00531 
00532     // lets not validate them by now - surely this should be done
00533     // for each time step: collect incoming flows; collect outgoing;
00534     std::vector<FlowDef> mflows;
00535     int index = 0;
00536     for (SUMOTime t = startTime; t < endTime; t += stepOffset, index++) {
00537         FlowDef inFlow;
00538         inFlow.qLKW = 0;
00539         inFlow.qPKW = 0;
00540         inFlow.vLKW = 0;
00541         inFlow.vPKW = 0;
00542         // collect incoming
00543         {
00544             // !! time difference is missing
00545             for (std::vector<ROEdge*>::iterator i = previous.begin(); i != previous.end(); ++i) {
00546                 const std::vector<FlowDef> &flows = static_cast<const RODFEdge*>(*i)->getFlows();
00547                 if (flows.size() != 0) {
00548                     const FlowDef& srcFD = flows[index];
00549                     inFlow.qLKW += srcFD.qLKW;
00550                     inFlow.qPKW += srcFD.qPKW;
00551                     inFlow.vLKW += srcFD.vLKW;
00552                     inFlow.vPKW += srcFD.vPKW;
00553                 }
00554             }
00555         }
00556         inFlow.vLKW /= (SUMOReal) previous.size();
00557         inFlow.vPKW /= (SUMOReal) previous.size();
00558         // collect outgoing
00559         FlowDef outFlow;
00560         outFlow.qLKW = 0;
00561         outFlow.qPKW = 0;
00562         outFlow.vLKW = 0;
00563         outFlow.vPKW = 0;
00564         {
00565             // !! time difference is missing
00566             for (std::vector<ROEdge*>::iterator i = latter.begin(); i != latter.end(); ++i) {
00567                 const std::vector<FlowDef> &flows = static_cast<const RODFEdge*>(*i)->getFlows();
00568                 if (flows.size() != 0) {
00569                     const FlowDef& srcFD = flows[index];
00570                     outFlow.qLKW += srcFD.qLKW;
00571                     outFlow.qPKW += srcFD.qPKW;
00572                     outFlow.vLKW += srcFD.vLKW;
00573                     outFlow.vPKW += srcFD.vPKW;
00574                 }
00575             }
00576         }
00577         outFlow.vLKW /= (SUMOReal) latter.size();
00578         outFlow.vPKW /= (SUMOReal) latter.size();
00579         //
00580         FlowDef mFlow;
00581         mFlow.qLKW = inFlow.qLKW - outFlow.qLKW;
00582         mFlow.qPKW = inFlow.qPKW - outFlow.qPKW;
00583         mFlow.vLKW = (inFlow.vLKW + outFlow.vLKW) / (SUMOReal) 2.;
00584         mFlow.vPKW = (inFlow.vPKW + outFlow.vPKW) / (SUMOReal) 2.;
00585         mflows.push_back(mFlow);
00586     }
00587     static_cast<RODFEdge*>(getDetectorEdge(*detector))->setFlows(mflows);
00588     flows.setFlows(detector->getID(), mflows);
00589 }
00590 
00591 
00592 void
00593 RODFNet::revalidateFlows(const RODFDetectorCon& detectors,
00594                          RODFDetectorFlows& flows,
00595                          SUMOTime startTime, SUMOTime endTime,
00596                          SUMOTime stepOffset) {
00597     const std::vector<RODFDetector*> &dets = detectors.getDetectors();
00598     for (std::vector<RODFDetector*>::const_iterator i = dets.begin(); i != dets.end(); ++i) {
00599         // check whether there is at least one entry with a flow larger than zero
00600         revalidateFlows(*i, flows, startTime, endTime, stepOffset);
00601     }
00602 }
00603 
00604 
00605 
00606 void
00607 RODFNet::removeEmptyDetectors(RODFDetectorCon& detectors,
00608                               RODFDetectorFlows& flows) {
00609     const std::vector<RODFDetector*> &dets = detectors.getDetectors();
00610     for (std::vector<RODFDetector*>::const_iterator i = dets.begin(); i != dets.end();) {
00611         bool remove = true;
00612         // check whether there is at least one entry with a flow larger than zero
00613         if (flows.knows((*i)->getID())) {
00614             remove = false;
00615         }
00616         if (remove) {
00617             WRITE_MESSAGE("Removed detector '" + (*i)->getID() + "' because no flows for him exist.");
00618             flows.removeFlow((*i)->getID());
00619             detectors.removeDetector((*i)->getID());
00620             i = dets.begin();
00621         } else {
00622             i++;
00623         }
00624     }
00625 }
00626 
00627 
00628 
00629 void
00630 RODFNet::reportEmptyDetectors(RODFDetectorCon& detectors,
00631                               RODFDetectorFlows& flows) {
00632     const std::vector<RODFDetector*> &dets = detectors.getDetectors();
00633     for (std::vector<RODFDetector*>::const_iterator i = dets.begin(); i != dets.end(); ++i) {
00634         bool remove = true;
00635         // check whether there is at least one entry with a flow larger than zero
00636         if (flows.knows((*i)->getID())) {
00637             remove = false;
00638         }
00639         if (remove) {
00640             WRITE_MESSAGE("Detector '" + (*i)->getID() + "' has no flow.");
00641         }
00642     }
00643 }
00644 
00645 
00646 
00647 ROEdge*
00648 RODFNet::getDetectorEdge(const RODFDetector& det) const {
00649     std::string edgeName = det.getLaneID();
00650     edgeName = edgeName.substr(0, edgeName.rfind('_'));
00651     ROEdge* ret = getEdge(edgeName);
00652     if (ret == 0) {
00653         throw ProcessError("Edge '" + edgeName + "' used by detector '" + det.getID() + "' is not known.");
00654     }
00655     return ret;
00656 }
00657 
00658 
00659 bool
00660 RODFNet::hasApproaching(ROEdge* edge) const {
00661     return
00662         myApproachingEdges.find(edge) != myApproachingEdges.end()
00663         &&
00664         myApproachingEdges.find(edge)->second.size() != 0;
00665 }
00666 
00667 
00668 bool
00669 RODFNet::hasApproached(ROEdge* edge) const {
00670     return
00671         myApproachedEdges.find(edge) != myApproachedEdges.end()
00672         &&
00673         myApproachedEdges.find(edge)->second.size() != 0;
00674 }
00675 
00676 
00677 bool
00678 RODFNet::hasDetector(ROEdge* edge) const {
00679     return
00680         myDetectorsOnEdges.find(edge) != myDetectorsOnEdges.end()
00681         &&
00682         myDetectorsOnEdges.find(edge)->second.size() != 0;
00683 }
00684 
00685 
00686 const std::vector<std::string> &
00687 RODFNet::getDetectorList(ROEdge* edge) const {
00688     return myDetectorsOnEdges.find(edge)->second;
00689 }
00690 
00691 
00692 SUMOReal
00693 RODFNet::getAbsPos(const RODFDetector& det) const {
00694     if (det.getPos() >= 0) {
00695         return det.getPos();
00696     }
00697     return getDetectorEdge(det)->getLength() + det.getPos();
00698 }
00699 
00700 bool
00701 RODFNet::isSource(const RODFDetector& det, const RODFDetectorCon& detectors,
00702                   bool strict) const {
00703     std::vector<ROEdge*> seen;
00704     return
00705         isSource(det, getDetectorEdge(det), seen, detectors, strict);
00706 }
00707 
00708 bool
00709 RODFNet::isFalseSource(const RODFDetector& det, const RODFDetectorCon& detectors) const {
00710     std::vector<ROEdge*> seen;
00711     return
00712         isFalseSource(det, getDetectorEdge(det), seen, detectors);
00713 }
00714 
00715 bool
00716 RODFNet::isDestination(const RODFDetector& det, const RODFDetectorCon& detectors) const {
00717     std::vector<ROEdge*> seen;
00718     return isDestination(det, getDetectorEdge(det), seen, detectors);
00719 }
00720 
00721 
00722 bool
00723 RODFNet::isSource(const RODFDetector& det, ROEdge* edge,
00724                   std::vector<ROEdge*> &seen,
00725                   const RODFDetectorCon& detectors,
00726                   bool strict) const {
00727     if (seen.size() == 1000) { // !!!
00728         WRITE_WARNING("Quitting checking for being a source for detector '" + det.getID() + "' due to seen edge limit.");
00729         return false;
00730     }
00731     if (edge == getDetectorEdge(det)) {
00732         // maybe there is another detector at the same edge
00733         //  get the list of this/these detector(s)
00734         const std::vector<std::string> &detsOnEdge = myDetectorsOnEdges.find(edge)->second;
00735         for (std::vector<std::string>::const_iterator i = detsOnEdge.begin(); i != detsOnEdge.end(); ++i) {
00736             if ((*i) == det.getID()) {
00737                 continue;
00738             }
00739             const RODFDetector& sec = detectors.getDetector(*i);
00740             if (getAbsPos(sec) < getAbsPos(det)) {
00741                 // ok, there is another detector on the same edge and it is
00742                 //  before this one -> no source
00743                 return false;
00744             }
00745         }
00746     }
00747     // it's a source if no edges are approaching the edge
00748     if (!hasApproaching(edge)) {
00749         if (edge != getDetectorEdge(det)) {
00750             if (hasDetector(edge)) {
00751                 return false;
00752             }
00753         }
00754         return true;
00755     }
00756     if (edge != getDetectorEdge(det)) {
00757         // ok, we are at one of the edges in front
00758         if (myAmInHighwayMode) {
00759             if (edge->getSpeed() >= 19.4) {
00760                 if (hasDetector(edge)) {
00761                     // we are still on the highway and there is another detector
00762                     return false;
00763                 }
00764                 // the next is a hack for the A100 scenario...
00765                 //  We have to look into further edges herein edges
00766                 const std::vector<ROEdge*> &appr = myApproachingEdges.find(edge)->second;
00767                 size_t noOk = 0;
00768                 size_t noFalse = 0;
00769                 size_t noSkipped = 0;
00770                 for (size_t i = 0; i < appr.size(); i++) {
00771                     if (!hasDetector(appr[i])) {
00772                         noOk++;
00773                     } else {
00774                         noFalse++;
00775                     }
00776                 }
00777                 if ((noFalse + noSkipped) == appr.size()) {
00778                     return false;
00779                 }
00780             }
00781         }
00782     }
00783 
00784     if (myAmInHighwayMode) {
00785         if (edge->getSpeed() < 19.4 && edge != getDetectorEdge(det)) {
00786             // we have left the highway already
00787             //  -> the detector will be a highway source
00788             if (!hasDetector(edge)) {
00789                 return true;
00790             }
00791         }
00792     }
00793     if (myDetectorsOnEdges.find(edge) != myDetectorsOnEdges.end()
00794             &&
00795             myDetectorEdges.find(det.getID())->second != edge) {
00796         return false;
00797     }
00798 
00799     // let's check the edges in front
00800     const std::vector<ROEdge*> &appr = myApproachingEdges.find(edge)->second;
00801     size_t noOk = 0;
00802     size_t noFalse = 0;
00803     size_t noSkipped = 0;
00804     seen.push_back(edge);
00805     for (size_t i = 0; i < appr.size(); i++) {
00806         bool had = std::find(seen.begin(), seen.end(), appr[i]) != seen.end();
00807         if (!had) {
00808             if (isSource(det, appr[i], seen, detectors, strict)) {
00809                 noOk++;
00810             } else {
00811                 noFalse++;
00812             }
00813         } else {
00814             noSkipped++;
00815         }
00816     }
00817     if (!strict) {
00818         return (noFalse + noSkipped) != appr.size();
00819     } else {
00820         return (noOk + noSkipped) == appr.size();
00821     }
00822 }
00823 
00824 
00825 bool
00826 RODFNet::isDestination(const RODFDetector& det, ROEdge* edge, std::vector<ROEdge*> &seen,
00827                        const RODFDetectorCon& detectors) const {
00828     if (seen.size() == 1000) { // !!!
00829         WRITE_WARNING("Quitting checking for being a destination for detector '" + det.getID() + "' due to seen edge limit.");
00830         return false;
00831     }
00832     if (edge == getDetectorEdge(det)) {
00833         // maybe there is another detector at the same edge
00834         //  get the list of this/these detector(s)
00835         const std::vector<std::string> &detsOnEdge = myDetectorsOnEdges.find(edge)->second;
00836         for (std::vector<std::string>::const_iterator i = detsOnEdge.begin(); i != detsOnEdge.end(); ++i) {
00837             if ((*i) == det.getID()) {
00838                 continue;
00839             }
00840             const RODFDetector& sec = detectors.getDetector(*i);
00841             if (getAbsPos(sec) > getAbsPos(det)) {
00842                 // ok, there is another detector on the same edge and it is
00843                 //  after this one -> no destination
00844                 return false;
00845             }
00846         }
00847     }
00848     if (!hasApproached(edge)) {
00849         if (edge != getDetectorEdge(det)) {
00850             if (hasDetector(edge)) {
00851                 return false;
00852             }
00853         }
00854         return true;
00855     }
00856     if (edge != getDetectorEdge(det)) {
00857         // ok, we are at one of the edges coming behind
00858         if (myAmInHighwayMode) {
00859             if (edge->getSpeed() >= 19.4) {
00860                 if (hasDetector(edge)) {
00861                     // we are still on the highway and there is another detector
00862                     return false;
00863                 }
00864             }
00865         }
00866     }
00867 
00868     if (myAmInHighwayMode) {
00869         if (edge->getSpeed() < 19.4 && edge != getDetectorEdge(det)) {
00870             if (hasDetector(edge)) {
00871                 return true;
00872             }
00873             if (myApproachedEdges.find(edge)->second.size() > 1) {
00874                 return true;
00875             }
00876 
00877         }
00878     }
00879 
00880     if (myDetectorsOnEdges.find(edge) != myDetectorsOnEdges.end()
00881             &&
00882             myDetectorEdges.find(det.getID())->second != edge) {
00883         return false;
00884     }
00885     const std::vector<ROEdge*> &appr  = myApproachedEdges.find(edge)->second;
00886     bool isall = true;
00887     size_t no = 0;
00888     seen.push_back(edge);
00889     for (size_t i = 0; i < appr.size() && isall; i++) {
00890         bool had = std::find(seen.begin(), seen.end(), appr[i]) != seen.end();
00891         if (!had) {
00892             if (!isDestination(det, appr[i], seen, detectors)) {
00893                 no++;
00894                 isall = false;
00895             }
00896         }
00897     }
00898     return isall;
00899 }
00900 
00901 bool
00902 RODFNet::isFalseSource(const RODFDetector& det, ROEdge* edge, std::vector<ROEdge*> &seen,
00903                        const RODFDetectorCon& detectors) const {
00904     if (seen.size() == 1000) { // !!!
00905         WRITE_WARNING("Quitting checking for being a false source for detector '" + det.getID() + "' due to seen edge limit.");
00906         return false;
00907     }
00908     seen.push_back(edge);
00909     if (edge != getDetectorEdge(det)) {
00910         // ok, we are at one of the edges coming behind
00911         if (hasDetector(edge)) {
00912             const std::vector<std::string> &dets = myDetectorsOnEdges.find(edge)->second;
00913             for (std::vector<std::string>::const_iterator i = dets.begin(); i != dets.end(); ++i) {
00914                 if (detectors.getDetector(*i).getType() == SINK_DETECTOR) {
00915                     return false;
00916                 }
00917                 if (detectors.getDetector(*i).getType() == BETWEEN_DETECTOR) {
00918                     return false;
00919                 }
00920                 if (detectors.getDetector(*i).getType() == SOURCE_DETECTOR) {
00921                     return true;
00922                 }
00923             }
00924         } else {
00925             if (myAmInHighwayMode && edge->getSpeed() < 19.) {
00926                 return false;
00927             }
00928         }
00929     }
00930 
00931     if (myApproachedEdges.find(edge) == myApproachedEdges.end()) {
00932         return false;
00933     }
00934 
00935     const std::vector<ROEdge*> &appr  = myApproachedEdges.find(edge)->second;
00936     bool isall = false;
00937     for (size_t i = 0; i < appr.size() && !isall; i++) {
00938         //printf("checking %s->\n", appr[i].c_str());
00939         bool had = std::find(seen.begin(), seen.end(), appr[i]) != seen.end();
00940         if (!had) {
00941             if (isFalseSource(det, appr[i], seen, detectors)) {
00942                 isall = true;
00943             }
00944         }
00945     }
00946     return isall;
00947 }
00948 
00949 
00950 void
00951 RODFNet::buildEdgeFlowMap(const RODFDetectorFlows& flows,
00952                           const RODFDetectorCon& detectors,
00953                           SUMOTime startTime, SUMOTime endTime,
00954                           SUMOTime stepOffset) {
00955     std::map<ROEdge*, std::vector<std::string> >::iterator i;
00956     for (i = myDetectorsOnEdges.begin(); i != myDetectorsOnEdges.end(); ++i) {
00957         ROEdge* into = (*i).first;
00958         const std::vector<std::string> &dets = (*i).second;
00959         std::map<SUMOReal, std::vector<std::string> > cliques;
00960         size_t maxCliqueSize = 0;
00961         for (std::vector<std::string>::const_iterator j = dets.begin(); j != dets.end(); ++j) {
00962             if (!flows.knows(*j)) {
00963                 continue;
00964             }
00965             const RODFDetector& det = detectors.getDetector(*j);
00966             bool found = false;
00967             for (std::map<SUMOReal, std::vector<std::string> >::iterator k = cliques.begin(); !found && k != cliques.end(); ++k) {
00968                 if (fabs((*k).first - det.getPos()) < 1) {
00969                     (*k).second.push_back(*j);
00970                     maxCliqueSize = MAX2(maxCliqueSize, (*k).second.size());
00971                     found = true;
00972                 }
00973             }
00974             if (!found) {
00975                 cliques[det.getPos()] = std::vector<std::string>();
00976                 cliques[det.getPos()].push_back(*j);
00977                 maxCliqueSize = MAX2(maxCliqueSize, (size_t) 1);
00978             }
00979         }
00980         std::vector<std::string> firstClique;
00981         for (std::map<SUMOReal, std::vector<std::string> >::iterator m = cliques.begin(); firstClique.size() == 0 && m != cliques.end(); ++m) {
00982             if ((*m).second.size() == maxCliqueSize) {
00983                 firstClique = (*m).second;
00984             }
00985         }
00986         std::vector<FlowDef> mflows; // !!! reserve
00987         for (SUMOTime t = startTime; t < endTime; t += stepOffset) {
00988             FlowDef fd;
00989             fd.qPKW = 0;
00990             fd.qLKW = 0;
00991             fd.vLKW = 0;
00992             fd.vPKW = 0;
00993             fd.fLKW = 0;
00994             fd.isLKW = 0;
00995             mflows.push_back(fd);
00996         }
00997         for (std::vector<std::string>::iterator l = firstClique.begin(); l != firstClique.end(); ++l) {
00998             bool didWarn = false;
00999             const std::vector<FlowDef> &dflows = flows.getFlowDefs(*l);
01000             int index = 0;
01001             for (SUMOTime t = startTime; t < endTime; t += stepOffset, index++) {
01002                 const FlowDef& srcFD = dflows[index];
01003                 FlowDef& fd = mflows[index];
01004                 fd.qPKW += srcFD.qPKW;
01005                 fd.qLKW += srcFD.qLKW;
01006                 fd.vLKW += (srcFD.vLKW / (SUMOReal) firstClique.size());
01007                 fd.vPKW += (srcFD.vPKW / (SUMOReal) firstClique.size());
01008                 fd.fLKW += (srcFD.fLKW / (SUMOReal) firstClique.size());
01009                 fd.isLKW += (srcFD.isLKW / (SUMOReal) firstClique.size());
01010                 if (!didWarn && srcFD.vPKW > 0 && srcFD.vPKW < 255 && srcFD.vPKW / 3.6 > into->getSpeed()) {
01011                     WRITE_MESSAGE("Detected PKW speed higher than allowed speed at '" + (*l) + "' on '" + into->getID() + "'.");
01012                     didWarn = true;
01013                 }
01014                 if (!didWarn && srcFD.vLKW > 0 && srcFD.vLKW < 255 && srcFD.vLKW / 3.6 > into->getSpeed()) {
01015                     WRITE_MESSAGE("Detected LKW speed higher than allowed speed at '" + (*l) + "' on '" + into->getID() + "'.");
01016                     didWarn = true;
01017                 }
01018             }
01019         }
01020         static_cast<RODFEdge*>(into)->setFlows(mflows);
01021     }
01022 }
01023 
01024 
01025 void
01026 RODFNet::buildDetectorDependencies(RODFDetectorCon& detectors) {
01027     // !!! this will not work when several detectors are lying on the same edge on different positions
01028 
01029 
01030     buildDetectorEdgeDependencies(detectors);
01031     // for each detector, compute the lists of predecessor and following detectors
01032     std::map<std::string, ROEdge*>::const_iterator i;
01033     for (i = myDetectorEdges.begin(); i != myDetectorEdges.end(); ++i) {
01034         const RODFDetector& det = detectors.getDetector((*i).first);
01035         if (!det.hasRoutes()) {
01036             continue;
01037         }
01038         // mark current detectors
01039         std::vector<RODFDetector*> last;
01040         {
01041             const std::vector<std::string> &detNames = myDetectorsOnEdges.find((*i).second)->second;
01042             for (std::vector<std::string>::const_iterator j = detNames.begin(); j != detNames.end(); ++j) {
01043                 last.push_back((RODFDetector*) &detectors.getDetector(*j));
01044             }
01045         }
01046         // iterate over the current detector's routes
01047         const std::vector<RODFRouteDesc> &routes = det.getRouteVector();
01048         for (std::vector<RODFRouteDesc>::const_iterator j = routes.begin(); j != routes.end(); ++j) {
01049             const std::vector<ROEdge*> &edges2Pass = (*j).edges2Pass;
01050             for (std::vector<ROEdge*>::const_iterator k = edges2Pass.begin() + 1; k != edges2Pass.end(); ++k) {
01051                 if (myDetectorsOnEdges.find(*k) != myDetectorsOnEdges.end()) {
01052                     const std::vector<std::string> &detNames = myDetectorsOnEdges.find(*k)->second;
01053                     // ok, consecutive detector found
01054                     for (std::vector<RODFDetector*>::iterator l = last.begin(); l != last.end(); ++l) {
01055                         // mark as follower of current
01056                         for (std::vector<std::string>::const_iterator m = detNames.begin(); m != detNames.end(); ++m) {
01057                             ((RODFDetector*) &detectors.getDetector(*m))->addPriorDetector((RODFDetector*) & (*l));
01058                             (*l)->addFollowingDetector((RODFDetector*) &detectors.getDetector(*m));
01059                         }
01060                     }
01061                     last.clear();
01062                     for (std::vector<std::string>::const_iterator m = detNames.begin(); m != detNames.end(); ++m) {
01063                         last.push_back((RODFDetector*) &detectors.getDetector(*m));
01064                     }
01065                 }
01066             }
01067         }
01068     }
01069 }
01070 
01071 
01072 void
01073 RODFNet::mesoJoin(RODFDetectorCon& detectors, RODFDetectorFlows& flows) {
01074     buildDetectorEdgeDependencies(detectors);
01075     std::map<ROEdge*, std::vector<std::string> >::iterator i;
01076     for (i = myDetectorsOnEdges.begin(); i != myDetectorsOnEdges.end(); ++i) {
01077         ROEdge* into = (*i).first;
01078         const std::vector<std::string> &dets = (*i).second;
01079         std::map<SUMOReal, std::vector<std::string> > cliques;
01080         // compute detector cliques
01081         for (std::vector<std::string>::const_iterator j = dets.begin(); j != dets.end(); ++j) {
01082             const RODFDetector& det = detectors.getDetector(*j);
01083             bool found = false;
01084             for (std::map<SUMOReal, std::vector<std::string> >::iterator k = cliques.begin(); !found && k != cliques.end(); ++k) {
01085                 if (fabs((*k).first - det.getPos()) < 10.) {
01086                     (*k).second.push_back(*j);
01087                     found = true;
01088                 }
01089             }
01090             if (!found) {
01091                 cliques[det.getPos()] = std::vector<std::string>();
01092                 cliques[det.getPos()].push_back(*j);
01093             }
01094         }
01095         // join detector cliques
01096         for (std::map<SUMOReal, std::vector<std::string> >::iterator m = cliques.begin(); m != cliques.end(); ++m) {
01097             std::vector<std::string> clique = (*m).second;
01098             // do not join if only one
01099             if (clique.size() == 1) {
01100                 continue;
01101             }
01102             std::string nid;
01103             for (std::vector<std::string>::iterator n = clique.begin(); n != clique.end(); ++n) {
01104                 std::cout << *n << " ";
01105                 if (n != clique.begin()) {
01106                     nid = nid + "_";
01107                 }
01108                 nid = nid + *n;
01109             }
01110             std::cout << ":" << nid << std::endl;
01111             flows.mesoJoin(nid, (*m).second);
01112             detectors.mesoJoin(nid, (*m).second);
01113         }
01114     }
01115 }
01116 
01117 
01118 
01119 /****************************************************************************/
01120 
 All Data Structures Files Functions Variables Typedefs Enumerations Enumerator Friends Defines