SUMO - Simulation of Urban MObility
|
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 /****************************************************************************/