[f98063b] | 1 | #! /usr/bin/env python |
---|
| 2 | |
---|
| 3 | import numpy as np |
---|
| 4 | from aubio import pitch |
---|
| 5 | import pylab as plt |
---|
| 6 | |
---|
| 7 | buf_size = 2048 * 1 |
---|
| 8 | hop_size = buf_size // 4 |
---|
| 9 | |
---|
| 10 | samplerate = 44100 |
---|
| 11 | minfreq = 40 |
---|
| 12 | maxfreq = 6000 |
---|
| 13 | |
---|
| 14 | def sinewave(freq, duration, samplerate = samplerate): |
---|
| 15 | """ generate a sinewave """ |
---|
| 16 | length = hop_size |
---|
| 17 | while length < duration * samplerate: |
---|
| 18 | length += hop_size |
---|
| 19 | return np.sin( 2. * np.pi * np.arange(length) * freq / samplerate ).astype("float32") |
---|
| 20 | |
---|
| 21 | def get_stats_for_pitch_method(method, freqs, samplerate = samplerate): |
---|
| 22 | """ for a given pitch method and a list of frequency, generate a sinewave |
---|
| 23 | and get mean deviation """ |
---|
| 24 | means = np.zeros(len(freqs)) |
---|
| 25 | medians = np.zeros(len(freqs)) |
---|
| 26 | for freq, fn in zip(freqs, range(len(freqs))): |
---|
| 27 | s = sinewave(freq, .50).reshape(-1, hop_size) |
---|
| 28 | #s = (sinewave(freq, .50) + .0*sinewave(freq/2., .50)).reshape(-1, hop_size) |
---|
| 29 | p = pitch(method, buf_size, hop_size, samplerate = samplerate) |
---|
| 30 | candidates = np.zeros(len(s)) |
---|
| 31 | #samples = np.zeros(buf_size) |
---|
| 32 | for frame, i in zip(s, range(len(s))): |
---|
| 33 | candidates[i] = p(frame)[0] |
---|
| 34 | # skip first few candidates |
---|
| 35 | candidates = candidates[4:] |
---|
| 36 | means[fn] = np.mean(candidates[candidates != 0] - freq) |
---|
| 37 | medians[fn] = np.median(candidates[candidates != 0] - freq) |
---|
| 38 | print (freq, means[fn], medians[fn]) |
---|
| 39 | return means, medians |
---|
| 40 | |
---|
| 41 | if __name__ == '__main__': |
---|
| 42 | freqs = np.arange(minfreq, maxfreq, 1.) |
---|
| 43 | modes = ["yin", "yinfft"] |
---|
| 44 | for mode in modes: |
---|
| 45 | means, medians = get_stats_for_pitch_method(mode, freqs) |
---|
| 46 | plt.figure() |
---|
| 47 | plt.plot(freqs, means, 'g-') |
---|
| 48 | plt.plot(freqs, medians, 'r--') |
---|
| 49 | #plt.savefig(mode + '_deviations_test.png', dpi=300) |
---|
| 50 | plt.show() |
---|