如何使用 Python 从 USB 音频设备获取 24 位样本?

How to get 24-bit samples from USB audio device using Python?

我正在尝试使用 Python 从某些 USB 音频设备获取 24 位音频样本流。 我已经搜索了一些解决方案,发现 this 线程正在使用格式为 pyaudio.paInt24 的 PyAudio 流,不幸的是我仍然有 16 位样本。我尝试使用 PyAudio 流进行录制并使用 WAVE 进行保存,示例代码:

    def initialize(self):
        self.p = pyaudio.PyAudio()

        self.stream = self.p.open(format=self.format,            # pyaudio.paInt24
                                  channels=self.channels,        # 1
                                  rate=self.fs,                  # 16000
                                  input=True,
                                  input_device_index=self.input_device_index,
                                  frames_per_buffer=self.chunk)  # 1024

    def run(self):

        frames = []

        for _ in range(0, int(self.fs / self.chunk * self.duration)):
            data = self.stream.read(self.chunk)
            frames.append(data)

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

        # write recording to a WAV file
        wf = wave.open(self.recorded_file, 'wb')
        wf.setnchannels(self.channels)
        wf.setsampwidth(self.p.get_sample_size(self.format))
        wf.setframerate(self.fs)
        wf.writeframes(b''.join(frames))
        wf.close()

我也尝试了同样的SoundDevice,示例代码:

    def initialize(self):
        sd.default.samplerate = self.fs         # 16000
        sd.default.channels   = self.channels   # 1
        sd.default.device     = self.input_device_index

    def run(self):

        data = sd.rec(int(self.duration * self.fs), dtype=np.int32)
        sd.wait()

        # Save file
        wf = wave.open(self.recorded_file, 'wb')
        wf.setnchannels(self.channels)
        wf.setsampwidth(3)
        wf.setframerate(self.fs)
        wf.writeframes(b''.join(data))

为了确保问题发生在接收样本时而不是在保存样本时,我确保 24 位音频文件确实可以用 WAVE 保存,使用此示例代码:

import wave
with wave.open(path_to_file_to_read, mode='rb') as rb:
    white_noise = rb.readframes(rb.getframerate())

    with wave.open(path_to_file_to_save+'_save_with_wave.wav', mode='wb') as wb:
        wb.setnchannels(rb.getnchannels())
        wb.setsampwidth(rb.getsampwidth())
        wb.setnframes(rb.getnframes())
        wb.setframerate(rb.getframerate())
        wb.writeframesraw(white_noise)

此外,我在录制完成后立即设置了一个断点,以查看录制的样本,我看到它看起来像 16 位: 我会注意到,为了确保 USB 音频设备确实向我发送了 24 位样本,我使用 Audacity 进行了录音,实际上我得到了 24 位,出于某种原因我可以不要对 Python.

做任何类似的事情

有没有使用Python代码记录24位样本的简单方法?

PyAudioSoundDevice 在某些 windows 声音之间使用 portaudio 绑定体系结构和 python。 PortAudio 不支持全深度 24 位,结果是 16 位音频加上额外的 8 个零位。 声卡 支持 24 位 - https://soundcard.readthedocs.io/en/latest/

为了获得真正的 24 位样本,您可以使用以下方法:

import soundcard as sc
import soundfile as sf

FS = 16000
TIME_IN_SEC = 5
FRAMES = FS * TIME_IN_SEC
DEVICE_NAME = 'default'
FILE_PATH = 'abc.wav'    

# get device
audio_device = sc.get_microphone(DEVICE_NAME)

# receive samples
data = audio_device.record(samplerate=FS, numframes=FRAMES)
    
# write recording to a WAV file
sf.write(FILE_PATH, data, FS, subtype='PCM_24')