View Javadoc
1   package org.opentrafficsim.road.gtu.lane.tactical.lmrs;
2   
3   import java.util.SortedSet;
4   
5   import org.djunits.value.vdouble.scalar.Length;
6   import org.djunits.value.vdouble.scalar.Speed;
7   import org.opentrafficsim.core.gtu.behavioralcharacteristics.BehavioralCharacteristics;
8   import org.opentrafficsim.core.gtu.behavioralcharacteristics.ParameterException;
9   import org.opentrafficsim.core.gtu.perception.EgoPerception;
10  import org.opentrafficsim.core.gtu.plan.operational.OperationalPlanException;
11  import org.opentrafficsim.core.network.LateralDirectionality;
12  import org.opentrafficsim.road.gtu.lane.perception.LanePerception;
13  import org.opentrafficsim.road.gtu.lane.perception.RelativeLane;
14  import org.opentrafficsim.road.gtu.lane.perception.categories.InfrastructurePerception;
15  import org.opentrafficsim.road.gtu.lane.perception.categories.NeighborsPerception;
16  import org.opentrafficsim.road.gtu.lane.perception.headway.HeadwayGTU;
17  import org.opentrafficsim.road.gtu.lane.tactical.following.CarFollowingModel;
18  import org.opentrafficsim.road.gtu.lane.tactical.util.CarFollowingUtil;
19  import org.opentrafficsim.road.gtu.lane.tactical.util.lmrs.Desire;
20  import org.opentrafficsim.road.gtu.lane.tactical.util.lmrs.LmrsParameters;
21  import org.opentrafficsim.road.gtu.lane.tactical.util.lmrs.VoluntaryIncentive;
22  
23  /**
24   * Determines desire out of hierarchal courtesy. For right-hand driving this is towards the right if the follower has a higher
25   * desired speed. If the left follower has a higher desired speed, a negative desire towards the left exists. For left-hand
26   * driving it is the other way around. Hierarchal desire depends on the level of hierarchal courtesy.
27   * <p>
28   * Copyright (c) 2013-2017 Delft University of Technology, PO Box 5, 2600 AA, Delft, the Netherlands. All rights reserved. <br>
29   * BSD-style license. See <a href="http://opentrafficsim.org/docs/current/license.html">OpenTrafficSim License</a>.
30   * <p>
31   * @version $Revision$, $LastChangedDate$, by $Author$, initial version Apr 13, 2016 <br>
32   * @author <a href="http://www.transport.citg.tudelft.nl">Wouter Schakel</a>
33   */
34  // TODO keep left or right rules
35  public class IncentiveHierarchal implements VoluntaryIncentive
36  {
37  
38      /** {@inheritDoc} */
39      @Override
40      public final Desire determineDesire(final BehavioralCharacteristics behavioralCharacteristics,
41              final LanePerception perception, final CarFollowingModel carFollowingModel, final Desire mandatoryDesire,
42              final Desire voluntaryDesire) throws ParameterException, OperationalPlanException
43      {
44          double dLeft = 0;
45          double dRight = 0;
46          double hierarchy = behavioralCharacteristics.getParameter(LmrsParameters.HIERARCHY);
47          NeighborsPerception neighbors = perception.getPerceptionCategory(NeighborsPerception.class);
48          Speed vDes = carFollowingModel.desiredSpeed(behavioralCharacteristics,
49                  perception.getPerceptionCategory(InfrastructurePerception.class).getSpeedLimitProspect(RelativeLane.CURRENT)
50                          .getSpeedLimitInfo(Length.ZERO));
51          Speed ownSpeed = perception.getPerceptionCategory(EgoPerception.class).getSpeed();
52          InfrastructurePerception infra = perception.getPerceptionCategory(InfrastructurePerception.class);
53          boolean leftLane = infra.getLegalLaneChangePossibility(RelativeLane.CURRENT, LateralDirectionality.LEFT).si > 0.0;
54          boolean rightLane = infra.getLegalLaneChangePossibility(RelativeLane.CURRENT, LateralDirectionality.RIGHT).si > 0.0;
55          // change right to get out of the way
56          if (rightLane && mandatoryDesire.getRight() >= 0.0)
57          {
58              SortedSet<HeadwayGTU> followers = neighbors.getFollowers(RelativeLane.CURRENT);
59              if (!followers.isEmpty())
60              {
61                  HeadwayGTU follower = followers.first();
62                  Speed vDesFollower = follower.getCarFollowingModel().desiredSpeed(follower.getBehavioralCharacteristics(),
63                          follower.getSpeedLimitInfo());
64                  if (vDes.lt(vDesFollower)
65                          && CarFollowingUtil
66                                  .followSingleLeader(follower.getCarFollowingModel(), follower.getBehavioralCharacteristics(),
67                                          follower.getSpeed(), follower.getSpeedLimitInfo(), follower.getDistance(), ownSpeed)
68                                  .le0())
69                  {
70                      dRight = hierarchy;
71                  }
72              }
73          }
74          // stay right to keep out of the way
75          if (leftLane && mandatoryDesire.getLeft() <= 0.0)
76          {
77              SortedSet<HeadwayGTU> followers = neighbors.getFollowers(RelativeLane.LEFT);
78              if (followers != null && !followers.isEmpty())
79              {
80                  HeadwayGTU follower = followers.first();
81                  Speed vDesFollower = follower.getCarFollowingModel().desiredSpeed(follower.getBehavioralCharacteristics(),
82                          follower.getSpeedLimitInfo());
83                  if (vDes.lt(vDesFollower)
84                          && CarFollowingUtil
85                                  .followSingleLeader(follower.getCarFollowingModel(), follower.getBehavioralCharacteristics(),
86                                          follower.getSpeed(), follower.getSpeedLimitInfo(), follower.getDistance(), ownSpeed)
87                                  .le0())
88                  {
89                      dLeft = -hierarchy;
90                  }
91              }
92          }
93          return new Desire(dLeft, dRight);
94      }
95  
96      /** {@inheritDoc} */
97      @Override
98      public final String toString()
99      {
100         return "IncentiveHierarchal";
101     }
102 
103 }