【Dual-Path-RNN-Pytorch源码分析】AudioReader

理解AudioReader类:从SCP文件加载与处理音频
AudioReader是一个用于读取SCP文件中音频路径并使用torchaudio加载音频数据的工具类。SCP文件存储的是音频文件及其路径,如1.wav/local/file/path/1.wav等。AudioReader通过torchaudio.load读取音频,处理采样率不匹配问题,并以字典形式组织数据,支持通过文件名或索引访问。当遇到torchaudio无法加载音频时,可能是缺少合适的backend,如在Windows上需安装SoundFile。此外,提供了读写wav文件的辅助函数。该类设计简洁,方便音频处理任务的调用。
部署运行你感兴趣的模型镜像

AudioReader 是Dual-Path-RNN-Pytorch源码中用来读入scp文件的工具类,它的输入是一个scp文件的全路径。

有关scp文件,它是一个文件与文件路径的记录文件。 内容样例如下

1.wav  /local/file/path/1.wav
2.wav  /local/file/path/2.wav
3.wav  /local/file/path/3.wav
4.wav  /local/file/path/4.wav
5.wav  /local/file/path/5.wav
6.wav  /local/file/path/6.wav

AudioReader 通过torchaudio读入文件中的每一个音频文件,这里注意一下,有些同学可能安装完torchaudio后但是会有如下错误:
No audio I/O backend is available
torchaudio需要一个具体“做事”的软件(backend)去执行载入音频文件,所以需要安装它。

torchaudio在windows下的backend默认为soundfile
使用pip install SoundFile 即可以安装
torchaudio在linux下的backend默认为sox

所以它的读操作如下,即使用了torchaudio.load

def read_wav(fname, return_rate=False):
    '''
         Read wavfile using Pytorch audio
         input:
               fname: wav file path
               return_rate: Whether to return the sampling rate
         output:
                src: output tensor of size C x L 
                     L is the number of audio frames 
                     C is the number of channels. 
                sr: sample rate
    '''
    src, sr = torchaudio.load(fname, channels_first=True)
    if return_rate:
        return src.squeeze(), sr
    else:
        return src.squeeze()

AudioReader 类本身可以理解为一个字典(dict),它的内部实现形式为

{
	'1.wav': '/local/file/path/1.wav',
	'2.wav': '/local/file/path/2.wav',
	'3.wav': '/local/file/path/3.wav',
	'4.wav': '/local/file/path/4.wav',
	'5.wav': '/local/file/path/5.wav',
	'6.wav': '/local/file/path/6.wav'
}

但是实际通过字典返回时,是把对应的文件load完返回数据的。这样方便调用者使用。
同时,它扩展了字典key值,允许使用int来索引。总结AudioReader不复杂,但是设计上还是不错的。

下面是全部源码,请参考

def read_wav(fname, return_rate=False):
    '''
         Read wavfile using Pytorch audio
         input:
               fname: wav file path
               return_rate: Whether to return the sampling rate
         output:
                src: output tensor of size C x L 
                     L is the number of audio frames 
                     C is the number of channels. 
                sr: sample rate
    '''
    src, sr = torchaudio.load(fname, channels_first=True)
    if return_rate:
        return src.squeeze(), sr
    else:
        return src.squeeze()


def write_wav(fname, src, sample_rate):
    '''
         Write wav file
         input:
               fname: wav file path
               src: frames of audio
               sample_rate: An integer which is the sample rate of the audio
         output:
               None
    '''
    torchaudio.save(fname, src, sample_rate)


class AudioReader(object):
    '''
        Class that reads Wav format files
        Input as a different scp file address
        Output a matrix of wav files in all scp files.
    '''

    def __init__(self, scp_path, sample_rate=8000):
        super(AudioReader, self).__init__()
        self.sample_rate = sample_rate
        self.index_dict = handle_scp(scp_path)
        self.keys = list(self.index_dict.keys())

    def _load(self, key):
        src, sr = read_wav(self.index_dict[key], return_rate=True)
        if self.sample_rate is not None and sr != self.sample_rate:
            raise RuntimeError('SampleRate mismatch: {:d} vs {:d}'.format(
                sr, self.sample_rate))
        return src

    def __len__(self):
        return len(self.keys)

    def __iter__(self):
        for key in self.keys:
            yield key, self._load(key)

    def __getitem__(self, index):
        if type(index) not in [int, str]:
            raise IndexError('Unsupported index type: {}'.format(type(index)))
        if type(index) == int:
            num_uttrs = len(self.keys)
            if num_uttrs < index and index < 0:
                raise KeyError('Interger index out of range, {:d} vs {:d}'.format(
                    index, num_uttrs))
            index = self.keys[index]
        if index not in self.index_dict:
            raise KeyError("Missing utterance {}!".format(index))

        return self._load(index)

您可能感兴趣的与本文相关的镜像

PyTorch 2.5

PyTorch 2.5

PyTorch
Cuda

PyTorch 是一个开源的 Python 机器学习库,基于 Torch 库,底层由 C++ 实现,应用于人工智能领域,如计算机视觉和自然语言处理

Dual-path RNN (双通道循环神经网络) 是一种深度学习模型,用于处理序列数据,具有两个独立的循环神经网络路径。这种结构允许模型同时学习两个不同方面的特征,然后将它们整合在一起进行最终的预测。 在实现 Dual-path RNN 的代码中,我们首先需要定义两个循环神经网络模块,分别代表两个不同的路径。这些模块通常使用 LSTM(长短期记忆)或 GRU(门控循环单元)等结构,以实现对序列数据的有效建模。 然后,我们需要定义一个整合层,用于将两个路径上的特征进行整合。这个整合层可以是简单的拼接操作,也可以是更为复杂的注意力机制,以便模型能够更好地融合两个路径上的信息。 接下来,我们需要定义模型的前向传播过程。在这个过程中,输入数据会分别经过两个独立的路径,然后传入整合层,最终得到模型的输出。在训练过程中,我们通常会利用反向传播算法来更新模型参数,以最小化预测输出与真实数值之间的差距。 最后,我们需要定义模型的损失函数和优化器,以便在训练过程中能够衡量模型的性能并不断优化模型参数。常见的损失函数可以是均方差损失(mean squared error)或交叉熵损失(cross-entropy loss),而优化器则可以选择 Adam、SGD 等方法。 综上所述,实现 Dual-path RNN 的代码需要定义两个独立的循环神经网络路径、整合层以及模型的前向传播过程、损失函数和优化器。通过有效地组织这些代码,我们可以构建一个能够同时学习多个方面特征的深度学习模型。
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
红包 添加红包
表情包 插入表情
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值