Mercurial > hg > midi-score-follower
comparison src/BayesianArrayStructure.cpp @ 9:75dcd1308658
looked at tempo process, likelihood function changed and improved. Now drawing using constrained vector function. Good working version.
author | Andrew N Robertson <andrew.robertson@eecs.qmul.ac.uk> |
---|---|
date | Tue, 23 Aug 2011 11:20:44 +0100 |
parents | 4a8e6a6cd224 |
children | 3f103cf78148 |
comparison
equal
deleted
inserted
replaced
8:d9a3613e7264 | 9:75dcd1308658 |
---|---|
18 prior.createVector(1); | 18 prior.createVector(1); |
19 likelihood.createVector(1); | 19 likelihood.createVector(1); |
20 posterior.createVector(1); | 20 posterior.createVector(1); |
21 | 21 |
22 speedPriorValue = 1.0; | 22 speedPriorValue = 1.0; |
23 speedEstimate = speedPriorValue; | |
23 | 24 |
24 lastEventTime = ofGetElapsedTimeMillis(); | 25 lastEventTime = ofGetElapsedTimeMillis(); |
25 | 26 |
26 /* | 27 /* |
27 tmpPrior.createVector(240); | 28 tmpPrior.createVector(240); |
74 //relativeSpeedPosterior.addToIndex(50, 1); | 75 //relativeSpeedPosterior.addToIndex(50, 1); |
75 relativeSpeedPosterior.renormalise(); | 76 relativeSpeedPosterior.renormalise(); |
76 relativeSpeedPosterior.getMaximum(); | 77 relativeSpeedPosterior.getMaximum(); |
77 | 78 |
78 setSpeedPrior(speedPriorValue); | 79 setSpeedPrior(speedPriorValue); |
80 speedEstimate = speedPriorValue; | |
79 | 81 |
80 prior.zero(); | 82 prior.zero(); |
81 posterior.zero(); | 83 posterior.zero(); |
82 // posterior.offset = - 200; | 84 // posterior.offset = - 200; |
83 // posterior.addGaussianShape(200, 40, 1); | 85 // posterior.addGaussianShape(200, 40, 1); |
202 void BayesianArrayStructure::updateTmpBestEstimate(const double& timeDifference){ | 204 void BayesianArrayStructure::updateTmpBestEstimate(const double& timeDifference){ |
203 //input is the time since the start of playing | 205 //input is the time since the start of playing |
204 | 206 |
205 // double timeDiff = ofGetElapsedTimeMillis() - lastEventTime;//lastBestEstimateUpdateTime; | 207 // double timeDiff = ofGetElapsedTimeMillis() - lastEventTime;//lastBestEstimateUpdateTime; |
206 | 208 |
207 tmpBestEstimate = posterior.getIndexInRealTerms(posterior.MAPestimate) + timeDifference*relativeSpeedPosterior.getIndexInRealTerms(relativeSpeedPosterior.MAPestimate); | 209 tmpBestEstimate = posterior.getIndexInRealTerms(posterior.MAPestimate) + timeDifference*relativeSpeedPosterior.getIndexInRealTerms(relativeSpeedPosterior.integratedEstimate); |
208 // | 210 // |
209 printf("tmp best %f and best %f time diff %f posterior MAP %f at speed %f\n", tmpBestEstimate, bestEstimate, timeDifference, posterior.getIndexInRealTerms(posterior.MAPestimate), relativeSpeedPosterior.getIndexInRealTerms(relativeSpeedPosterior.MAPestimate)); | 211 //printf("tmp best %f and best %f time diff %f posterior MAP %f at speed %f\n", tmpBestEstimate, bestEstimate, timeDifference, posterior.getIndexInRealTerms(posterior.MAPestimate), relativeSpeedPosterior.getIndexInRealTerms(relativeSpeedPosterior.integratedEstimate)); |
210 //lastBestEstimateUpdateTime = ofGetElapsedTimeMillis(); | 212 //lastBestEstimateUpdateTime = ofGetElapsedTimeMillis(); |
211 } | 213 } |
212 | 214 |
213 void BayesianArrayStructure::updateBestEstimate(){ | 215 void BayesianArrayStructure::updateBestEstimate(){ |
214 // double timeDiff = ofGetElapsedTimeMillis() - lastEventTime;// | 216 // double timeDiff = ofGetElapsedTimeMillis() - lastEventTime;// |
215 double timeDiff = ofGetElapsedTimeMillis() - lastBestEstimateUpdateTime; | 217 double timeDiff = ofGetElapsedTimeMillis() - lastBestEstimateUpdateTime; |
216 bestEstimate = posterior.getIndexInRealTerms(posterior.MAPestimate) + timeDiff*relativeSpeedPosterior.getIndexInRealTerms(relativeSpeedPosterior.MAPestimate); | 218 |
219 double speedEstimate = relativeSpeedPosterior.getIntegratedEstimate(); | |
220 speedEstimate = relativeSpeedPosterior.getIndexInRealTerms(speedEstimate); | |
221 //relativeSpeedPosterior.getIndexInRealTerms(relativeSpeedPosterior.MAPestimate) | |
222 bestEstimate = posterior.getIndexInRealTerms(posterior.MAPestimate) + timeDiff*speedEstimate; | |
217 | 223 |
218 // bestEstimate = tmpBestEstimate; | 224 // bestEstimate = tmpBestEstimate; |
219 } | 225 } |
220 | 226 |
221 void BayesianArrayStructure::calculatePosterior(){ | 227 void BayesianArrayStructure::calculatePosterior(){ |
266 | 272 |
267 } | 273 } |
268 | 274 |
269 void BayesianArrayStructure::complexCrossUpdate(const double& timeDifferenceInPositionVectorUnits){ | 275 void BayesianArrayStructure::complexCrossUpdate(const double& timeDifferenceInPositionVectorUnits){ |
270 int distanceMoved, newPriorIndex; | 276 int distanceMoved, newPriorIndex; |
277 | |
278 double speedValue = relativeSpeedPosterior.offset; | |
279 | |
271 for (int i = 0;i < relativeSpeedPosterior.arraySize;i++){ | 280 for (int i = 0;i < relativeSpeedPosterior.arraySize;i++){ |
272 | 281 |
273 double speedValue = relativeSpeedPosterior.getIndexInRealTerms(i);//so for scalar 0.01, 50 -> speed value of 0.5 | 282 // double speedValue = relativeSpeedPosterior.getIndexInRealTerms(i);//so for scalar 0.01, 50 -> speed value of 0.5 |
274 | 283 |
275 //so we have moved | 284 //so we have moved |
276 distanceMoved = round(timeDifferenceInPositionVectorUnits * speedValue);//round the value | 285 distanceMoved = round(timeDifferenceInPositionVectorUnits * speedValue);//round the value |
277 | 286 |
278 if (relativeSpeedPosterior.array[i] != 0){ | 287 if (relativeSpeedPosterior.array[i] != 0){ |
279 double speedContribution = relativeSpeedPosterior.array[i]; | 288 double speedContribution = relativeSpeedPosterior.array[i]; |
280 // printf("speed [%i] gives %f moved %i in %f units \n", i, speedValue, distanceMoved, timeDifferenceInPositionVectorUnits); | 289 // printf("speed [%i] gives %f moved %i in %f units \n", i, speedValue, distanceMoved, timeDifferenceInPositionVectorUnits); |
281 | 290 |
291 newPriorIndex = posterior.offset - prior.offset + distanceMoved; | |
292 | |
282 for (int postIndex = 0;postIndex < posterior.arraySize;postIndex++){ | 293 for (int postIndex = 0;postIndex < posterior.arraySize;postIndex++){ |
283 //old posterior contributing to new prior | 294 //old posterior contributing to new prior |
284 newPriorIndex = postIndex + posterior.offset - prior.offset + distanceMoved; | 295 // newPriorIndex = postIndex + posterior.offset - prior.offset + distanceMoved; |
296 | |
285 if (newPriorIndex >= 0 && newPriorIndex < prior.arraySize){ | 297 if (newPriorIndex >= 0 && newPriorIndex < prior.arraySize){ |
286 prior.addToIndex(newPriorIndex, posterior.array[postIndex]*speedContribution); | 298 prior.addToIndex(newPriorIndex, posterior.array[postIndex]*speedContribution); |
287 } | 299 } |
288 | 300 |
289 } | 301 newPriorIndex++;//optimised code - the commented line above explains how this works |
302 }//end for | |
303 | |
290 | 304 |
291 }//if not zero | 305 }//if not zero |
306 speedValue += relativeSpeedPosterior.scalar; | |
307 //optimised line | |
308 //as we wanted: | |
309 // double speedValue = relativeSpeedPosterior.getIndexInRealTerms(i);//so for scalar 0.01, 50 -> speed value of 0.5 | |
292 }//end speed | 310 }//end speed |
293 } | 311 } |
294 | 312 |
295 | 313 |
296 | 314 |
297 void BayesianArrayStructure::translateByMaximumSpeed(const double& timeDifferenceInPositionVectorUnits){ | 315 void BayesianArrayStructure::translateByMaximumSpeed(const double& timeDifferenceInPositionVectorUnits){ |
316 | |
298 int distanceMoved, newPriorIndex; | 317 int distanceMoved, newPriorIndex; |
299 | 318 |
300 | 319 double speedValue = relativeSpeedPosterior.getIndexInRealTerms(relativeSpeedPosterior.integratedEstimate); |
301 double speedValue = relativeSpeedPosterior.getIndexInRealTerms(relativeSpeedPosterior.MAPestimate);//using max value only | |
302 //so for scalar 0.01, 50 -> speed value of 0.5 | 320 //so for scalar 0.01, 50 -> speed value of 0.5 |
303 double speedContribution = relativeSpeedPosterior.array[relativeSpeedPosterior.MAPestimate]; | 321 double speedContribution = relativeSpeedPosterior.array[relativeSpeedPosterior.integratedEstimate]; |
304 //so we have moved | 322 //so we have moved |
305 distanceMoved = round(timeDifferenceInPositionVectorUnits * speedValue);//round the value | 323 distanceMoved = round(timeDifferenceInPositionVectorUnits * speedValue);//round the value |
306 // printf("speed [%i] gives %f moved %i in %f units \n", i, speedValue, distanceMoved, timeDifferenceInPositionVectorUnits); | 324 // printf("speed [%i] gives %f moved %i in %f units \n", i, speedValue, distanceMoved, timeDifferenceInPositionVectorUnits); |
307 | 325 |
308 for (int postIndex = 0;postIndex < posterior.arraySize;postIndex++){ | 326 for (int postIndex = 0;postIndex < posterior.arraySize;postIndex++){ |
342 relativeSpeedPosterior.copyFromDynamicVector(tmpPosteriorForStorage); | 360 relativeSpeedPosterior.copyFromDynamicVector(tmpPosteriorForStorage); |
343 } | 361 } |
344 | 362 |
345 void BayesianArrayStructure::calculateNewPriorOffset(const double& timeDifference){ | 363 void BayesianArrayStructure::calculateNewPriorOffset(const double& timeDifference){ |
346 | 364 |
347 double maxSpeed = relativeSpeedPosterior.getIndexInRealTerms(relativeSpeedPosterior.MAPestimate); | 365 double maxSpeed = relativeSpeedPosterior.getIndexInRealTerms(relativeSpeedPosterior.integratedEstimate); |
348 // printf("Maxspeed is %f\n", maxSpeed); | 366 // printf("Maxspeed is %f\n", maxSpeed); |
349 | 367 |
350 double priorMax = posterior.getMaximum(); | 368 double priorMax = posterior.getMaximum(); |
351 double distanceTravelled = maxSpeed * (timeDifference / prior.scalar); | 369 double distanceTravelled = maxSpeed * (timeDifference / prior.scalar); |
352 double newMaxLocation = posterior.MAPestimate + distanceTravelled; | 370 double newMaxLocation = posterior.MAPestimate + distanceTravelled; |
360 // commented for the moment | 378 // commented for the moment |
361 double relativeAmount = max(1.0, timeDifference/1000.); | 379 double relativeAmount = max(1.0, timeDifference/1000.); |
362 // printf("decay %f around %i \n", timeDifference, relativeSpeedPosterior.MAPestimate); | 380 // printf("decay %f around %i \n", timeDifference, relativeSpeedPosterior.MAPestimate); |
363 relativeAmount *= speedDecayAmount; | 381 relativeAmount *= speedDecayAmount; |
364 relativeSpeedPosterior.renormalise(); | 382 relativeSpeedPosterior.renormalise(); |
365 relativeSpeedPosterior.addGaussianShape(relativeSpeedPosterior.MAPestimate, speedDecayWidth, relativeAmount); | 383 relativeSpeedPosterior.addGaussianShape(relativeSpeedPosterior.integratedEstimate, speedDecayWidth, relativeAmount); |
366 | 384 |
367 relativeSpeedPosterior.renormalise(); | 385 relativeSpeedPosterior.renormalise(); |
368 double newMax = relativeSpeedPosterior.getMaximum(); | 386 double newMax = relativeSpeedPosterior.getMaximum(); |
369 | 387 |
370 //old code | 388 //old code |
382 | 400 |
383 | 401 |
384 | 402 |
385 } | 403 } |
386 | 404 |
387 void BayesianArrayStructure::updateTempoDistribution(const double& speedRatio, const double& matchFactor){ | 405 void BayesianArrayStructure::setLikelihoodToConstant(){ |
406 //set new likelihood | |
407 relativeSpeedLikelihood.zero(); | |
408 relativeSpeedLikelihood.addConstant(speedLikelihoodNoise); | |
409 } | |
410 | |
411 | |
412 void BayesianArrayStructure::updateTempoLikelihood(const double& speedRatio, const double& matchFactor){ | |
413 | |
388 //speedratio is speed of played relative to the recording | 414 //speedratio is speed of played relative to the recording |
389 | 415 |
390 double index = relativeSpeedLikelihood.getRealTermsAsIndex(speedRatio); | 416 double index = relativeSpeedLikelihood.getRealTermsAsIndex(speedRatio); |
391 // printf("\nindex of likelihood would be %f\n", index); | 417 // printf("index of likelihood would be %f for ratio %f\n", index, speedRatio); |
392 if (index >= 0 && index < relativeSpeedPrior.length){ | 418 if (index >= 0 && index < relativeSpeedPrior.length){ |
393 //then we can do update | 419 relativeSpeedLikelihood.addGaussianShape(index , 5, matchFactor); |
394 | 420 } |
395 //set new likelihood | 421 } |
396 relativeSpeedLikelihood.zero(); | 422 |
397 relativeSpeedLikelihood.addConstant(speedLikelihoodNoise); | 423 |
398 | 424 void BayesianArrayStructure::updateTempoDistribution(){ |
399 relativeSpeedLikelihood.addGaussianShape(index , 5, 0.5*matchFactor); | |
400 | |
401 | 425 |
402 //copy posterior to prior | 426 //copy posterior to prior |
403 relativeSpeedPrior.copyFromDynamicVector(relativeSpeedPosterior); | 427 relativeSpeedPrior.copyFromDynamicVector(relativeSpeedPosterior); |
404 | 428 |
405 //update | 429 //update |
407 | 431 |
408 //normalise | 432 //normalise |
409 relativeSpeedPosterior.renormalise(); | 433 relativeSpeedPosterior.renormalise(); |
410 | 434 |
411 relativeSpeedPosterior.getMaximum(); | 435 relativeSpeedPosterior.getMaximum(); |
412 }//end if within range | 436 |
413 | 437 relativeSpeedPosterior.updateIntegratedEstimate(); |
414 | 438 speedEstimate = relativeSpeedPosterior.getIndexInRealTerms(relativeSpeedPosterior.integratedEstimate); |
415 } | |
416 | |
417 | |
418 void BayesianArrayStructure::setFlatTempoLikelihood(){ //set new likelihood | |
419 relativeSpeedLikelihood.zero(); | |
420 relativeSpeedLikelihood.addConstant(0.3); | |
421 } | |
422 | |
423 void BayesianArrayStructure::updateTempoLikelihood(const double& speedRatio, const double& matchFactor){ | |
424 | |
425 double index = relativeSpeedLikelihood.getRealTermsAsIndex(speedRatio); | |
426 | |
427 if (index >= 0 && index < relativeSpeedPrior.length){ | |
428 relativeSpeedLikelihood.addGaussianShape(index , 5, 0.5);//*matchFactor); | |
429 } | |
430 } | 439 } |
431 | 440 |
432 | 441 |
433 void BayesianArrayStructure::calculateTempoUpdate(){ | 442 void BayesianArrayStructure::calculateTempoUpdate(){ |
434 //copy posterior to prior | 443 //copy posterior to prior |
464 | 473 |
465 } | 474 } |
466 | 475 |
467 | 476 |
468 void BayesianArrayStructure::drawTempoArrays(){ | 477 void BayesianArrayStructure::drawTempoArrays(){ |
469 ofSetColor(0,255,255); | 478 ofSetColor(0,0,255); |
470 relativeSpeedPrior.drawVector(0, relativeSpeedPrior.arraySize); | 479 // relativeSpeedPrior.drawVector(0, relativeSpeedPrior.arraySize); |
471 | 480 |
472 ofSetColor(255,0,255); | 481 ofSetColor(255,0,255); |
473 relativeSpeedLikelihood.drawVector(0, relativeSpeedLikelihood.arraySize); | 482 relativeSpeedLikelihood.drawVector(0, relativeSpeedLikelihood.arraySize); |
474 | 483 // relativeSpeedLikelihood.drawConstrainedVector(0, 199, 0, 1000);// relativeSpeedLikelihood.arraySize); |
475 ofSetColor(255,255,0); | 484 ofSetColor(255,0,0); |
476 relativeSpeedPosterior.drawVector(0, relativeSpeedPosterior.arraySize); | 485 relativeSpeedPosterior.drawVector(0, relativeSpeedPosterior.arraySize); |
477 | 486 |
478 ofSetColor(0,0,255); | 487 // ofSetColor(0,0,255); |
479 tmpPosteriorForStorage.drawVector(0, tmpPosteriorForStorage.arraySize); | 488 // tmpPosteriorForStorage.drawVector(0, tmpPosteriorForStorage.arraySize); |
480 | 489 |
481 ofSetColor(255,255, 255); | 490 ofSetColor(255,255, 255); |
482 ofLine(screenWidth/2, 0, screenWidth/2, ofGetHeight());//middle of screen | 491 ofLine(screenWidth/2, 0, screenWidth/2, ofGetHeight());//middle of screen |
483 | 492 |
484 ofSetColor(0, 255, 0); | 493 ofSetColor(155,255, 0); |
485 double fractionOfScreen = ((double)relativeSpeedPosterior.MAPestimate / relativeSpeedPosterior.length); | 494 double fractionOfScreen = ((double)relativeSpeedPosterior.integratedEstimate / relativeSpeedPosterior.length); |
486 ofLine(screenWidth * fractionOfScreen, 0, screenWidth * fractionOfScreen, ofGetHeight()); | 495 ofLine(screenWidth * fractionOfScreen, 0, screenWidth * fractionOfScreen, ofGetHeight()); |
487 } | 496 } |
488 | 497 |
489 | 498 |
490 void BayesianArrayStructure::drawArraysRelativeToTimeframe(const double& startTimeMillis, const double& endTimeMillis){ | 499 void BayesianArrayStructure::drawArraysRelativeToTimeframe(const double& startTimeMillis, const double& endTimeMillis){ |
533 | 542 |
534 | 543 |
535 } | 544 } |
536 | 545 |
537 } | 546 } |
547 | |
548 | |
549 /* | |
550 | |
551 void BayesianArrayStructure::updateTempoDistribution(const double& speedRatio, const double& matchFactor){ | |
552 //speedratio is speed of played relative to the recording | |
553 | |
554 double index = relativeSpeedLikelihood.getRealTermsAsIndex(speedRatio); | |
555 // printf("\nindex of likelihood would be %f\n", index); | |
556 if (index >= 0 && index < relativeSpeedPrior.length){ | |
557 //then we can do update | |
558 | |
559 //set new likelihood | |
560 relativeSpeedLikelihood.zero(); | |
561 relativeSpeedLikelihood.addConstant(speedLikelihoodNoise); | |
562 | |
563 relativeSpeedLikelihood.addGaussianShape(index , 5, 0.5*matchFactor); | |
564 | |
565 | |
566 //copy posterior to prior | |
567 relativeSpeedPrior.copyFromDynamicVector(relativeSpeedPosterior); | |
568 | |
569 //update | |
570 relativeSpeedPosterior.doProduct(relativeSpeedPrior, relativeSpeedLikelihood); | |
571 | |
572 //normalise | |
573 relativeSpeedPosterior.renormalise(); | |
574 | |
575 relativeSpeedPosterior.getMaximum(); | |
576 }//end if within range | |
577 | |
578 | |
579 } | |
580 | |
581 */ |