【Paddle实战】基于PaddleSpeech搭建私人录音转文字服务

环境搭建

安装paddlepaddle和paddleSpeech:

pip install paddlepaddlepip install paddlespeech

PaddleSpeech 是基于飞桨 PaddlePaddle 的语音方向的开源模型库,用于语音和音频中的各种关键任务的开发,包含大量基于深度学习前沿和有影响力的模型,一些典型的应用如下:

  • 声音分类

  • 语音识别

  • 语音翻译

  • 语音合成

相关依赖如下:

  • gcc >= 4.8.5

  • paddlepaddle >= 2.3.1

  • python >= 3.7

  • linux(推荐), mac, windows

  • win必须安装Microsoft C++生成工具

命令行调用

语音分类

paddlespeech cls --input 1.mp3

图片

一段python办公自动化抖音广告语,因为有背景音乐,所以判断为Music。

语音识别

图片

这段广告语被完整识别出来,唯一的问题是不带标点符号。

语音翻译(英翻中)

paddlespeech asr --lang zh --input input_16k.wav

windows暂不支持,但是linux可以。

语音合成

paddlespeech tts --input "你好,欢迎关注电力数据新应用!" --output output.wav

图片

自动生成语音,大数据工匠,2秒

API调用语音识别​​​​​​​

from paddlespeech.cli.asr.infer import ASRExecutor
asr = ASRExecutor()result = asr(audio_file="1.mp3")print(result)

图片

PaddleSpeech识别最长语音为50s,故需要切分。

代码实现

音频切分:

安装auditok库。

pip install auditok

引入需要的库。​​​​​​​

from paddlespeech.cli.asr.infer import ASRExecutorfrom paddlespeech.cli.text.infer import TextExecutorimport csvimport moviepy.editor as mpimport auditokimport osimport paddleimport soundfileimport librosaimport warnings
warnings.filterwarnings('ignore')

通过auditok.split来对音频进行切分,切分后新建目录:change/audio/文件名/,将文件存入该目录。​​​​​​​

