Total time is not good because it doesn't penalize waiting time for
earlier trains. This can cause the state tree to explode as later ones
start moving.
The sum of travel and wait times for each train works much better.
state(other.state),
delay(other.delay),
waypoint(other.waypoint),
state(other.state),
delay(other.delay),
waypoint(other.waypoint),
+ distance_traveled(other.distance_traveled),
remaining_estimate(other.remaining_estimate),
remaining_estimate(other.remaining_estimate),
+ wait_time(other.wait_time),
blocked_by(other.blocked_by)
{
++occupied_tracks->refcount;
blocked_by(other.blocked_by)
{
++occupied_tracks->refcount;
--occupied_tracks->n_tracks;
}
--occupied_tracks->n_tracks;
}
+ distance_traveled += distance;
remaining_estimate -= distance;
}
remaining_estimate -= distance;
}
if(state==MOVING)
advance(info->speed*secs);
if(state==MOVING)
advance(info->speed*secs);
+ else if(state!=ARRIVED)
+ wait_time += secs*Time::sec;
}
void TrainRoutePlanner::TrainRoutingState::advance_track(unsigned next_path)
}
void TrainRoutePlanner::TrainRoutingState::advance_track(unsigned next_path)
TrainRoutePlanner::RoutingStep::RoutingStep(const RoutingStep *p):
time(p->time),
TrainRoutePlanner::RoutingStep::RoutingStep(const RoutingStep *p):
time(p->time),
- total_estimate(p->total_estimate),
+ cost_estimate(p->cost_estimate),
trains(p->trains),
prev(p)
{ }
trains(p->trains),
prev(p)
{ }
void TrainRoutePlanner::RoutingStep::update_estimate()
{
void TrainRoutePlanner::RoutingStep::update_estimate()
{
+ cost_estimate = Time::zero;
for(vector<TrainRoutingState>::const_iterator i=trains.begin(); i!=trains.end(); ++i)
for(vector<TrainRoutingState>::const_iterator i=trains.begin(); i!=trains.end(); ++i)
- {
- Time::TimeDelta t = time+(i->remaining_estimate/i->info->speed)*Time::sec+i->delay;
- if(i==trains.begin() || t>total_estimate)
- total_estimate = t;
- }
+ if(i->remaining_estimate>=0)
+ cost_estimate += i->wait_time+((i->distance_traveled+i->remaining_estimate)/i->info->speed)*Time::sec;
}
bool TrainRoutePlanner::RoutingStep::is_viable() const
{
}
bool TrainRoutePlanner::RoutingStep::is_viable() const
{
- if(total_estimate<Time::zero)
- return false;
-
for(vector<TrainRoutingState>::const_iterator i=trains.begin(); i!=trains.end(); ++i)
if(i->remaining_estimate<0)
return false;
for(vector<TrainRoutingState>::const_iterator i=trains.begin(); i!=trains.end(); ++i)
if(i->remaining_estimate<0)
return false;
bool TrainRoutePlanner::RoutingStep::operator<(const RoutingStep &other) const
{
bool TrainRoutePlanner::RoutingStep::operator<(const RoutingStep &other) const
{
- return total_estimate<other.total_estimate;
+ return cost_estimate<other.cost_estimate;
TrainState state;
Msp::Time::TimeDelta delay;
int waypoint;
TrainState state;
Msp::Time::TimeDelta delay;
int waypoint;
+ float distance_traveled;
float remaining_estimate;
float remaining_estimate;
+ Msp::Time::TimeDelta wait_time;
int blocked_by;
TrainRoutingState(TrainRoutingInfo &);
int blocked_by;
TrainRoutingState(TrainRoutingInfo &);
struct RoutingStep
{
Msp::Time::TimeDelta time;
struct RoutingStep
{
Msp::Time::TimeDelta time;
- Msp::Time::TimeDelta total_estimate;
+ Msp::Time::TimeDelta cost_estimate;
std::vector<TrainRoutingState> trains;
const RoutingStep *prev;
std::vector<TrainRoutingState> trains;
const RoutingStep *prev;