diff --git a/Simulation.cpp b/Simulation.cpp index 11cd64116af5aee19d0d75e3adfe0318988e618d..209dabd584dc71607a6639790a33072cd3211715 100644 --- a/Simulation.cpp +++ b/Simulation.cpp @@ -449,7 +449,7 @@ void Simulation::PrintStatistics() { for(itr = transitions.begin(); itr != transitions.end(); ++itr){ Transition* goal = itr->second; if(goal->IsExit()){ - Log->Write("Exit ID [%d] used by [%d] pedestrians",goal->GetID(),goal->GetDoorUsage()); + Log->Write("Exit ID [%d] used by [%d] pedestrians. Last passing time [%0.2f] s",goal->GetID(),goal->GetDoorUsage(),goal->GetLastPassingTime()); } } } diff --git a/general/Macros.h b/general/Macros.h index ecc53f9a3db5310b269db0a8aa176d684bb42532..2a3a37eaa49176e87c6ab4c80169845ebeaaf415 100644 --- a/general/Macros.h +++ b/general/Macros.h @@ -50,8 +50,11 @@ #define J_EPS_INFO_DIST 2.0 // [m] abstand für Informationsaustausch (GraphRouter) #define J_EPS_GOAL 0.005 // [m] Abstand zum Ziel, damit Fußgänger immer zu einem Raum gehört #define J_TOLERANZ 0.03 // [m] Toleranz beim erstellen der Linien -#define J_EPS_V 0.1 // [m/s] wenn v<EPS_V wird mit 0 gerechnet +#define J_EPS_V 0.2 // [m/s] wenn v<EPS_V wird mit 0 gerechnet +// routing macros +#define J_QUEUE_VEL_THRESHOLD_NEW_ROOM 0.7 // [m/s] maximum speed to be considered in a queue while looking for a reference in a new room +#define J_QUEUE_VEL_THRESHOLD_JAM 0.2 // [m/s] maximum speed to be considered in a queue while looking for a reference in a jam situation // Lenght of array #define CLENGTH 1000 diff --git a/geometry/Building.cpp b/geometry/Building.cpp index 0ea768ebb1bb5f4dc8bc3236dd7fbff513c6ff64..c25824d1a988b2796a64fcbc727bc013d069995b 100644 --- a/geometry/Building.cpp +++ b/geometry/Building.cpp @@ -1357,7 +1357,7 @@ void Building::DeletePedestrian(Pedestrian* ped) { //update the stats before deleting Transition* trans =GetTransitionByUID(ped->GetExitIndex()); if(trans) { - trans->IncreaseDoorUsage(1); + trans->IncreaseDoorUsage(1, ped->GetGlobalTime()); } delete ped; } diff --git a/geometry/Transition.cpp b/geometry/Transition.cpp index c11a007dd3d0e0ac12b774ea2ac4ccd8b8c3ba1a..92ce074ba9e40faf08d6e245c9867aeafd573267 100644 --- a/geometry/Transition.cpp +++ b/geometry/Transition.cpp @@ -38,6 +38,7 @@ using namespace std; Transition::Transition() : Crossing() { _isOpen = true; _doorUsage=0; + _lastPassingTime=0; _room2 = NULL; } @@ -180,10 +181,15 @@ string Transition::WriteElement() const { return geometry; } -void Transition::IncreaseDoorUsage(int number) { +void Transition::IncreaseDoorUsage(int number, double time) { _doorUsage+=number; + _lastPassingTime=time; } int Transition::GetDoorUsage() const { return _doorUsage; } + +double Transition::GetLastPassingTime() const { + return _lastPassingTime; +} diff --git a/geometry/Transition.h b/geometry/Transition.h index 91534d4eaad4b966ed6d2e643d558c02916eda55..85d1ca9fb208943542b7971e2cffdd298c29e5f1 100644 --- a/geometry/Transition.h +++ b/geometry/Transition.h @@ -40,6 +40,7 @@ private: std::string _type; // number of agents that passed that exit int _doorUsage; + double _lastPassingTime; public: @@ -70,15 +71,21 @@ public: /** * Increment the number of persons that used that exit - * @param number + * @param number, how many person have passed the door + * @param time, at which time */ - void IncreaseDoorUsage(int number); + void IncreaseDoorUsage(int number, double time); /** * @return the number of pedestrians that used that exit. */ int GetDoorUsage() const; + /** + * @return the last time this door was crossed + */ + double GetLastPassingTime() const; + /** * Set/Get the type of the transition * TODO: where is type defined? diff --git a/inputfiles/ship_msw/ini_ship.xml b/inputfiles/ship_msw/ini_ship.xml index cc8deb658adb9feb66d0b1a2b8bacffc4400e2e7..c6f8b4d010ce10a8285380846cc349f00fcd26b0 100755 --- a/inputfiles/ship_msw/ini_ship.xml +++ b/inputfiles/ship_msw/ini_ship.xml @@ -10,8 +10,8 @@ <geometry>bateau.xml</geometry> <!-- trajectories file and format --> <trajectories format="xml-plain" embed_mesh="false" fps="8"> - <!-- <file location="trajectories_4.xml" /> --> - <socket hostname="127.0.0.1" port="8989"/> + <!--<file location="trajectories_4.xml" /> --> + <socket hostname="127.0.0.1" port="8989"/> </trajectories> <!-- where to store the logs --> <!--<logfile>outputfiles/log.txt</logfile> --> @@ -26,7 +26,7 @@ <!-- doors states are: close or open --> <doors> <door trans_id="3" caption="" state="open" /> - <door trans_id="4" caption="" state="close" /> + <door trans_id="4" caption="" state="open" /> <door trans_id="6" caption="" state="open" /> </doors> </traffic_constraints> @@ -70,7 +70,7 @@ <group group_id="5" room_id="0" subroom_id="0" number="0" goal_id="" router_id="1" route_id="" motivation=""/> <group group_id="0" room_id="0" subroom_id="0" number="0" goal_id="" router_id="1" route_id="" /> <group group_id="1" room_id="0" subroom_id="1" number="0" goal_id="" router_id="2" route_id="" patience="5"/> - <group group_id="2" room_id="0" number="100" goal_id="-1" router_id="2" patience="5"/> + <group group_id="2" room_id="0" number="200" goal_id="-1" router_id="2" patience="5"/> <group group_id="3" room_id="0" subroom_id="0" number="10" goal_id="-1" router_id="2" patience="5"/> </agents_distribution> </agents> @@ -100,7 +100,7 @@ </operational_models> <route_choice_models> - <router router_id="2" description="global_shortest"> + <router router_id="2" description="quickest"> <parameters> <!-- extra routing information --> <navigation_lines file="routing.xml" /> diff --git a/routing/GlobalRouter.cpp b/routing/GlobalRouter.cpp index df818b3386ec748b4c4c8dd62c75c6c75a45ff3b..f20159d5de1e0b2a64725229776e5ddd07e4603b 100644 --- a/routing/GlobalRouter.cpp +++ b/routing/GlobalRouter.cpp @@ -717,7 +717,7 @@ void GlobalRouter::GetRelevantRoutesTofinalDestination(Pedestrian *ped, vector<A if(ap->GetNearestTransitAPTO(ped->GetFinalDestination())==goals[g2]){ //FIXME there are interference with hlines. suitable only for quickest route considering exits, // crossings only - relevant=true; + relevant=false; break; } } diff --git a/routing/QuickestPathRouter.cpp b/routing/QuickestPathRouter.cpp index 7975c9973f864eb470b85a6d2630400d6222b959..2363a96c44002477a3e9fdee8fd9b25cf11c3449 100644 --- a/routing/QuickestPathRouter.cpp +++ b/routing/QuickestPathRouter.cpp @@ -76,15 +76,21 @@ int QuickestPathRouter::FindExit(Pedestrian* ped){ // that ped will be deleted if(next==-1) return next; + if(ped->IsFeelingLikeInJam()){ //ped->SetSpotlight(true); - Redirect(ped); - ped->ResetTimeInJam(); + + if(isCongested(ped)==true){ + Redirect(ped); + ped->ResetTimeInJam(); + //ped->SetSpotlight(true); + } //cout<<"I am feeling like in Jam next: "<<ped->GetID()<<endl; //ped->RerouteIn(2.50); // seconds }else if(ped->IsReadyForRerouting()){ Redirect(ped); ped->ResetRerouting(); + }else{ ped->UpdateReroutingTime(); } @@ -194,6 +200,7 @@ int QuickestPathRouter::GetQuickestRoute(Pedestrian*ped, AccessPoint* nearestAP) // get all AP connected to the nearest //const vector<AccessPoint*>& aps = nearestAP->GetConnectingAPs(); + //TODO: should be get relevant destination const vector<AccessPoint*>& aps = nearestAP->GetTransitAPsTo(ped->GetFinalDestination()); //special case where there is only one alternative @@ -209,7 +216,7 @@ int QuickestPathRouter::GetQuickestRoute(Pedestrian*ped, AccessPoint* nearestAP) int flag=0; int exitid=aps[ap]->GetID(); Pedestrian* myref=NULL; - SelectReferencePedestrian(ped,&myref,exitid,&flag); + SelectReferencePedestrian(ped,&myref,J_QUEUE_VEL_THRESHOLD_NEW_ROOM,exitid,&flag); // compute the time double time=FLT_MAX; @@ -526,20 +533,20 @@ void QuickestPathRouter::Init(Building* building){ Log->Write("INFO:\tDone with Quickest Path Router Engine!"); } -void QuickestPathRouter::SelectReferencePedestrian(Pedestrian* myself, Pedestrian** myref, int exitID, int* flag){ +void QuickestPathRouter::SelectReferencePedestrian(Pedestrian* myself, Pedestrian** myref, double jamThreshold, int exitID, int* flag){ *flag=FREE_EXIT; // assume free exit Crossing* crossing=_building->GetTransOrCrossByUID(exitID); - double jamThreshold=0.5; + double radius=3.0;//start radius for looking at the reference in metres bool done=false; do{ vector<Pedestrian*> queue; queue.reserve(250); - GetQueueAtExit(crossing,jamThreshold,radius,queue); + GetQueueAtExit(crossing,jamThreshold,radius,queue,myself->GetSubRoomID()); if(queue.size()==0){ //check if I can see/reach the exit without much effort if(IsDirectVisibilityBetween(myself,crossing)){ @@ -557,7 +564,7 @@ void QuickestPathRouter::SelectReferencePedestrian(Pedestrian* myself, Pedestria double closestDistance=FLT_MAX; //select a reference pedestrian I can see for(unsigned int p=0;p<queue.size();p++){ - Pedestrian* ped = queue[p]; + Pedestrian* ped = queue[p]; //ped->SetSpotlight(true); if(IsDirectVisibilityBetween(myself,ped)==false) continue; double dist= (ped->GetPos()-myself->GetPos()).NormSquare(); //cout<<"suspect found 1 @ "<< dist<< " { "<< closestDistance<<" }"<<endl; @@ -588,13 +595,41 @@ void QuickestPathRouter::SelectReferencePedestrian(Pedestrian* myself, Pedestria exit(EXIT_FAILURE); } } - }while (done==false); + /////delete me after + // if(done==true){ + // //debug area + // if(*myref){ + // + // if(myself->GetID()==488){ + // myself->SetSpotlight(true); + // (*myref)->SetSpotlight(true); + // (*myref)->Dump((*myref)->GetID()); + // + // //highlight the queue + // for(unsigned int p=0;p<queue.size();p++){ + // Pedestrian* ped = queue[p]; + // ped->SetSpotlight(true); + // } + // + // } + // } + // } + //// delete me after + } while (done==false); + + + //debug area if(*myref){ - //(*myref)->SetSpotlight(true); - myself->SetSpotlight(true); - //cout<<"ref ped found: " <<endl; - //getc(stdin); + + // if(myself->GetID()==488){ + // myself->SetSpotlight(true); + // (*myref)->SetSpotlight(true); + // (*myref)->Dump((*myref)->GetID()); + // + // + // } + } else{ //cout<<"no ref ped found: " <<endl; @@ -630,9 +665,9 @@ int QuickestPathRouter::GetCommonDestinationCount(AccessPoint* ap1, AccessPoint* } -//TODO: maybe you should consider only the queue in the current subroom of the pedestrian. + void QuickestPathRouter::GetQueueAtExit(Crossing* crossing, double minVel, - double radius, vector<Pedestrian*>& queue){ + double radius, vector<Pedestrian*>& queue,int subroomToConsider){ SubRoom* sbr1 = crossing->GetSubRoom1(); SubRoom* sbr2 = crossing->GetSubRoom2(); @@ -646,7 +681,7 @@ void QuickestPathRouter::GetQueueAtExit(Crossing* crossing, double minVel, sbr2=NULL; } - if (sbr1){ + if (sbr1 && (sbr1->GetSubRoomID()==subroomToConsider)){ //double closestDistance=FLT_MAX; const vector<Pedestrian*>& peds = sbr1->GetAllPedestrians(); for (unsigned int p=0;p<peds.size();p++){ @@ -663,7 +698,7 @@ void QuickestPathRouter::GetQueueAtExit(Crossing* crossing, double minVel, } } - if (sbr2){ + if (sbr2 && (sbr2->GetSubRoomID()==subroomToConsider)){ //double closestDistance=FLT_MAX; const vector<Pedestrian*>& peds = sbr2->GetAllPedestrians(); for (unsigned int p=0;p<peds.size();p++){ @@ -680,7 +715,8 @@ void QuickestPathRouter::GetQueueAtExit(Crossing* crossing, double minVel, } } } - + //cout<<"queue size:"<<queue.size()<<endl; + //cout<<"mean val:"<<minVel2<<endl; } bool QuickestPathRouter::IsDirectVisibilityBetween(Pedestrian* ped, Pedestrian* ref){ @@ -767,7 +803,52 @@ int QuickestPathRouter::GetObstaclesCountBetween(const Point& p1, const Point& p int QuickestPathRouter::isCongested(Pedestrian* ped){ + //define as the ratio of people in front of me and behind me + + Room* room=_building->GetRoom(ped->GetRoomID()); + SubRoom* sub=room->GetSubRoom(ped->GetSubRoomID()); + const vector<Pedestrian*>& allPeds=sub->GetAllPedestrians(); + + //in the case there are only few people in the room + if(allPeds.size()<=OBSTRUCTION) return false; + + double myDist=ped->GetDistanceToNextTarget(); + double inFrontofMe=0; + double behindMe=0; + + for (unsigned int p=0;p<allPeds.size();p++){ + Pedestrian* ped2 = allPeds[p]; + //only consider pedestrians that are going in my direction + // caution this will not work with hlines + if(ped2->GetExitIndex()!=ped->GetExitIndex()) continue; + // skip myself + if(ped2->GetID()==ped->GetID()) continue; + + if(myDist>ped2->GetDistanceToNextTarget()){ + inFrontofMe++; + } else { + behindMe++; + } + } + + + double ratio=inFrontofMe/(inFrontofMe+behindMe); + // if(ped->GetID()==255) cout<<"ratio:"<<ratio<<endl; + // if((ped->GetID()==255) && (ratio>0.8)){ + // cout<<"ratio:"<<ratio<<endl; + // ped->Dump(255); + // exit(0); + // } + + if(ratio>0.8) return true; + + return false; + + //if(ped->GetID()==88) + //cout<<"ratio:"<<ratio<<endl; + //return true; + /* //collect the pedestrians within 1 metre radius vector<Pedestrian*> neighbourhood; double range=1.0;//1m @@ -818,7 +899,9 @@ int QuickestPathRouter::isCongested(Pedestrian* ped){ } if(pedCrossing<OBSTRUCTION) return false; + return true; + */ } @@ -827,7 +910,7 @@ double QuickestPathRouter::GetEstimatedTravelTimeVia(Pedestrian* ped, int exitid //select a reference pedestrian Pedestrian* myref=NULL; int flag=FREE_EXIT; //assume free exit - SelectReferencePedestrian(ped,&myref,exitid,&flag); + SelectReferencePedestrian(ped,&myref,J_QUEUE_VEL_THRESHOLD_JAM,exitid,&flag); AccessPoint* ap=_accessPoints[exitid]; @@ -855,8 +938,8 @@ double QuickestPathRouter::GetEstimatedTravelTimeVia(Pedestrian* ped, int exitid if((myref!=NULL) && (flag==REF_PED_FOUND)){ //time to reach the reference - //double t1= (ped->GetPos()- myref->GetPos()).Norm()/ped->GetV().Norm(); - double t1= (ped->GetPos()- myref->GetPos()).Norm()/ped->GetV0Norm(); + double t1= (ped->GetPos()- myref->GetPos()).Norm()/ped->GetV().Norm(); + //double t1= (ped->GetPos()- myref->GetPos()).Norm()/ped->GetV0Norm(); if(myref->GetV().Norm()==0.0){ Log->Write("ERROR:\t the reference pedestrian velocity is zero"); exit(0); @@ -865,7 +948,9 @@ double QuickestPathRouter::GetEstimatedTravelTimeVia(Pedestrian* ped, int exitid double t2=(myref->GetPos() - ap->GetCentre()).Norm()/myref->GetV().Norm(); //guess time from the Ap to the outside - double t3 = (ap->GetDistanceTo(ped->GetFinalDestination()))/ped->GetV().Norm(); + //double t3 = (ap->GetDistanceTo(ped->GetFinalDestination()))/ped->GetV().Norm(); + // we assume the desired velocity, because we cannot see anything + double t3 = (ap->GetDistanceTo(ped->GetFinalDestination()))/ped->GetV0Norm(); time=t1+t2+t3; } @@ -896,7 +981,7 @@ void QuickestPathRouter::Redirect(Pedestrian* ped){ Room* room=_building->GetRoom(ped->GetRoomID()); SubRoom* sub=room->GetSubRoom(ped->GetSubRoomID()); - const vector<int>& goals=room->GetAllTransitionsIDs(); + //const vector<int>& goals=room->GetAllTransitionsIDs(); //filter to keep only the emergencies exits. vector <AccessPoint*> relevantAPs; diff --git a/routing/QuickestPathRouter.h b/routing/QuickestPathRouter.h index 21454a8393e27b4e1bbe42dcd2340dd179af8c17..046ed999478f08f39ac049502c77107960d0ed8e 100644 --- a/routing/QuickestPathRouter.h +++ b/routing/QuickestPathRouter.h @@ -158,7 +158,7 @@ private: * flag=1: the exit is free, no reference * flag=2: I can't see the exit, nor references, too crowded, too many crossing pedes */ - void SelectReferencePedestrian(Pedestrian* me, Pedestrian** myref, int exitID, int* flag); + void SelectReferencePedestrian(Pedestrian* me, Pedestrian** myref, double JamThreshold, int exitID, int* flag); /** * extend the graph by connecting alternative routes. @@ -186,13 +186,11 @@ private: /** * return the queue at the specified exit within the specified radius + * if subroomToConsider == -1 then the two side of the crossing will be considered * - * @param exitID - * @param radius - * @param queue */ void GetQueueAtExit(Crossing* crossing, double minVel, - double radius, std::vector<Pedestrian*>& queue); + double radius, std::vector<Pedestrian*>& queue, int subroomToConsider=-1); /**