# 引入auditok库import auditok# 输入类别为audiodef qiefen(path, ty='audio', mmin_dur=1, mmax_dur=100000, mmax_silence=1, menergy_threshold=55):    audio_file = path    audio, audio_sample_rate = soundfile.read(        audio_file, dtype="int16", always_2d=True)
    audio_regions = auditok.split(        audio_file,        min_dur=mmin_dur,  # minimum duration of a valid audio event in seconds        max_dur=mmax_dur,  # maximum duration of an event        # maximum duration of tolerated continuous silence within an event        max_silence=mmax_silence,        energy_threshold=menergy_threshold  # threshold of detection    )
    for i, r in enumerate(audio_regions):        # Regions returned by `split` have 'start' and 'end' metadata fields        print(            "Region {i}: {r.meta.start:.3f}s -- {r.meta.end:.3f}s".format(i=i, r=r))
        epath = ''        file_pre = str(epath.join(audio_file.split('.')[0].split('/')[-1]))
        mk = 'change'        if (os.path.exists(mk) == False):            os.mkdir(mk)        if (os.path.exists(mk + '/' + ty) == False):            os.mkdir(mk + '/' + ty)        if (os.path.exists(mk + '/' + ty + '/' + file_pre) == False):            os.mkdir(mk + '/' + ty + '/' + file_pre)        num = i        # 为了取前三位数字排序        s = '000000' + str(num)
        file_save = mk + '/' + ty + '/' + file_pre + '/' + \                    s[-3:] + '-' + '{meta.start:.3f}-{meta.end:.3f}' + '.wav'        filename = r.save(file_save)        print("region saved as: {}".format(filename))    return mk + '/' + ty + '/' + file_pre
qiefen("1.wav")

执行后qiefen("1.wav")后,可以把1.wav进行切分。

图片

语音转文本

遍历每一个文件,将它们分别送入ASRExecutor进行识别,所有识别文本集中保存到列表words里,最终写入result.csv文件。

# 语音转文本asr_executor = ASRExecutor()
def audio2txt(path):    # 返回path下所有文件构成的一个list列表    print(f"path: {path}")    filelist = os.listdir(path)    # 保证读取按照文件的顺序    filelist.sort(key=lambda x: int(os.path.splitext(x)[0][:3]))    # 遍历输出每一个文件的名字和类型    words = []    for file in filelist:        print(path + '/' + file)        text = asr_executor(            audio_file=path + '/' + file,            device=paddle.get_device(), force_yes=True) # force_yes参数需要注意        words.append(text)    return words​​​​​
# 保存import csv
def txt2csv(txt_all):    with open('result.csv', 'w', encoding='utf-8') as f:        f_csv = csv.writer(f)        for row in txt_all:            f_csv.writerow([row])​​​​​​
# 可替换成自身的录音文件source_path = '录音.wav'# 划分音频path = qiefen(path=source_path, ty='audio',                mmin_dur=0.5, mmax_dur=100000, mmax_silence=0.5, menergy_threshold=55)# 音频转文本  需要GPUtxt_all = audio2txt(path)# 存入csvtxt2csv(txt_all)

标点符号修正:

将result.csv文件读入,拼成完整的段落,利用TextExecutor进行标点符号修正,最终将修正结果存入final_result.txt文件。​​​​​​​

# 拿到新生成的音频的路径texts = ''source_path = 'result.csv'with open(source_path, 'r') as f:    text = f.readlines()for i in range(len(text)):    text[i] = text[i].replace('\n', '')    texts = texts + text[i]print(texts)text_executor = TextExecutor()if text:    result = text_executor(        text=texts,        task='punc',        model='ernie_linear_p3_wudao',        device=paddle.get_device(),        # force_yes=True    )print(result)​​​​​​
with open("final_result.txt", 'w') as f:    f.writelines(result)

将会议录音文件录音.wav放入工程目录下,执行程序,结果如下。

图片

图片

可以看到只有“一键三连”翻译成了“一见三连”,其他内容准确无误进行了识别。

  • 5
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
好的,以下是使用 PaddlePaddle 搭建 CRNN 进行语音识别的基本步骤: 1. 数据准备:准备好训练集和测试集。每个音频文件应该有对应的文本标注。 2. 特征提取:使用 Mel-spectrogram 技术将音频文件换为图像,以便训练模型。 3. 构建模型:使用 PaddlePaddle 搭建 CRNN 模型,其中包括卷积层、循环神经网络层和全连接层。 4. 训练模型:使用训练集进行模型训练,并使用测试集进行验证。 5. 模型优化:根据实际情况对模型进行调整和优化,以提高模型的准确性。 6. 模型部署:将模型部署到生产环境中,以进行实际应用。 以下是一个基本的 CRNN 模型实现的代码示例: ```python import paddle import paddle.fluid as fluid class CRNN(fluid.dygraph.Layer): def __init__(self, name_scope, num_classes): super(CRNN, self).__init__(name_scope) self.num_classes = num_classes self.conv1 = fluid.dygraph.Conv2D(num_channels=1, num_filters=32, filter_size=(3, 3), stride=(1, 1), padding=(1, 1)) self.pool1 = fluid.dygraph.Pool2D(pool_size=(2, 2), pool_stride=(2, 2), pool_type='max') self.conv2 = fluid.dygraph.Conv2D(num_channels=32, num_filters=64, filter_size=(3, 3), stride=(1, 1), padding=(1, 1)) self.pool2 = fluid.dygraph.Pool2D(pool_size=(2, 2), pool_stride=(2, 2), pool_type='max') self.conv3 = fluid.dygraph.Conv2D(num_channels=64, num_filters=128, filter_size=(3, 3), stride=(1, 1), padding=(1, 1)) self.conv4 = fluid.dygraph.Conv2D(num_channels=128, num_filters=128, filter_size=(3, 3), stride=(1, 1), padding=(1, 1)) self.pool3 = fluid.dygraph.Pool2D(pool_size=(2, 2), pool_stride=(2, 2), pool_type='max') self.conv5 = fluid.dygraph.Conv2D(num_channels=128, num_filters=256, filter_size=(3, 3), stride=(1, 1), padding=(1, 1)) self.batch_norm1 = fluid.dygraph.BatchNorm(num_channels=256, act='relu') self.conv6 = fluid.dygraph.Conv2D(num_channels=256, num_filters=256, filter_size=(3, 3), stride=(1, 1), padding=(1, 1)) self.batch_norm2 = fluid.dygraph.BatchNorm(num_channels=256, act='relu') self.pool4 = fluid.dygraph.Pool2D(pool_size=(2, 2), pool_stride=(2, 1), pool_type='max') self.conv7 = fluid.dygraph.Conv2D(num_channels=256, num_filters=512, filter_size=(3, 3), stride=(1, 1), padding=(1, 1)) self.batch_norm3 = fluid.dygraph.BatchNorm(num_channels=512, act='relu') self.conv8 = fluid.dygraph.Conv2D(num_channels=512, num_filters=512, filter_size=(3, 3), stride=(1, 1), padding=(1, 1)) self.batch_norm4 = fluid.dygraph.BatchNorm(num_channels=512, act='relu') self.pool5 = fluid.dygraph.Pool2D(pool_size=(2, 2), pool_stride=(2, 1), pool_type='max') self.conv9 = fluid.dygraph.Conv2D(num_channels=512, num_filters=512, filter_size=(2, 2), stride=(1, 1), padding=(0, 0)) self.batch_norm5 = fluid.dygraph.BatchNorm(num_channels=512, act='relu') self.fc1 = fluid.dygraph.Linear(512, 512, act='relu') self.fc2 = fluid.dygraph.Linear(512, self.num_classes) def forward(self, x): x = self.conv1(x) x = self.pool1(x) x = self.conv2(x) x = self.pool2(x) x = self.conv3(x) x = self.conv4(x) x = self.pool3(x) x = self.conv5(x) x = self.batch_norm1(x) x = self.conv6(x) x = self.batch_norm2(x) x = self.pool4(x) x = self.conv7(x) x = self.batch_norm3(x) x = self.conv8(x) x = self.batch_norm4(x) x = self.pool5(x) x = self.conv9(x) x = self.batch_norm5(x) x = fluid.layers.squeeze(x, [2]) x = fluid.layers.transpose(x, [0, 2, 1]) x = fluid.layers.fc(x, size=512, act='relu') x = fluid.layers.dropout(x, dropout_prob=0.5) x = fluid.layers.fc(x, size=self.num_classes, act='softmax') return x ``` 其中,`num_classes` 表示分类数目,`forward()` 方法中定义了 CRNN 的前向传播过程。在训练过程中,使用 `fluid.dygraph.to_variable()` 方法将数据换为 PaddlePaddle 支持的数据格式,然后使用 `model()` 方法进行模型的前向传播和反向传播,最终使用 `model.save()` 方法保存模型。 希望以上内容能对您有所帮助!

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值