|  | 91 |  | 
                          |  | 92 |  | 
                          |  | 93 |  | 
                          |  | 94 | /******************************** | 
                          |  | 95 | * KOD PRO TrafficAgentCycleTime * | 
                          |  | 96 | *********************************/ | 
                          |  | 97 | double last_queue; | 
                          |  | 98 | double sum_queue_length; | 
                          |  | 99 | double last_sum_queue_length; | 
                          |  | 100 | double queue_diff_sum; | 
                          |  | 101 | double queue_variance_sum; | 
                          |  | 102 | int n_of_queues_in_length; | 
                          |  | 103 | int last_n_of_queues_in_length; | 
                          |  | 104 | double last_variance; | 
                          |  | 105 | double green_time_ratio; | 
                          |  | 106 | double Tc; | 
                          |  | 107 | double last_Tc; | 
                          |  | 108 | double saturated_stream; | 
                          |  | 109 | double delta; // ztratovy cas pri prechodu na zelenou | 
                          |  | 110 | // udaje opro kalmana | 
                          |  | 111 | double queue_avg; //  pruner | 
                          |  | 112 | double queue_w;   //  vaha | 
                          |  | 113 | double queue_d;   //  rozptyl | 
                          |  | 114 | double queue_dd;  //  snizeni verohodnosti odhadu | 
                          |  | 115 | double queue_r;   //  neduveryhodnost mereni = 1 | 
                          |  | 116 |  | 
                          |  | 117 | double Ro_avg;  //  prumer | 
                          |  | 118 | double Ro_w;    //  vaha K | 
                          |  | 119 | double Ro_d;            //  rozptyl P | 
                          |  | 120 | double Ro_dd;           //  snizeni verohodnosti odhadu Q | 
                          |  | 121 | double Ro_r;            //  neduveryhodnost mereni = 1 R | 
                          |  | 122 |  | 
                          |  | 123 | double last_queue_avg; | 
                          |  | 124 |  | 
                          |  | 125 | // pomocne funkce | 
                          |  | 126 |  | 
                          |  | 127 |  | 
                          |  | 128 |  | 
                          |  | 129 | void init () { | 
                          |  | 130 | last_Tc = 0; | 
                          |  | 131 | saturated_stream = 0.5; | 
                          |  | 132 | queue = 0; | 
                          |  | 133 | sum_queue_length = 0; | 
                          |  | 134 | last_sum_queue_length = 0; | 
                          |  | 135 | n_of_queues_in_length = 0; | 
                          |  | 136 | last_n_of_queues_in_length = 0; | 
                          |  | 137 | queue_diff_sum = 0; | 
                          |  | 138 | queue_variance_sum = 0; | 
                          |  | 139 | last_variance = 0; | 
                          |  | 140 | delta = 5; | 
                          |  | 141 | // KALMAN | 
                          |  | 142 | queue_avg = 0;  //  prumer | 
                          |  | 143 | queue_w = 1;    //  vaha K | 
                          |  | 144 | queue_d = 0.9;          //  rozptyl P | 
                          |  | 145 | queue_dd =0.1;          //  snizeni verohodnosti odhadu Q | 
                          |  | 146 | queue_r = 9;            //  neduveryhodnost mereni = 1 R | 
                          |  | 147 |  | 
                          |  | 148 | Ro_avg = 0;     //  prumer | 
                          |  | 149 | Ro_w = 1;       //  vaha K | 
                          |  | 150 | Ro_d = 0.9;             //  rozptyl P | 
                          |  | 151 | Ro_dd =0.1;             //  snizeni verohodnosti odhadu Q | 
                          |  | 152 | Ro_r = 9;               //  neduveryhodnost mereni = 1 R | 
                          |  | 153 |  | 
                          |  | 154 | last_queue_avg = 0; | 
                          |  | 155 | } | 
                          |  | 156 |  | 
                          |  | 157 | /*double abs ( double x ) { | 
                          |  | 158 | if ( x > 0 ) return x; | 
                          |  | 159 | else return -x; | 
                          |  | 160 | }*/ | 
                          |  | 161 |  | 
                          |  | 162 | void echo () { | 
                          |  | 163 | //cout << "n:" << n_of_queues_in_length << " " << getQueueName() << " q:" << getQueue() << " aq:" << getAverageQueueLength() << " diff:" << getAverageQueueGrow() << " D:" << getQueueVariance() << endl; | 
                          |  | 164 | /*cout << "n:" << n_of_queues_in_length | 
                          |  | 165 | << " " << getQueueName() | 
                          |  | 166 | << "LAST aq:" << last_sum_queue_length/last_n_of_queues_in_length | 
                          |  | 167 | << " aq:" << getAverageQueueLength() | 
                          |  | 168 | << " diff" <<  getAverageQueueLength() - last_sum_queue_length/last_n_of_queues_in_length | 
                          |  | 169 | << endl;*/ | 
                          |  | 170 | cout << getQueueName(); | 
                          |  | 171 | /*if ( last_n_of_queues_in_length> 0 && n_of_queues_in_length > 0 ) | 
                          |  | 172 | cout << " DIFF: " << getAverageQueueLength() - last_sum_queue_length/last_n_of_queues_in_length; | 
                          |  | 173 | else | 
                          |  | 174 | cout << " no diff available";*/ | 
                          |  | 175 | //cout << "\tn " << n_of_queues_in_length; | 
                          |  | 176 | //cout << " prijizdejicich aut za 90: " << getRo()*90; | 
                          |  | 177 | cout << "\tgtr: " << green_time_ratio; | 
                          |  | 178 | cout << "\tRo: " << getRo(); | 
                          |  | 179 | cout << "\tC: " << green_time_ratio*Tc*saturated_stream - getRo()*Tc << endl; | 
                          |  | 180 | //cout << "\tWT:"; | 
                          |  | 181 | for ( int i = -2; i <= 2; i++ ) { | 
                          |  | 182 | double tc = Tc + i*8; | 
                          |  | 183 | cout << tc << "\t"; | 
                          |  | 184 | } | 
                          |  | 185 | cout << endl; | 
                          |  | 186 | for ( int i = -2; i <= 2; i++ ) { | 
                          |  | 187 | double tc = Tc + i*8; | 
                          |  | 188 | cout << (int)(100*getWT(tc)) << "\t"; | 
                          |  | 189 | } | 
                          |  | 190 | //cout << " diff: " << getRo()*Tc - saturated_stream*getGreenTime(); | 
                          |  | 191 | /*if ( saturated_stream*getGreenTime() >= getAverageQueueLength() ) | 
                          |  | 192 | cout << " projede vsechno "; | 
                          |  | 193 | else | 
                          |  | 194 | cout << " zustanou auta ";*/ | 
                          |  | 195 | cout << endl << endl; | 
                          |  | 196 | } | 
                          |  | 197 |  | 
                          |  | 198 |  | 
                          |  | 199 | Lane getLane () { | 
                          |  | 200 | return lane; | 
                          |  | 201 | } | 
                          |  | 202 |  | 
                          |  | 203 | string getSG () { | 
                          |  | 204 | return lane.sg; | 
                          |  | 205 | } | 
                          |  | 206 |  | 
                          |  | 207 | string getQueueName () { | 
                          |  | 208 | return lane.queue; | 
                          |  | 209 | } | 
                          |  | 210 |  | 
                          |  | 211 | double getQueue() { | 
                          |  | 212 | return queue_avg; | 
                          |  | 213 | } | 
                          |  | 214 |  | 
                          |  | 215 | void addQueueLength ( int ql ) { | 
                          |  | 216 | // pricita pouze namerene udaje | 
                          |  | 217 | if ( ql >= 0 ) { | 
                          |  | 218 | last_queue = queue; | 
                          |  | 219 | queue = ql; | 
                          |  | 220 | queue_diff_sum += queue - last_queue; | 
                          |  | 221 | //queue_variance_sum += abs(queue - last_queue); | 
                          |  | 222 |  | 
                          |  | 223 | sum_queue_length += ql; | 
                          |  | 224 | n_of_queues_in_length ++; | 
                          |  | 225 | // KALMAN | 
                          |  | 226 | cout << endl << "pridani fronty\t" << queue_avg << "\t" << ql << endl; | 
                          |  | 227 | queue_avg += queue_w*( ql - queue_avg ); | 
                          |  | 228 | queue_d += queue_dd; | 
                          |  | 229 | queue_w = queue_d/(queue_d+1); | 
                          |  | 230 | queue_d = (1-queue_w)*queue_d; | 
                          |  | 231 |  | 
                          |  | 232 | double Ro = getActualRo(); | 
                          |  | 233 | Ro_avg += Ro_w*( Ro - Ro_avg ); | 
                          |  | 234 | Ro_d += Ro_dd; | 
                          |  | 235 | Ro_w = Ro_d/(Ro_d+1); | 
                          |  | 236 | Ro_d = (1-Ro_w)*Ro_d; | 
                          |  | 237 | } | 
                          |  | 238 | } | 
                          |  | 239 |  | 
                          |  | 240 | void resetQueue () { | 
                          |  | 241 | last_Tc = Tc; | 
                          |  | 242 | //last_variance = getQueueVariance(); | 
                          |  | 243 | last_n_of_queues_in_length = n_of_queues_in_length; | 
                          |  | 244 | last_sum_queue_length = sum_queue_length; | 
                          |  | 245 | n_of_queues_in_length = 0; | 
                          |  | 246 | sum_queue_length = 0; | 
                          |  | 247 | queue_variance_sum = 0; | 
                          |  | 248 | queue_diff_sum = 0; | 
                          |  | 249 | // kalman | 
                          |  | 250 | last_queue_avg = getAverageQueueLength(); | 
                          |  | 251 | } | 
                          |  | 252 |  | 
                          |  | 253 | double getAverageQueueLength () { | 
                          |  | 254 | // kalmam | 
                          |  | 255 | return queue_avg; | 
                          |  | 256 |  | 
                          |  | 257 | if( n_of_queues_in_length > 0 ) | 
                          |  | 258 | return sum_queue_length / n_of_queues_in_length; | 
                          |  | 259 | else | 
                          |  | 260 | return 0.0; | 
                          |  | 261 | } | 
                          |  | 262 |  | 
                          |  | 263 | double getLastAverageQueueLength () { | 
                          |  | 264 | if( last_n_of_queues_in_length > 0 ) | 
                          |  | 265 | return last_sum_queue_length / last_n_of_queues_in_length; | 
                          |  | 266 | else | 
                          |  | 267 | return 0.0; | 
                          |  | 268 | } | 
                          |  | 269 |  | 
                          |  | 270 | /*double getAverageQueueGrow () { | 
                          |  | 271 | return queue_diff_sum / n_of_queues_in_length; | 
                          |  | 272 | }*/ | 
                          |  | 273 |  | 
                          |  | 274 | /*double getQueueVariance () { | 
                          |  | 275 | return queue_variance_sum / n_of_queues_in_length; | 
                          |  | 276 | }*/ | 
                          |  | 277 |  | 
                          |  | 278 | double getGreenTime ( double tc ) { return green_time_ratio * tc - delta; } | 
                          |  | 279 | double getGreenTime () { return getGreenTime( Tc ); } | 
                          |  | 280 |  | 
                          |  | 281 | double getRedTime ( double tc ) { return (1-green_time_ratio) * tc;     } | 
                          |  | 282 | double getRedTime () { return getRedTime( Tc ); } | 
                          |  | 283 |  | 
                          |  | 284 | double getRelativeQueueDiff () { | 
                          |  | 285 | if ( last_n_of_queues_in_length > 0 && n_of_queues_in_length > 0 ) { | 
                          |  | 286 |  | 
                          |  | 287 | return getAverageQueueLength()/(Tc*(1-green_time_ratio)) - (last_sum_queue_length/last_n_of_queues_in_length)/(last_Tc*(1-green_time_ratio)); | 
                          |  | 288 | } | 
                          |  | 289 | else | 
                          |  | 290 | return 0; | 
                          |  | 291 | } | 
                          |  | 292 |  | 
                          |  | 293 | // hodnotici funkce - suma cekaciho casu aut za 10h | 
                          |  | 294 | double getWT ( double  Tc ) { | 
                          |  | 295 | double T = 36000; // celkovy cas 10h | 
                          |  | 296 | double Ro = getRo(); | 
                          |  | 297 | double Gr = green_time_ratio; | 
                          |  | 298 | double ss = saturated_stream; | 
                          |  | 299 | double WT = 0; | 
                          |  | 300 | double q = 0;  // zacina s nulovou frontou ? | 
                          |  | 301 | double ti = 0; | 
                          |  | 302 | double sumq = q; | 
                          |  | 303 | while ( ti < T ) { | 
                          |  | 304 | // ve fronte stoji vic aut nez je schopno odjet za zelenou | 
                          |  | 305 | if ( q > 0.5*ss*Tc ) { | 
                          |  | 306 | WT += 0.5*ss*(Tc*Gr - delta)*(Tc*Gr - delta); | 
                          |  | 307 | } | 
                          |  | 308 | else { | 
                          |  | 309 |  | 
                          |  | 310 | WT += 0.5*q*(Tc*Gr - delta); | 
                          |  | 311 | } | 
                          |  | 312 |  | 
                          |  | 313 | if ( (Tc*Gr - delta)*ss < q ) | 
                          |  | 314 | q -= (Tc*Gr - delta)*ss; | 
                          |  | 315 | else | 
                          |  | 316 | q = 0; | 
                          |  | 317 |  | 
                          |  | 318 | WT += q * Tc; // zbytek fronty ceka cely cyklus | 
                          |  | 319 | // cekani vozidel, ktera prijela za pocitany cyklus | 
                          |  | 320 | if ( q > 0 ) { | 
                          |  | 321 | //pokud je fronta > 0, auta cekaji prumerne polovinu delky cyklu | 
                          |  | 322 | WT += Ro*Tc*0.5*Tc; | 
                          |  | 323 | } | 
                          |  | 324 | else { | 
                          |  | 325 | // pokud je fronta = 0 cekaji pouze auta, ktera prijela na cervenou (p=(1-Gr)) 0.5Tc(1-Gr) | 
                          |  | 326 | WT += Ro*(1-Gr)*Tc*0.5*(1-Gr)*Tc; | 
                          |  | 327 | } | 
                          |  | 328 | // fronta se zvetsi o Ro*Tc | 
                          |  | 329 | q += Ro*Tc; | 
                          |  | 330 | sumq += Ro*Tc; | 
                          |  | 331 | ti += Tc; | 
                          |  | 332 | } | 
                          |  | 333 |  | 
                          |  | 334 | //return WT; | 
                          |  | 335 | if ( sumq > 0 ) | 
                          |  | 336 | return 100*(WT/(0.5*T*sumq)); | 
                          |  | 337 | else | 
                          |  | 338 | return 0; | 
                          |  | 339 | } | 
                          |  | 340 |  | 
                          |  | 341 | //double getWT ( double  tc ) { | 
                          |  | 342 | //      double T = ; | 
                          |  | 343 | //      double WT = 0; | 
                          |  | 344 | //      double cWT = 0; | 
                          |  | 345 | //      double q = 0; | 
                          |  | 346 | //      double cq = 0; | 
                          |  | 347 | //      double sum_t; | 
                          |  | 348 | //      double car_part = 0.1; | 
                          |  | 349 | //      double Ro = getRo(); | 
                          |  | 350 | //      double dt = car_part/Ro; | 
                          |  | 351 | //      while ( sum_t < T ) { | 
                          |  | 352 | //              if ( q < 0 ) | 
                          |  | 353 | //                      q = 0; | 
                          |  | 354 | //              WT += q * dt; | 
                          |  | 355 | //              // prirustek fronty za dt | 
                          |  | 356 | //              q += car_part; | 
                          |  | 357 | //              // zelena - auta projedou | 
                          |  | 358 | //              if ( (sum_t - tc*(int)(sum_t/tc)) > delta && ) | 
                          |  | 359 | //                      q -= saturated_stream*dt; | 
                          |  | 360 | //              sum_t += dt; | 
                          |  | 361 | //      } | 
                          |  | 362 | //} | 
                          |  | 363 | // Odhad hustoty ( auto/sec ) | 
                          |  | 364 | double getActualRo () { | 
                          |  | 365 | // pokud delka fronty mensi nez pocet aut ktere odjedou za zelenou | 
                          |  | 366 | if ( saturated_stream*getGreenTime() >= getAverageQueueLength() ) { | 
                          |  | 367 | // pocet aut, ktera prijela pri cervene | 
                          |  | 368 | return getAverageQueueLength()/getRedTime(); | 
                          |  | 369 | } | 
                          |  | 370 | else { | 
                          |  | 371 | //fronta se nevynuluje | 
                          |  | 372 | // pocet aut = to co stihlo projet na zelenou + o co narostla fronta | 
                          |  | 373 | // doba pocet_cyklu*90 | 
                          |  | 374 | //double T = n_of_queues_in_length*90; | 
                          |  | 375 | //double cars_per_green = T*(getGreenTime()/Tc)*saturated_stream; | 
                          |  | 376 | //return (cars_per_green + queue_diff_sum)/T; | 
                          |  | 377 | double T = 90; | 
                          |  | 378 | double cars_per_green = T*(getGreenTime()/Tc)*saturated_stream; | 
                          |  | 379 | return (cars_per_green + (getLastAverageQueueLength()-getAverageQueueLength()))/T; | 
                          |  | 380 | } | 
                          |  | 381 | } | 
                          |  | 382 |  | 
                          |  | 383 | double getRo() { | 
                          |  | 384 | return Ro_avg; | 
                          |  | 385 | } | 
                          |  | 386 |  | 
                          |  | 387 |  | 
                          |  | 388 |  | 
                          |  | 389 | /*************************************** | 
                          |  | 390 | * KONEC KODU PRO TrafficAgentCycleTime * | 
                          |  | 391 | ****************************************/ |