| 114 | |
| 115 | |
| 116 | bool MFCC::ApplyMelFilterBank( |
| 117 | std::vector<float>& fftVec, |
| 118 | std::vector<std::vector<float>>& melFilterBank, |
| 119 | std::vector<uint32_t>& filterBankFilterFirst, |
| 120 | std::vector<uint32_t>& filterBankFilterLast, |
| 121 | std::vector<float>& melEnergies) |
| 122 | { |
| 123 | const size_t numBanks = melEnergies.size(); |
| 124 | |
| 125 | if (numBanks != filterBankFilterFirst.size() || |
| 126 | numBanks != filterBankFilterLast.size()) |
| 127 | { |
| 128 | printf("unexpected filter bank lengths\n"); |
| 129 | return false; |
| 130 | } |
| 131 | |
| 132 | for (size_t bin = 0; bin < numBanks; ++bin) |
| 133 | { |
| 134 | auto filterBankIter = melFilterBank[bin].begin(); |
| 135 | auto end = melFilterBank[bin].end(); |
| 136 | float melEnergy = FLT_MIN; /* Avoid log of zero at later stages */ |
| 137 | const uint32_t firstIndex = filterBankFilterFirst[bin]; |
| 138 | const uint32_t lastIndex = std::min<uint32_t>(filterBankFilterLast[bin], fftVec.size() - 1); |
| 139 | |
| 140 | for (uint32_t i = firstIndex; i <= lastIndex && filterBankIter != end; i++) |
| 141 | { |
| 142 | float energyRep = sqrt(fftVec[i]); |
| 143 | melEnergy += (*filterBankIter++ * energyRep); |
| 144 | } |
| 145 | |
| 146 | melEnergies[bin] = melEnergy; |
| 147 | } |
| 148 | |
| 149 | return true; |
| 150 | } |
| 151 | |
| 152 | void MFCC::ConvertToLogarithmicScale(std::vector<float>& melEnergies) |
| 153 | { |
no test coverage detected