SUMO - Simulation of Urban MObility
MSAgentbasedTrafficLightLogic.cpp
Go to the documentation of this file.
00001 /****************************************************************************/
00011 // An agentbased traffic light logic
00012 /****************************************************************************/
00013 // SUMO, Simulation of Urban MObility; see http://sumo.sourceforge.net/
00014 // Copyright (C) 2001-2012 DLR (http://www.dlr.de/) and contributors
00015 /****************************************************************************/
00016 //
00017 //   This file is part of SUMO.
00018 //   SUMO is free software: you can redistribute it and/or modify
00019 //   it under the terms of the GNU General Public License as published by
00020 //   the Free Software Foundation, either version 3 of the License, or
00021 //   (at your option) any later version.
00022 //
00023 /****************************************************************************/
00024 
00025 
00026 // ===========================================================================
00027 // included modules
00028 // ===========================================================================
00029 #ifdef _MSC_VER
00030 #include <windows_config.h>
00031 #else
00032 #include <config.h>
00033 #endif
00034 
00035 #include <utility>
00036 #include <vector>
00037 #include <bitset>
00038 #include <netload/NLDetectorBuilder.h>
00039 #include <utils/common/TplConvert.h>
00040 #include "MSTrafficLightLogic.h"
00041 #include "MSAgentbasedTrafficLightLogic.h"
00042 #include <microsim/MSLane.h>
00043 #include <microsim/MSEdge.h>
00044 
00045 #ifdef CHECK_MEMORY_LEAKS
00046 #include <foreign/nvwa/debug_new.h>
00047 #endif // CHECK_MEMORY_LEAKS
00048 
00049 
00050 // ===========================================================================
00051 // member method definitions
00052 // ===========================================================================
00053 MSAgentbasedTrafficLightLogic::MSAgentbasedTrafficLightLogic(
00054     MSTLLogicControl& tlcontrol,
00055     const std::string& id, const std::string& programID,
00056     const Phases& phases, unsigned int step, SUMOTime delay,
00057     const std::map<std::string, std::string> &parameter)
00058     : MSSimpleTrafficLightLogic(tlcontrol, id, programID, phases, step, delay),
00059       tSinceLastDecision(0), stepOfLastDecision(0) {
00060 
00061     tDecide = 1;
00062     if (parameter.find("decision-horizon") != parameter.end()) {
00063         tDecide = (unsigned int) TplConvert<char>::_2int(parameter.find("decision-horizon")->second.c_str());
00064     }
00065     numberOfValues = 3;
00066     if (parameter.find("learn-horizon") != parameter.end()) {
00067         numberOfValues = (unsigned int) TplConvert<char>::_2int(parameter.find("learn-horizon")->second.c_str());
00068     }
00069     tCycle = 90;
00070     if (parameter.find("tcycle") != parameter.end()) {
00071         tCycle = (unsigned int) TplConvert<char>::_2SUMOReal(parameter.find("tcycle")->second.c_str());
00072     }
00073     deltaLimit = 1;
00074     if (parameter.find("min-diff") != parameter.end()) {
00075         deltaLimit = TplConvert<char>::_2int(parameter.find("min-diff")->second.c_str());
00076     }
00077 }
00078 
00079 
00080 void
00081 MSAgentbasedTrafficLightLogic::init(NLDetectorBuilder& nb) {
00082     SUMOReal det_offset = TplConvert<char>::_2SUMOReal(myParameter.find("detector_offset")->second.c_str());
00083     LaneVectorVector::const_iterator i2;
00084     LaneVector::const_iterator i;
00085     // build the detectors
00086     for (i2 = myLanes.begin(); i2 != myLanes.end(); ++i2) {
00087         const LaneVector& lanes = *i2;
00088         for (i = lanes.begin(); i != lanes.end(); i++) {
00089             MSLane* lane = (*i);
00090             // Build the lane state detetcor and set it into the container
00091             std::string id = "TL_" + myID + "_" + myProgramID + "_E2OverLanesDetectorStartingAt_" + lane->getID();
00092 
00093             if (myE2Detectors.find(lane) == myE2Detectors.end()) {
00094                 MSDetectorFileOutput* det =
00095                     nb.buildMultiLaneE2Det(id,
00096                                            DU_TL_CONTROL, lane, 0, det_offset,
00097                                            /*haltingTimeThreshold!!!*/ 1,
00098                                            /*haltingSpeedThreshold!!!*/(SUMOReal)(5.0 / 3.6),
00099                                            /*jamDistThreshold!!!*/ 10);
00100                 myE2Detectors[lane] = static_cast<MS_E2_ZS_CollectorOverLanes*>(det);
00101             }
00102         }
00103     }
00104 
00105 
00106     // initialise the duration
00107     unsigned int tCycleIst = 0;          // the actual cycletime
00108     unsigned int tCycleMin = 0;          // the minimum cycle time
00109     unsigned int tDeltaGreen = 0;         // the difference between the actual cycle time and the required cycle time
00110 
00112     for (unsigned int actStep = 0; actStep != myPhases.size(); actStep++) {
00113         unsigned int dur = (unsigned int) myPhases[actStep]->duration;
00114         tCycleIst = tCycleIst + dur;
00115         if (myPhases[actStep]->isGreenPhase()) {
00116             unsigned int mindur = (unsigned int) myPhases[actStep]->minDuration;
00117             tCycleMin = tCycleMin + mindur;
00118         } else {
00119             tCycleMin = tCycleMin + dur;
00120         }
00121     }
00122     if (tCycle < tCycleMin) {
00123         tCycle = tCycleMin;
00124     }
00125     if (tCycleIst < tCycle) {
00126         tDeltaGreen = tCycle - tCycleIst;
00127         lengthenCycleTime(tDeltaGreen);
00128     }
00129     if (tCycleIst > tCycle) {
00130         tDeltaGreen = tCycleIst - tCycle;
00131         cutCycleTime(tDeltaGreen);
00132     }
00133 }
00134 
00135 
00136 MSAgentbasedTrafficLightLogic::~MSAgentbasedTrafficLightLogic() {}
00137 
00138 
00139 // ------------ Switching and setting current rows
00140 SUMOTime
00141 MSAgentbasedTrafficLightLogic::trySwitch(bool) {
00142     assert(getCurrentPhaseDef().minDuration >= 0);
00143     assert(getCurrentPhaseDef().minDuration <= getCurrentPhaseDef().duration);
00144     if (myPhases[myStep]->isGreenPhase()) {
00145         // collects the data for the signal control
00146         collectData();
00147         // decides wheter greentime shall distributed between phases
00148         if (tDecide <= tSinceLastDecision) {
00149             calculateDuration();
00150         }
00151     }
00152     // increment the index to the current phase
00153     nextStep();
00154     // set the next event
00155     while (getCurrentPhaseDef().duration == 0) {
00156         nextStep();
00157     }
00158     assert(myPhases.size() > myStep);
00159     return getCurrentPhaseDef().duration;
00160 }
00161 
00162 
00163 // ------------ "agentbased" algorithm methods
00164 unsigned int
00165 MSAgentbasedTrafficLightLogic::nextStep() {
00166     // increment the index to the current phase
00167     myStep++;
00168     assert(myStep <= myPhases.size());
00169     if (myStep == myPhases.size()) {
00170         myStep = 0;
00171     }
00172     // increment the number of cycles since last decision
00173     if (myStep == stepOfLastDecision) {
00174         tSinceLastDecision = tSinceLastDecision + 1;
00175     }
00176     return myStep;
00177 }
00178 
00179 
00180 void
00181 MSAgentbasedTrafficLightLogic::collectData() {
00182     const std::string& state = getCurrentPhaseDef().getState();
00183     // finds the maximum QUEUE_LENGTH_AHEAD_OF_TRAFFIC_LIGHTS_IN_VEHICLES of one phase
00184     SUMOReal maxPerPhase = 0;
00185     for (unsigned int i = 0; i < (unsigned int) state.size(); i++)  {
00186         // finds the maximum QUEUE_LENGTH_AHEAD_OF_TRAFFIC_LIGHTS_IN_VEHICLES of all lanes that have green
00187         if (state[i] == LINKSTATE_TL_GREEN_MAJOR || state[i] == LINKSTATE_TL_GREEN_MINOR) {
00188             const std::vector<MSLane*> &lanes = getLanesAt(i);
00189             if (lanes.empty())    {
00190                 break;
00191             }
00192             SUMOReal maxPerBit = 0;
00193             for (LaneVector::const_iterator j = lanes.begin(); j != lanes.end(); j++) {
00194                 if ((*j)->getEdge().getPurpose() == MSEdge::EDGEFUNCTION_INTERNAL) {
00195                     continue;
00196                 }
00205             }
00206             if (maxPerPhase < maxPerBit) {
00207                 maxPerPhase = maxPerBit;
00208             }
00209         }
00210     }
00211     // if still no entry for the phase exists a new entry with an empty value is created
00212     if (myRawDetectorData.find(myStep) == myRawDetectorData.end()) {
00213         ValueType firstData;
00214         myRawDetectorData[myStep] = firstData;
00215     }
00216     /* checks whether the number of values that are already in the dataqueue is
00217        the same number of values taht shall be consideres in the traffic control
00218        if both numbers are the same, the oldest value is deleted */
00219     if (myRawDetectorData[myStep].size() == numberOfValues) {
00220         myRawDetectorData[myStep].pop_back();
00221     }
00222     // adds the detectorvalue of the considered phase
00223     myRawDetectorData[myStep].push_front(maxPerPhase);
00224 }
00225 
00226 
00227 void
00228 MSAgentbasedTrafficLightLogic::aggregateRawData() {
00229     for (PhaseValueMap::const_iterator i = myRawDetectorData.begin(); i != myRawDetectorData.end(); i++) {
00230         SUMOReal sum = 0;
00231         for (ValueType:: const_iterator it = myRawDetectorData[(*i).first].begin(); it != myRawDetectorData[(*i).first].end(); it ++) {
00232             sum = sum + *it;
00233         }
00234         SUMOReal meanvalue = sum / myRawDetectorData[(*i).first].size();
00235         myMeanDetectorData[(*i).first] = meanvalue;
00236     }
00237 }
00238 
00239 
00240 void
00241 MSAgentbasedTrafficLightLogic::calculateDuration() {
00242     aggregateRawData();
00243     unsigned int stepOfMaxValue = findStepOfMaxValue();
00244     if (stepOfMaxValue == myPhases.size())    {
00245         return;
00246     }
00247     unsigned int stepOfMinValue = findStepOfMinValue();
00248     if (stepOfMinValue == myPhases.size())    {
00249         return;
00250     }
00251     if (stepOfMinValue == stepOfMaxValue)    {
00252         return;
00253     }
00254     SUMOReal deltaIst = (myMeanDetectorData[stepOfMaxValue] - myMeanDetectorData[stepOfMinValue])
00255                         / myMeanDetectorData[stepOfMaxValue];
00256     if (deltaIst > deltaLimit) {
00257         myPhases[stepOfMaxValue]->duration = myPhases[stepOfMaxValue]->duration + 1;
00258         myPhases[stepOfMinValue]->duration = myPhases[stepOfMinValue]->duration - 1;
00259         tSinceLastDecision = 0;
00260         stepOfLastDecision = myStep;
00261     }
00262 }
00263 
00264 
00265 void
00266 MSAgentbasedTrafficLightLogic::lengthenCycleTime(unsigned int toLengthen) {
00267     typedef std::pair <unsigned int, unsigned int> contentType;
00268     typedef std::vector< std::pair <unsigned int, unsigned int> > GreenPhasesVector;
00269     GreenPhasesVector tmp_phases(myPhases.size());
00270     tmp_phases.clear();
00271     unsigned int maxLengthen = 0;  // the sum of all times, that is possible to lengthen
00272 
00273     /* fills the vector tmp_phases with the difference between
00274        duration and maxduration and the myStep of the phases.
00275        only phases with duration < maxDuration are written in the vector.
00276        sorts the vector after the difference. */
00277     for (unsigned int i_Step = 0; i_Step != myPhases.size(); i_Step++) {
00278         if (myPhases[i_Step]->isGreenPhase()) {
00279             unsigned int dur = (unsigned int) myPhases[i_Step]->duration;
00280             unsigned int maxdur = (unsigned int) myPhases[i_Step]->maxDuration;
00281             if (dur < maxdur) {
00282                 contentType tmp;
00283                 tmp.second = i_Step;
00284                 tmp.first = maxdur - dur;
00285                 tmp_phases.push_back(tmp);
00286                 maxLengthen = maxLengthen + tmp.first;
00287             }
00288         }
00289     }
00290     sort(tmp_phases.begin(), tmp_phases.end());
00291     //lengthens the phases acording to the difference between duration and maxDuration
00292     for (GreenPhasesVector::iterator i = tmp_phases.begin(); i != tmp_phases.end(); i++) {
00293         SUMOTime toLengthenPerPhase = 0;
00294         SUMOReal tmpdb = ((*i).first * toLengthen / SUMOReal(maxLengthen)) + (SUMOReal) 0.5;
00295         toLengthenPerPhase = static_cast<SUMOTime>(tmpdb);
00296         toLengthen = toLengthen - (unsigned int) toLengthenPerPhase;
00297         maxLengthen = maxLengthen - (*i).first;
00298         SUMOTime newDur = myPhases[(*i).second]->duration + toLengthenPerPhase;
00299         myPhases[(*i).second]->duration = newDur;
00300     }
00301 }
00302 
00303 
00304 void
00305 MSAgentbasedTrafficLightLogic::cutCycleTime(unsigned int toCut) {
00306     typedef std::pair <unsigned int, unsigned int> contentType;
00307     typedef std::vector< std::pair <unsigned int, unsigned int> > GreenPhasesVector;
00308     GreenPhasesVector tmp_phases(myPhases.size());
00309     tmp_phases.clear();
00310     unsigned maxCut = 0;  // the sum of all times, that is possible to cut
00311 
00312     /* fills the vector tmp_phases with the difference between
00313        duration and minduration and the myStep of the phases.
00314        only phases with duration > minDuration are written in the vector.
00315        sorts the vector after the difference. */
00316     for (unsigned i_Step = 0; i_Step != myPhases.size(); i_Step++) {
00317         if (myPhases[i_Step]->isGreenPhase()) {
00318             unsigned int dur = (unsigned int) myPhases[i_Step]->duration;
00319             unsigned int mindur = (unsigned int) myPhases[i_Step]->minDuration;
00320             if (dur > mindur) {
00321                 contentType tmp;
00322                 tmp.second = i_Step;
00323                 tmp.first = dur - mindur;
00324                 tmp_phases.push_back(tmp);
00325                 maxCut = maxCut + tmp.first;
00326             }
00327         }
00328     }
00329     std::sort(tmp_phases.begin(), tmp_phases.end());
00330     //cuts the phases acording to the difference between duration and minDuration
00331     for (GreenPhasesVector::iterator i = tmp_phases.begin(); i != tmp_phases.end(); i++) {
00332         SUMOTime toCutPerPhase = 0;
00333         SUMOReal tmpdb = ((*i).first * toCut / SUMOReal(maxCut)) + (SUMOReal) 0.5;
00334         toCutPerPhase = static_cast<SUMOTime>(tmpdb);
00335         toCut = toCut - (unsigned int) toCutPerPhase;
00336         maxCut = maxCut - (*i).first;
00337         SUMOTime newDur = myPhases[(*i).second]->duration - toCutPerPhase;
00338         myPhases[(*i).second]->duration = newDur;
00339     }
00340 }
00341 
00342 
00343 unsigned int
00344 MSAgentbasedTrafficLightLogic::findStepOfMaxValue() const {
00345     unsigned int StepOfMaxValue = (unsigned int) myPhases.size();
00346     SUMOReal MaxValue = -1;
00347     for (MeanDataMap::const_iterator it = myMeanDetectorData.begin(); it != myMeanDetectorData.end(); it++) {
00348         // checks whether the actual duruation is shorter than maxduration
00349         // otherwise the phase can't be lenghten
00350         unsigned int maxDur = (unsigned int) myPhases[(*it).first]->maxDuration;
00351         unsigned int actDur = (unsigned int) myPhases[(*it).first]->duration;
00352         if (actDur >= maxDur) {
00353             continue;
00354         }
00355         if ((*it).second > MaxValue) {
00356             MaxValue = (*it).second;
00357             StepOfMaxValue = (*it).first;
00358         }
00359     }
00360     return StepOfMaxValue;
00361 }
00362 
00363 
00364 unsigned int
00365 MSAgentbasedTrafficLightLogic::findStepOfMinValue() const {
00366     unsigned int StepOfMinValue = (unsigned int) myPhases.size();
00367     SUMOReal MinValue = 9999;
00368     for (MeanDataMap::const_iterator it = myMeanDetectorData.begin(); it != myMeanDetectorData.end(); it++) {
00369         // checks whether the actual duruation is longer than minduration
00370         // otherwise the phase can't be cut
00371         unsigned int minDur = (unsigned int) myPhases[(*it).first]->minDuration;
00372         unsigned int actDur = (unsigned int) myPhases[(*it).first]->duration;
00373         if (actDur <= minDur) {
00374             continue;
00375         }
00376         if ((*it).second < MinValue) {
00377             MinValue = (*it).second;
00378             StepOfMinValue = (*it).first;
00379         }
00380     }
00381     return StepOfMinValue;
00382 }
00383 
00384 
00385 /*
00386 SUMOReal
00387 MSAgentbasedTrafficLightLogic::currentForLane(E2::DetType what,
00388         MSLane *lane) const
00389 {
00390 
00391     E2DetectorMap::const_iterator i=myE2Detectors.find(lane);
00392     return (*i).second->getCurrent(what);
00393 }
00394 */
00395 
00396 
00397 /****************************************************************************/
00398 
 All Data Structures Files Functions Variables Typedefs Enumerations Enumerator Friends Defines