-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathRunner.java
More file actions
351 lines (324 loc) · 11.1 KB
/
Copy pathRunner.java
File metadata and controls
351 lines (324 loc) · 11.1 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
import java.util.Arrays;
import java.util.Random;
public class Runner {
private int swimDistance;
private int bikeSumDistance;
private int runSumDistance;
public String classname;
private double swimspeed;
private double runspeed;
private double bikespeed;
public double position;
private double t1time;
private double t2time;
public double nextTravel; //How much the runner will travel in the next step
private int t1count; //How many steps the runner stays at transition 1
private int t2count; //How many steps the runner stays at transition 2
//ORIGINAL VALUES
private double forwardTime = 2; //How long in the future do runners consider for density
private double lloDensityRun = 1.5; //What Density of people/m do we start getting slowdown (assuming 20 foot wide road)
private double lloDensitySwim = 0.75;
private double lloDensityBike = 0.75;
private double uloDensityRun = 6; //What Density of people/m do can we not traverse (assuming 20 foot wide road))
private double uloDensitySwim = 3;
private double uloDensityBike = 3;
private double step; //Length of time between updates
/* Halved Densitys
private double lloDensityRun = 0.8; //What Density of people/m do we start getting slowdown (assuming 20 foot wide road)
private double lloDensitySwim = 0.4;
private double lloDensityBike = 0.4;
private double uloDensityRun = 3; //What Density of people/m do can we not traverse (assuming 20 foot wide road))
private double uloDensitySwim = 1.5;
private double uloDensityBike = 1.5;
private int step; //Length of time between updates
*/
private int stepNumber;
private int expectedStepNumber;
//Need to add timers and shit in order to measure the time spent and the distance lost in congestion yeah...
Random rand = new Random();
public Runner(String classnamer, double steplength, int swimDistances, int bikeSumDistances, int runSumDistances){ //Initializes all the speed variables and transition times randomly based on class average and standard deviation
swimDistance = swimDistances;
bikeSumDistance = bikeSumDistances;
runSumDistance = runSumDistances;
double d1, d2, d3, d4, d5, d6, d7, d8, d9, d10;
classname = classnamer;
if(classname.equalsIgnoreCase("ATH")){
d1 = 1404.9375;
d2 = 210.132092;
d3 = 697.96875;
d4 = 215.3605239;
d5 = 6539.03125;
d6 = 1143.254168;
d7 = 270.875;
d8 = 110.5202894;
d9 = 4645.536875;
d10 = 823.6366583;
/* //NO VARIANCE
d1 = 1404.9375;
d2 = 0;
d3 = 697.96875;
d4 = 0;
d5 = 6539.03125;
d6 = 0;
d7 = 270.875;
d8 = 0;
d9 = 4645.536875;
d10 = 0;
*/
}
else if(classname.equalsIgnoreCase("CLY")){
d1 = 1537.616667;
d2 = 228.0364073;
d3 = 482.6666667;
d4 = 190.4020016;
d5 = 5296.25;
d6 = 766.3613296;
d7 = 208.05;
d8 = 126.4455647;
d9 = 4280.767167;
d10 = 817.0947949;
}
else if(classname.equalsIgnoreCase("FOPEN")){
d1 = 1349.106904;
d2 = 201.2769749;
d3 = 601.8674833;
d4 = 206.066424;
d5 = 5897.638085;
d6 = 892.6504087;
d7 = 222.045657;
d8 = 122.5521167;
d9 = 3741.610457;
d10 = 704.0984312;
}
else if(classname.equalsIgnoreCase("FPREMIER")){
d1 = 1021.777778;
d2 = 81.42928463;
d3 = 297.1111111;
d4 = 37.01784688;
d5 = 4576.222222;
d6 = 268.4895106;
d7 = 86.33333333;
d8 = 27.95432783;
d9 = 2647.816111;
d10 = 218.4670151;
}
else if(classname.equalsIgnoreCase("FPRO")){
d1 = 778.1666667;
d2 = 19.59946144;
d3 = 218.1666667;
d4 = 9.06305075;
d5 = 4058;
d6 = 133.0776716;
d7 = 54.83333333;
d8 = 8.091490729;
d9 = 2298.666667;
d10 = 108.6549073;
}
else if(classname.equalsIgnoreCase("MOPEN")){
d1 = 1400.34653;
d2 = 256.449216;
d3 = 457.5328365;
d4 = 180.2161519;
d5 = 5090.950163;
d6 = 699.3881369;
d7 = 180.4415463;
d8 = 90.73903324;
d9 = 3559.92463;
d10 = 694.8203805;
}
else if(classname.equalsIgnoreCase("MPREMIER")){
d1 = 1000.306122;
d2 = 84.67662475;
d3 = 263.755102;
d4 = 33.19609678;
d5 = 4117.734694;
d6 = 279.7328008;
d7 = 75.32653061;
d8 = 19.16351524;
d9 = 2384.832857;
d10 = 209.4799308;
}
else{
d1 = 788.4285714;
d2 = 67.8293176;
d3 = 196.1428571;
d4 = 18.63505584;
d5 = 3730.428571;
d6 = 162.3451853;
d7 = 51.42857143;
d8 = 4.92391084;
d9 = 2119.714286;
d10 = 103.3022117;
}
double swimtime = rand.nextGaussian()*d2+d1;
swimspeed = 1500 / swimtime;
t1time = rand.nextGaussian()*d4+d3;
if(t1time < 0){
t1time = 0;
}
t1count = (int)Math.round(t1time/step);
double biketime = rand.nextGaussian()*d6+d5;
bikespeed = 40000 / biketime;
t2time = rand.nextGaussian()*d8+d7;
if(t2time < 0){
t2time = 0;
}
t2count = (int)Math.round(t2time/step);
double runtime = rand.nextGaussian()*d10+d9;
runspeed = 10000 / runtime;
step = steplength;
expectedStepNumber = 1 + t1count + t2count + (int)(swimDistance/(swimspeed*step) + 1) + (int)((bikeSumDistance - swimDistance)/(bikespeed*step) + 1) + (int)((runSumDistance - bikeSumDistance)/(runspeed*step) + 1);
}
public double getBikeSpeed(){
return bikespeed;
}
public double getRunSpeed(){
return runspeed;
}
public double getSwimSpeed(){
return swimspeed;
}
public void printStats(){
System.out.println("Group:\t" + classname + "\nSwim speed:\t" + swimspeed + "\nBike speed:\t" + bikespeed + "\nRun speed:\t" + runspeed + "\nPosition:\t" + position);
}
//Calculate how far this will move in the next step, stores and returns it. If at a transition, remains stationary but decreases number of the step count by 1. If finished, returns -1
public double calcTravel(double[][]runners){
double travelDistance = -1;
if(position < swimDistance){
double speed = Math.min(swimspeed,maxCongestionSpeed(runners));
travelDistance = Math.min(step*speed, swimDistance-position);
}
else if(swimDistance < position && position < bikeSumDistance){
double speed = Math.min(bikespeed,maxCongestionSpeed(runners));
travelDistance = Math.min(step*speed, bikeSumDistance-position);
}
else if(bikeSumDistance < position && position < runSumDistance){
double speed = Math.min(runspeed,maxCongestionSpeed(runners));
travelDistance = Math.min(step*speed, runSumDistance-position);
}
else if(position == swimDistance){
if(t1count > 0){
t1count--;
travelDistance = 0;
}
else{
double speed = Math.min(bikespeed,maxCongestionSpeed(runners));
travelDistance = Math.min(step*speed, bikeSumDistance-position);
}
}
else if(position == bikeSumDistance){
if(t2count > 0){
t2count--;
travelDistance = 0;
}
else{
double speed = Math.min(runspeed,maxCongestionSpeed(runners));
travelDistance = Math.min(step*speed, runSumDistance-position);
}
}
nextTravel = travelDistance;
return travelDistance;
}
//Advances the position of the runner
public void timestep(){
position += nextTravel;
stepNumber++;
}
//calculates the maximum speed a runner can travel given the congestion, relates to average running speed of those in front of them.
/*private double maxCongestionSpeed(double[][]runners){
double[]temp = runnerDensitySpeed(runners);
double density = temp[0];
double avgvelocity = temp[1];
double maxSpeed = 100;
if(position > runSumDistance && position < runSumDistance){
maxSpeed = avgvelocity + 3.9;
if(density < uloDensityRun && density > lloDensityRun){
maxSpeed = avgvelocity + 3.9 * Math.pow((uloDensityRun-density)/(uloDensityRun-lloDensityRun),2);
}
else if (density >= uloDensityRun){
maxSpeed = avgvelocity;
}
}
else if(position <= runSumDistance){
maxSpeed = avgvelocity + 1.7;
if(density < uloDensitySwim && density > lloDensitySwim){
maxSpeed = avgvelocity + 1.7 * Math.pow((uloDensitySwim-density)/(uloDensitySwim-lloDensitySwim),2);
}
else if (density >= uloDensitySwim){
maxSpeed = avgvelocity;
}
}
else if(position > runSumDistance && position < runSumDistance){
maxSpeed = avgvelocity + 9;
if(density < uloDensityBike && density > lloDensityBike){
maxSpeed = avgvelocity + 9 * Math.pow((uloDensityBike-density)/(uloDensityBike-lloDensityBike),2);
}
else if (density >= uloDensityBike){
maxSpeed = avgvelocity;
}
}
return maxSpeed;
}*/
//returns the density of runners and their average speed in the step seconds in front of the runner. Runners lists all runners' positions and run speeds.
public double maxCongestionSpeed(double[][]runners){
double scanningDistance = 0;
int discardedRunners = 0;
int maxRunners = 0;
double maxSpeed = 0;
if(position < swimDistance){
scanningDistance = Math.min(forwardTime * swimspeed, swimDistance-position);
discardedRunners = (int) (scanningDistance*lloDensitySwim+0.5);
maxRunners = (int) (scanningDistance*uloDensitySwim+0.5);
maxSpeed = swimspeed;
}
else if(position >= swimDistance && position < bikeSumDistance){
scanningDistance = Math.min(forwardTime * bikespeed, bikeSumDistance-position);
discardedRunners = (int) (scanningDistance*lloDensityBike+0.5);
maxRunners = (int) (scanningDistance*uloDensityBike+0.5);
maxSpeed = bikespeed;
}
else if(position >= bikeSumDistance && position < runSumDistance){
scanningDistance = Math.min(forwardTime * runspeed, runSumDistance-position);
discardedRunners = (int) (scanningDistance*lloDensityRun+0.5);
maxRunners = (int) (scanningDistance*uloDensityRun+0.5);
maxSpeed = runspeed;
}
int runnerCounter = 0;
for(int counter = 0; counter < runners.length; counter++){
if (runners[counter][0] > position && runners[counter][0] < position + scanningDistance){
runnerCounter ++;
}
}
if(discardedRunners >= Math.min(maxRunners, runnerCounter)){
return maxSpeed;
}
double[]speeds = new double[runnerCounter];
int runnerCounterCounter = 0;
for(int counter = 0; runnerCounterCounter < runnerCounter; counter++){
if (runners[counter][0] > position && runners[counter][0] < position + scanningDistance){
speeds[runnerCounterCounter] = runners[counter][1];
runnerCounterCounter++;
}
}
double[]toBeAveraged = new double[maxRunners-discardedRunners];
for(int index = 0; index < maxRunners-discardedRunners; index++){
toBeAveraged[index] = maxSpeed;
}
Arrays.sort(speeds);
for(int index = discardedRunners; index < Math.min(runnerCounter, maxRunners); index++){
toBeAveraged[index-discardedRunners] = Math.min(speeds[index],maxSpeed);
}
double speedCounter = 0;
for(int index = 0; index < maxRunners-discardedRunners; index++){
speedCounter += toBeAveraged[index];
}
return speedCounter/(maxRunners-discardedRunners);
}
//returns the difference between the number of expected steps with no congestion and the number of steps with it.
public int getStepNumber(){
return stepNumber;
}
public int stepDifference(){
return stepNumber-expectedStepNumber;
}
}