Python环境下获取并处理音频信号

363 阅读2分钟

我们希望使用Python从连接到插孔的麦克风中获取声音信号,并立即对其进行处理。我们已经明确了处理和后续步骤,但我们却不知道如何从程序中获取信号。对于通道数量,我们并不关注,一个声道就足够了。由于我们不会回放声音,所以声卡上不需要ASIO。我们的问题是:如何使用Python获取Jack音频?

huake_00063_.jpg 2、解决方案 针对上述问题,我们可以选择以下几种解决方案:

方法一:使用PyAudio PyAudio是一个跨平台的Python绑定,允许您录制和播放音频。PyAudio软件包易于安装和使用,并且提供了一个清晰的演示示例,可以帮助您入门。

import pyaudio
import wave

CHUNK = 1024
FORMAT = pyaudio.paInt16
CHANNELS = 2
RATE = 44100
RECORD_SECONDS = 5
WAVE_OUTPUT_FILENAME = "output.wav"

p = pyaudio.PyAudio()

stream = p.open(format=FORMAT,
                channels=CHANNELS,
                rate=RATE,
                input=True,
                frames_per_buffer=CHUNK)

print("* recording")

frames = []

for i in range(0, int(RATE / CHUNK * RECORD_SECONDS)):
    data = stream.read(CHUNK)
    frames.append(data)

print("* done recording")

stream.stop_stream()
stream.close()
p.terminate()

wf = wave.open(WAVE_OUTPUT_FILENAME, 'wb')
wf.setnchannels(CHANNELS)
wf.setsampwidth(p.get_sample_size(FORMAT))
wf.setframerate(RATE)
wf.writeframes(b''.join(frames))
wf.close()

方法二:使用Sounddevice Sounddevice是一个Python库,允许您录制和播放音频。Sounddevice软件包同样易于安装和使用,并且还提供了一个清晰的演示示例,可帮助您入门。

import sounddevice as sd
import numpy as np
import scipy.io.wavfile as wav

fs = 44100
duration = 5  # seconds
myrecording = sd.rec(duration * fs, samplerate=fs, channels=2, dtype='float64')
print "Recording Audio"
sd.wait()
print "Audio recording complete , Play Audio"
sd.play(myrecording, fs)
sd.wait()
print "Play Audio Complete"

方法三:使用Pysox Pysox是一个Python绑定,用于libsox。libsox是一个强大的音频处理库,可用于各种音频操作,包括录制和播放音频。Pysox软件包易于安装和使用,但它不提供清晰的演示示例。

import pysox

rec = pysox.Recorder(samplerate=44100, channels=2, bitdepth=16)
rec.record('output.wav', duration=5)

方法四:使用PyJack PyJack是一个Python绑定,允许您与Jack音频连接服务器交互。Jack是一个低延迟音频服务器,可用于录制和播放音频。PyJack软件包易于安装和使用,但它不提供清晰的演示示例。

import pyjack

client = pyjack.Client('MyClient')
client.register_port('input', pyjack.PortFlags.IS_INPUT | pyjack.PortFlags.IS_TERMINAL)
client.register_port('output', pyjack.PortFlags.IS_OUTPUT | pyjack.PortFlags.IS_TERMINAL)

client.activate()

print(client.get_ports())

input_port = client.get_ports(type=pyjack.PortFlags.IS_INPUT)[0]
output_port = client.get_ports(type=pyjack.PortFlags.IS_OUTPUT)[0]

client.connect(input_port, output_port)

while True:
    data = client.recv(input_port)
    client.send(output_port, data)