SUMO - Simulation of Urban MObility
AGActivities.cpp
Go to the documentation of this file.
00001 /****************************************************************************/
00009 // Main class that manages activities taken in account and generates the
00010 // inhabitants' trip list.
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 // activitygen module
00015 // Copyright 2010 TUM (Technische Universitaet Muenchen, http://www.tum.de/)
00016 /****************************************************************************/
00017 //
00018 //   This file is part of SUMO.
00019 //   SUMO is free software: you can redistribute it and/or modify
00020 //   it under the terms of the GNU General Public License as published by
00021 //   the Free Software Foundation, either version 3 of the License, or
00022 //   (at your option) any later version.
00023 //
00024 /****************************************************************************/
00025 
00026 
00027 // ===========================================================================
00028 // included modules
00029 // ===========================================================================
00030 #ifdef _MSC_VER
00031 #include <windows_config.h>
00032 #else
00033 #include <config.h>
00034 #endif
00035 
00036 #include "AGActivities.h"
00037 #include "AGWorkAndSchool.h"
00038 #include "AGFreeTime.h"
00039 #include "../city/AGTime.h"
00040 #include <sstream>
00041 #include <utils/common/RandHelper.h>
00042 
00043 #define REBUILD_ITERATION_LIMIT 2
00044 
00045 
00046 // ===========================================================================
00047 // method definitions
00048 // ===========================================================================
00049 void
00050 AGActivities::addTrip(AGTrip t, std::list<AGTrip> *tripSet) {
00051     tripSet->push_back(t);
00052 }
00053 
00054 void
00055 AGActivities::addTrips(std::list<AGTrip> t, std::list<AGTrip> *tripSet) {
00056     std::list<AGTrip>::iterator it;
00057     for (it = t.begin() ; it != t.end() ; ++it) {
00058         tripSet->push_back(*it);
00059     }
00060 }
00061 
00062 void
00063 AGActivities::generateActivityTrips() {
00064     int numbErr;
00068     numbErr = 0;
00069     std::list<AGBusLine>::iterator itBL;
00070     for (itBL = myCity->busLines.begin() ; itBL != myCity->busLines.end() ; ++itBL) {
00071         if (! generateBusTraffic(*itBL)) {
00072             ++numbErr;
00073         }
00074     }
00075     if (numbErr != 0) {
00076         std::cerr << "ERROR: " << numbErr << " bus lines couldn't been completely generated ( " << (float)numbErr * 100.0 / (float)myCity->busLines.size() << "% )..." << std::endl;
00077     } else {
00078         std::cout << "no problem during bus line trip generation..." << std::endl;
00079     }
00080 
00081     std::cout << "after public transportation: " << trips.size() << std::endl;
00086     numbErr = 0;
00087     std::list<AGHousehold>::iterator itHH;
00088     for (itHH = myCity->households.begin() ; itHH != myCity->households.end() ; ++itHH) {
00089         if (! generateTrips(*itHH)) {
00090             ++numbErr;
00091         }
00092     }
00093     if (numbErr != 0) {
00094         std::cout << "WARNING: " << numbErr << " ( " << (float)numbErr * 100.0 / (float)myCity->households.size() << "% ) households' trips haven't been generated: would probably need more iterations for rebuilding..." << std::endl;
00095     } else {
00096         std::cout << "no problem during households' trips generation..." << std::endl;
00097     }
00098 
00099     std::cout << "after household activities: " << trips.size() << std::endl;
00104     if (! generateInOutTraffic()) {
00105         std::cerr << "ERROR while generating in/Out traffic..." << std::endl;
00106     } else {
00107         std::cout << "no problem during in/out traffic generation..." << std::endl;
00108     }
00109 
00110     std::cout << "after incoming/outgoing traffic: " << trips.size() << std::endl;
00115     if (! generateRandomTraffic()) {
00116         std::cerr << "ERROR while generating random traffic..." << std::endl;
00117     } else {
00118         std::cout << "no problem during random traffic generation..." << std::endl;
00119     }
00120 
00121     std::cout << "after random traffic: " << trips.size() << std::endl;
00122 }
00123 
00124 bool
00125 AGActivities::generateTrips(AGHousehold& hh) {
00126     int iteration = 0;
00127     bool generated = false;
00128     std::list<AGTrip> temporaTrips;
00129     while (!generated && iteration < REBUILD_ITERATION_LIMIT) {
00130         if (!temporaTrips.empty()) {
00131             temporaTrips.clear();
00132         }
00133         // Work and school activities
00134         AGWorkAndSchool ws(&hh, &(myCity->statData), &temporaTrips);
00135         generated = ws.generateTrips();
00136         if (!generated) {
00137             hh.regenerate();
00138             ++iteration;
00139             continue;
00140         }
00141         addTrips(ws.partialActivityTrips, &temporaTrips);
00142 
00143         // free time activities
00144         AGFreeTime ft(&hh, &(myCity->statData), &temporaTrips, nbrDays);
00145         generated = ft.generateTrips();
00146         if (!generated) {
00147             hh.regenerate();
00148             ++iteration;
00149             continue;
00150         }
00151         addTrips(ft.partialActivityTrips, &temporaTrips);
00152         //cout << "after this hh: " << temporaTrips.size() << " we have: " << trips.size() << endl;
00153         //trips of all activities generated:
00154         addTrips(temporaTrips, &trips);
00155     }
00156     return generated;
00157 }
00158 
00159 bool
00160 AGActivities::generateBusTraffic(AGBusLine bl) {
00161     std::list<AGBus>::iterator itB;
00162     std::list<AGPosition>::iterator itS;
00166     for (itB = bl.buses.begin() ; itB != bl.buses.end() ; ++itB) {
00167         if (bl.stations.size() < 1) {
00168             return false;
00169         }
00170         AGTrip t(bl.stations.front(), bl.stations.back(), *itB, itB->getDeparture());
00171         for (itS = bl.stations.begin() ; itS != bl.stations.end() ; ++itS) {
00172             if (*itS == t.getDep() || *itS == t.getArr()) {
00173                 continue;
00174             }
00175             t.addLayOver(*itS);
00176         }
00177         trips.push_back(t);
00178     }
00182     //verify that buses return back to the beginning
00183     if (bl.revStations.empty()) {
00184         return true;    //in this case, no return way: everything is ok.
00185     }
00186     for (itB = bl.revBuses.begin() ; itB != bl.revBuses.end() ; ++itB) {
00187         if (bl.revStations.size() < 1) {
00188             return false;
00189         }
00190         AGTrip t(bl.revStations.front(), bl.revStations.back(), *itB, itB->getDeparture());
00191         for (itS = bl.revStations.begin() ; itS != bl.revStations.end() ; ++itS) {
00192             if (*itS == t.getDep() || *itS == t.getArr()) {
00193                 continue;
00194             }
00195             t.addLayOver(*itS);
00196         }
00197         trips.push_back(t);
00198     }
00199     return true;
00200 }
00201 
00202 bool
00203 AGActivities::generateInOutTraffic() {
00209     if (myCity->peopleIncoming.empty()) {
00210         return true;
00211     }
00212     if (myCity->cityGates.empty()) {
00213         return false;
00214     }
00215     int num = 1;
00216     std::list<AGAdult>::iterator itA;
00217 
00218     for (itA = myCity->peopleIncoming.begin() ; itA != myCity->peopleIncoming.end() ; ++itA) {
00219         int posi = myCity->statData.getRandomCityGateByIncoming();
00220         std::string nom(generateName(num, "carIn"));
00221         AGTrip wayTrip(myCity->cityGates[posi], itA->getWorkPosition().getPosition(), nom, itA->getWorkPosition().getOpening());
00222         //now we put the estimated time of entrance in the city.
00223         wayTrip.setDepTime(wayTrip.estimateDepTime(wayTrip.getTime(), myCity->statData.speedTimePerKm));
00224         AGTrip retTrip(itA->getWorkPosition().getPosition(), myCity->cityGates[posi], nom, itA->getWorkPosition().getClosing());
00225         trips.push_back(wayTrip);
00226         trips.push_back(retTrip);
00227         ++num;
00228     }
00229     return true;
00230 }
00231 
00232 std::string
00233 AGActivities::generateName(int i, std::string prefix) {
00234     std::ostringstream os;
00235     os << i;
00236     return prefix + os.str();
00237 }
00238 
00239 bool
00240 AGActivities::generateRandomTraffic() {
00241     //total number of trips during the whole simulation
00242     int totalTrips = 0, ttOneDayTrips = 0, ttDailyTrips = 0;
00243     std::list<AGTrip>::iterator it;
00244     for (it = trips.begin() ; it != trips.end() ; ++it) {
00245         if (it->isDaily()) {
00246             ++ttDailyTrips;
00247         } else {
00248             ++ttOneDayTrips;
00249         }
00250     }
00251     totalTrips = ttOneDayTrips + ttDailyTrips * nbrDays;
00252     //TESTS
00253     std::cout << "Before Random traffic generation (days are still entire):" << std::endl;
00254     std::cout << "- Total number of trips: " << totalTrips << std::endl;
00255     std::cout << "- Total daily trips: " << ttDailyTrips << std::endl;
00256     std::cout << "- Total one-day trips: " << ttOneDayTrips << std::endl;
00257     //END OF TESTS
00258 
00259     //random uniform distribution:
00260     int nbrRandUni = (int)((float)totalTrips * myCity->statData.uniformRandomTrafficRate / (1.0f - myCity->statData.uniformRandomTrafficRate));
00261     //TESTS
00262     std::cout << "added uniform random trips: " << nbrRandUni << std::endl;
00263     //END OF TESTS
00264     for (int i = 0 ; i < nbrRandUni ; ++i) {
00265         AGPosition dep(myCity->getRandomStreet());
00266         AGPosition arr(myCity->getRandomStreet());
00267         AGTime depTime(RandHelper::rand(nbrDays * 86400));
00268         AGTrip rdtr(dep, arr, generateName(i, "randUni"), depTime.getTime() % 86400, depTime.getDay() + 1);
00269         rdtr.setType("random");
00270         trips.push_back(rdtr);
00271     }
00272 
00273     //random proportional distribution:
00274     float proportionalPercentage = 0.05f;
00275     //TODO generate a proportionally distributed random traffic
00276 
00277     return true;
00278 }
00279 
00280 /****************************************************************************/
 All Data Structures Files Functions Variables Typedefs Enumerations Enumerator Friends Defines