annotate src/MatchFeatureFeeder.cpp @ 246:aac9ad4064ea subsequence tip

Fix incorrect handling of silent tail in the non-subsequence MATCH phase; some debug output changes
author Chris Cannam
date Fri, 24 Jul 2020 14:29:55 +0100
parents 39fe8728e1ca
children
rev   line source
cannam@0 1 /* -*- c-basic-offset: 4 indent-tabs-mode: nil -*- vi:set ts=8 sts=4 sw=4: */
cannam@0 2
cannam@0 3 /*
cannam@0 4 Vamp feature extraction plugin using the MATCH audio alignment
cannam@0 5 algorithm.
cannam@0 6
cannam@0 7 Centre for Digital Music, Queen Mary, University of London.
Chris@236 8 Copyright (c) 2007-2020 Simon Dixon, Chris Cannam, and Queen Mary
Chris@230 9 University of London, Copyright (c) 2014-2015 Tido GmbH.
cannam@0 10
cannam@0 11 This program is free software; you can redistribute it and/or
cannam@0 12 modify it under the terms of the GNU General Public License as
cannam@0 13 published by the Free Software Foundation; either version 2 of the
cannam@0 14 License, or (at your option) any later version. See the file
cannam@0 15 COPYING included with this distribution for more information.
cannam@0 16 */
cannam@0 17
Chris@24 18 #include "MatchFeatureFeeder.h"
cannam@0 19
Chris@14 20 using std::vector;
Chris@235 21 using std::cerr;
Chris@235 22 using std::endl;
Chris@14 23
Chris@24 24 MatchFeatureFeeder::MatchFeatureFeeder(Matcher *m1, Matcher *m2) :
Chris@167 25 m_pm1(m1),
Chris@167 26 m_pm2(m2),
Chris@167 27 m_finder(m_pm1)
cannam@0 28 {
cannam@0 29 }
cannam@0 30
Chris@24 31 MatchFeatureFeeder::~MatchFeatureFeeder()
cannam@0 32 {
cannam@0 33 }
cannam@0 34
Chris@154 35 void
Chris@183 36 MatchFeatureFeeder::feed(feature_t f1, feature_t f2)
cannam@0 37 {
Chris@49 38 // We maintain two FIFO queues of feature vectors, one per input
Chris@49 39 // stream. When the match-feeder function is entered, it knows
Chris@49 40 // that it has at least one feature in each queue. It loops,
Chris@49 41 // processing up to one feature per matcher, until a queue is
Chris@49 42 // empty. Then it returns, to be called again with more data.
Chris@49 43
Chris@60 44 if (!f1.empty()) {
Chris@74 45 m_q1.push(f1);
Chris@60 46 }
Chris@60 47
Chris@60 48 if (!f2.empty()) {
Chris@74 49 m_q2.push(f2);
Chris@60 50 }
Chris@14 51
Chris@74 52 while (!m_q1.empty() && !m_q2.empty()) {
Chris@63 53 feedBlock();
Chris@63 54 }
Chris@63 55 }
Chris@63 56
Chris@167 57 int
Chris@167 58 MatchFeatureFeeder::getEstimatedReferenceFrame()
Chris@167 59 {
Chris@167 60 if (m_pm1->getFrameCount() == 0 || m_pm2->getFrameCount() == 0) {
Chris@167 61 return 0;
Chris@167 62 }
Chris@167 63 int bestRow = 0;
Chris@191 64 normpathcost_t bestCost = 0;
Chris@167 65 if (!m_finder.getBestColCost(m_pm2->getFrameCount()-1, bestRow, bestCost)) {
Chris@167 66 return -1;
Chris@167 67 } else {
Chris@167 68 return bestRow;
Chris@167 69 }
Chris@167 70 }
Chris@167 71
Chris@63 72 void
Chris@63 73 MatchFeatureFeeder::finish()
Chris@63 74 {
Chris@74 75 while (!m_q1.empty() || !m_q2.empty()) {
Chris@24 76 feedBlock();
Chris@14 77 }
Chris@200 78
Chris@200 79 // cerr << "MatchFeatureFeeder::finish: have " << m_pm1->getFrameCount()
Chris@200 80 // << " reference and " << m_pm2->getFrameCount() << " other frames"
Chris@200 81 // << endl;
Chris@14 82 }
Chris@14 83
Chris@24 84 void
Chris@24 85 MatchFeatureFeeder::feedBlock()
Chris@14 86 {
Chris@74 87 if (m_q1.empty()) { // ended
Chris@60 88 feed2();
Chris@74 89 } else if (m_q2.empty()) { // ended
Chris@60 90 feed1();
Chris@171 91 } else if (m_pm1->isFillingInitialBlock()) {
Chris@24 92 feed1();
Chris@24 93 feed2();
Chris@78 94 } else if (m_pm1->isOverrunning()) { // slope constraints
Chris@24 95 feed2();
Chris@78 96 } else if (m_pm2->isOverrunning()) {
Chris@24 97 feed1();
cannam@0 98 } else {
Chris@171 99 switch (m_finder.getExpandDirection()) {
Chris@181 100 case AdvanceThis:
Chris@24 101 feed1();
cannam@0 102 break;
Chris@181 103 case AdvanceOther:
Chris@24 104 feed2();
cannam@0 105 break;
Chris@181 106 case AdvanceBoth:
Chris@24 107 feed1();
Chris@24 108 feed2();
cannam@0 109 break;
Chris@181 110 case AdvanceNone:
Chris@74 111 cerr << "m_finder says AdvanceNone!" << endl;
Chris@45 112 break;
cannam@0 113 }
cannam@0 114 }
Chris@135 115
Chris@135 116 m_fpx.push_back(m_pm2->getFrameCount());
Chris@135 117 m_fpy.push_back(m_pm1->getFrameCount());
cannam@0 118 }
cannam@0 119
Chris@24 120 void
Chris@24 121 MatchFeatureFeeder::feed1()
cannam@0 122 {
Chris@74 123 m_pm1->consumeFeatureVector(m_q1.front());
Chris@74 124 m_q1.pop();
cannam@0 125 }
cannam@0 126
Chris@24 127 void
Chris@24 128 MatchFeatureFeeder::feed2()
cannam@0 129 {
Chris@74 130 m_pm2->consumeFeatureVector(m_q2.front());
Chris@74 131 m_q2.pop();
cannam@0 132 }
cannam@0 133