What is the easiest way to read wav-files using Python [summary]?

Roman picture Roman · Jan 14, 2010 · Viewed 30.3k times · Source

I want to use Python to access a wav-file and write its content in a form which allows me to analyze it (let's say arrays).

  1. I heard that "audiolab" is a suitable tool for that (it transforms numpy arrays into wav and vica versa).
  2. I have installed the "audiolab" but I had a problem with the version of numpy (I could not "from numpy.testing import Tester"). I had 1.1.1. version of numpy.
  3. I have installed a newer version on numpy (1.4.0). But then I got a new set of errors:

    Traceback (most recent call last): File "test.py", line 7, in import scikits.audiolab File "/usr/lib/python2.5/site-packages/scikits/audiolab/init.py", line 25, in from pysndfile import formatinfo, sndfile File "/usr/lib/python2.5/site-packages/scikits/audiolab/pysndfile/init.py", line 1, in from _sndfile import Sndfile, Format, available_file_formats, available_encodings File "numpy.pxd", line 30, in scikits.audiolab.pysndfile._sndfile (scikits/audiolab/pysndfile/_sndfile.c:9632) ValueError: numpy.dtype does not appear to be the correct type object

  4. I gave up to use audiolab and thought that I can use "wave" package to read in a wav-file. I asked a question about that but people recommended to use scipy instead. OK, I decided to focus on scipy (I have 0.6.0. version).

  5. But when I tried to do the following:

    from scipy.io import wavfile
    x = wavfile.read('/usr/share/sounds/purple/receive.wav')

I get the following:

Traceback (most recent call last):
  File "test3.py", line 4, in <module>
    from scipy.io import wavfile
  File "/usr/lib/python2.5/site-packages/scipy/io/__init__.py", line 23, in <module>
    from numpy.testing import NumpyTest
ImportError: cannot import name NumpyTest
  1. So, I gave up to use scipy. Can I use just wave package? I do not need much. I just need to have content of wav-file in human readable format and than I will figure out what to do with that.

Answer

James Roth picture James Roth · Apr 8, 2010

Have you tried the wave module? It has fewer dependencies:

http://docs.python.org/library/wave.html

def everyOther (v, offset=0):
   return [v[i] for i in range(offset, len(v), 2)]

def wavLoad (fname):
   wav = wave.open (fname, "r")
   (nchannels, sampwidth, framerate, nframes, comptype, compname) = wav.getparams ()
   frames = wav.readframes (nframes * nchannels)
   out = struct.unpack_from ("%dh" % nframes * nchannels, frames)

   # Convert 2 channles to numpy arrays
   if nchannels == 2:
       left = array (list (everyOther (out, 0)))
       right = array (list  (everyOther (out, 1)))
   else:
       left = array (out)
       right = left