1 package org.opentrafficsim.road.gtu.lane.tactical.util.lmrs;
2
3 import static org.opentrafficsim.road.gtu.lane.tactical.util.lmrs.GapAcceptance.egoAcceleration;
4
5 import org.djunits.unit.AccelerationUnit;
6 import org.djunits.value.vdouble.scalar.Acceleration;
7 import org.djunits.value.vdouble.scalar.Speed;
8 import org.opentrafficsim.base.parameters.ParameterException;
9 import org.opentrafficsim.base.parameters.ParameterTypes;
10 import org.opentrafficsim.base.parameters.Parameters;
11 import org.opentrafficsim.core.gtu.plan.operational.OperationalPlanException;
12 import org.opentrafficsim.core.network.LateralDirectionality;
13 import org.opentrafficsim.road.gtu.lane.perception.LanePerception;
14 import org.opentrafficsim.road.gtu.lane.perception.categories.NeighborsPerception;
15 import org.opentrafficsim.road.gtu.lane.perception.headway.HeadwayGTU;
16 import org.opentrafficsim.road.gtu.lane.tactical.following.CarFollowingModel;
17 import org.opentrafficsim.road.network.speed.SpeedLimitInfo;
18
19
20
21
22
23
24
25
26
27
28
29
30 public interface GapAcceptance
31 {
32
33
34 GapAcceptance INFORMED = new GapAcceptance()
35 {
36
37 @Override
38 public boolean acceptGap(final LanePerception perception, final Parameters params, final SpeedLimitInfo sli,
39 final CarFollowingModel cfm, final double desire, final Speed ownSpeed, final Acceleration ownAcceleration,
40 final LateralDirectionality lat) throws ParameterException, OperationalPlanException
41 {
42 NeighborsPerception neighbors = perception.getPerceptionCategory(NeighborsPerception.class);
43 if (neighbors.isGtuAlongside(lat))
44 {
45
46 return false;
47 }
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63 Acceleration b = params.getParameter(ParameterTypes.B);
64 Acceleration aFollow = new Acceleration(Double.POSITIVE_INFINITY, AccelerationUnit.SI);
65 for (HeadwayGTU follower : neighbors.getFirstFollowers(lat))
66 {
67 if (follower.getSpeed().gt0() || follower.getAcceleration().gt0())
68 {
69 Acceleration a = LmrsUtil.singleAcceleration(follower.getDistance(), follower.getSpeed(), ownSpeed, desire,
70 follower.getParameters(), follower.getSpeedLimitInfo(), follower.getCarFollowingModel());
71 aFollow = Acceleration.min(aFollow, a);
72 }
73 }
74
75 Acceleration aSelf = egoAcceleration(perception, params, sli, cfm, desire, ownSpeed, lat);
76 Acceleration threshold = b.multiplyBy(-desire);
77 return aFollow.ge(threshold) && aSelf.ge(threshold) && ownAcceleration.ge(threshold);
78 }
79
80
81 @Override
82 public String toString()
83 {
84 return "INFORMED";
85 }
86
87 };
88
89
90 GapAcceptance EGO_HEADWAY = new GapAcceptance()
91 {
92
93 @Override
94 public boolean acceptGap(final LanePerception perception, final Parameters params, final SpeedLimitInfo sli,
95 final CarFollowingModel cfm, final double desire, final Speed ownSpeed, final Acceleration ownAcceleration,
96 final LateralDirectionality lat) throws ParameterException, OperationalPlanException
97 {
98 NeighborsPerception neigbors = perception.getPerceptionCategory(NeighborsPerception.class);
99 if (neigbors.isGtuAlongside(lat))
100 {
101
102 return false;
103 }
104
105 Acceleration b = params.getParameter(ParameterTypes.B);
106 Acceleration aFollow = new Acceleration(Double.POSITIVE_INFINITY, AccelerationUnit.SI);
107 for (HeadwayGTU follower : neigbors.getFirstFollowers(lat))
108 {
109 if (follower.getSpeed().gt0() || follower.getAcceleration().gt0())
110 {
111
112 Parameters folParams = follower.getParameters();
113 folParams.setParameterResettable(ParameterTypes.TMIN, params.getParameter(ParameterTypes.TMIN));
114 folParams.setParameterResettable(ParameterTypes.TMAX, params.getParameter(ParameterTypes.TMAX));
115 Acceleration a = LmrsUtil.singleAcceleration(follower.getDistance(), follower.getSpeed(), ownSpeed, desire,
116 folParams, follower.getSpeedLimitInfo(), follower.getCarFollowingModel());
117 aFollow = Acceleration.min(aFollow, a);
118 folParams.resetParameter(ParameterTypes.TMIN);
119 folParams.resetParameter(ParameterTypes.TMAX);
120 }
121 }
122
123 Acceleration aSelf = egoAcceleration(perception, params, sli, cfm, desire, ownSpeed, lat);
124 Acceleration threshold = b.multiplyBy(-desire);
125 return aFollow.ge(threshold) && aSelf.ge(threshold);
126 }
127
128
129 @Override
130 public String toString()
131 {
132 return "EGO_HEADWAY";
133 }
134
135 };
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150 static Acceleration egoAcceleration(final LanePerception perception, final Parameters params, final SpeedLimitInfo sli,
151 final CarFollowingModel cfm, final double desire, final Speed ownSpeed, final LateralDirectionality lat)
152 throws ParameterException, OperationalPlanException
153 {
154 Acceleration aSelf = new Acceleration(Double.POSITIVE_INFINITY, AccelerationUnit.SI);
155 if (ownSpeed.gt0())
156 {
157 for (
158
159 HeadwayGTU leader : perception.getPerceptionCategory(NeighborsPerception.class).getFirstLeaders(lat))
160 {
161 Acceleration a = LmrsUtil.singleAcceleration(leader.getDistance(), ownSpeed, leader.getSpeed(), desire, params,
162 sli, cfm);
163 aSelf = Acceleration.min(aSelf, a);
164 }
165 }
166 return aSelf;
167 }
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183 boolean acceptGap(LanePerception perception, Parameters params, SpeedLimitInfo sli, CarFollowingModel cfm, double desire,
184 Speed ownSpeed, Acceleration ownAcceleration, LateralDirectionality lat)
185 throws ParameterException, OperationalPlanException;
186
187 }