I need to change the x-axis on this graph from 'samples' to time: enter image description here

I created the graph using this process:

y, _ = librosa.load('sound/data/kea-song.mp3', 48000)
y /= y.max()

# compute the rmse
e = librosa.feature.rmse(y=y)[0]
e -= e.min()#what does this really do, guessing a kind of normalisation?
e /= e.max()

I know the whole len(e)/sr=time formula but I cant actually apply it to the graph. I try this:

plt.plot(len(y)/48000, e)

But I have np.shape issues:

ValueError: x and y must have same first dimension, but have shapes (1,) and (5846,)

How do I do this?

Edit: I tried to do it using both of these (with error's afterwards):

plt.plot(y/48000, e)
ValueError: x and y must have same first dimension, but have shapes (2993006,) and (5846,)

plt.plot(e/48000, e)



plt.plot(np.arange(len(y))/48000, e)
ValueError: x and y must have same first dimension, but have shapes (2993006,) and (5846,)

plt.plot(np.arange(len(e))/48000, e) ended up with a graph with one vertical line down the middle.

-dear everyone this is what happens when you try do this with little background knowledge of the subject. Do your math homework!


You're getting an error because the two inputs to plt.plot need to be the same length. Notice that len(y)/48000 is just a number, so python tells us it of length 1.

Try plt.plot(range(len(e))/ 48000, e) **. What this does is change the values of your x axis to correspond to real time. If the sampling rate is $48000 \textrm{Hz}$, this means that $\textrm{sample}=1$ on your current axis now corresponds to 1/48000 of a second in the new axis, as this is the amount of time required to get one sample. Extend this to the whole axis - the time value on the new $x-$axis is simply the amount of time needed to take $y$ samples.

** if range() doesnt work, try numpy.arange() instead

Also, yes, these two lines

e -= e.min()
e /= e.max()

correspond to first shifting the signal so that its minimum value is now at 0, then dividing by the max. This is just a normalization, as you guessed.

  • $\begingroup$ Hey goldrik cheers for the help. But it doesn't seem to work: I've tried it both using plt.plot(y/48000, e) and plt.plot(e/48000, e). Ill update my main question to explain $\endgroup$ Nov 10 '17 at 10:23
  • $\begingroup$ Ahh, I realized my mistake. We have to specify the new axis here. Recreate the original axis using range (if range() doesnt work, try numpy.arange() instead), which is just a sequence from 0 to len(y). THEN we should do the division to get it in terms of real time. $\endgroup$
    – goldrik
    Nov 10 '17 at 10:32
  • $\begingroup$ Sorry, I meant len(e) here. $\endgroup$
    – goldrik
    Nov 10 '17 at 10:56
  • $\begingroup$ Didn't work again. About to go to bed. Thanks for the help man. $\endgroup$ Nov 10 '17 at 11:17

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.