基于Paraformer的alpha-token强制对齐

1. 基本原理

img1

CIF 作为Parafoemr的核心模块,用于预测字数和生成声学向量,从而实现了单轮非自回归解码。其中字数的预测主要通过encoder输出系数alpha的累计得分,满足通关阈值β=1.0即可产生一个token,其中alpha曲线在一定程度上呈现着vad效果,或者依次进行断句。

2. alpha-token 强制对齐

cif的时间戳对齐采用peak(通关方式)得到,这里我们直接尝试alpha-token对齐方式,将识别的token在编码器输出上进行对齐,其中对齐算法采用动态规划。具体参考main.py中的maxSumSubarrayWithGaps()。

以10s窗长进行音频切块,下面展示alpha-token 的对齐效果:
img2

用户可以修改main.py 参数进行试验

3. code

github:https://github.com/coolEphemeroptera/funasr_alpha_token_alignment

import subprocess
from typing import List
import matplotlib.font_manager
import numpy as np 
from funasr_onnx import SeacoParaformer
import os 
import shutil
import matplotlib.pyplot as plt 
import matplotlib
zhfont1 = matplotlib.font_manager.FontProperties(fname="./SourceHanSansSC-Bold.otf")class SeacoParaformerPlus(SeacoParaformer):def __init__(self, *args, **kwargs):super().__init__(*args, **kwargs)self.SR = 16000self.SECONDS_PER_FRAME = 0.02self.UPSAMPLE_TIMES = 3def decode(self,am_scores, valid_token_lens):res = []for am_score, valid_token_len in zip(am_scores, valid_token_lens):token_ids = am_score.argmax(axis=-1)token_chs = self.converter.ids2tokens(token_ids)token_chs_valid = token_chs[:valid_token_len]res.append(token_chs_valid)return resdef __call__(self, waveform_list: list, hotwords: str, imgDir = './display',**kwargs) -> List:# 加载热词编码hotwords, hotwords_length = self.proc_hotword(hotwords)[bias_embed] = self.eb_infer(hotwords, hotwords_length)bias_embed = bias_embed.transpose(1, 0, 2)_ind = np.arange(0, len(hotwords)).tolist()bias_embed = bias_embed[_ind, hotwords_length.tolist()]bias_embed = np.expand_dims(bias_embed, axis=0)# onnx推理waveform_nums = len(waveform_list)content = []id = 0duration = 0for beg_idx in range(0, waveform_nums, self.batch_size):end_idx = min(waveform_nums, beg_idx + self.batch_size)# 1.计算mel特征feats, feats_len = self.extract_feat(waveform_list[beg_idx:end_idx])# 2.热词编码同步复制bias_embed_ = np.repeat(bias_embed, feats.shape[0], axis=0)# 3. 解码am_scores, valid_token_lens,us_alphas, us_peaks = self.bb_infer(feats, feats_len, bias_embed_)# 4. 后处理res = self.decode(am_scores, valid_token_lens)for r,alpha,peak in zip(res,us_alphas,us_peaks):content.append({'id':id,'range':[duration,duration+len(waveform_list[id])],'tokens':r,'alpha':alpha,'peak':peak})duration += len(waveform_list[id])id += 1return contentdef align_with_alpha(self,asr_res,img_path="tmp.png"):id = asr_res['id']tokens = asr_res['tokens'][:-1]tokens_n = len(tokens)stime,etime = round(asr_res['range'][0]/self.SR,2),round(asr_res['range'][1]/self.SR,2)alpha = asr_res['alpha']peak = asr_res['peak']# alpha 对齐max_val,max_path = maxSumSubarrayWithGaps(alpha,tokens_n,3)AX,AY = [],[]for ft,i,score in max_path:AX.append(ft*self.SECONDS_PER_FRAME+stime)AY.append(alpha[ft])# 绘图plt.rcParams['font.sans-serif'] = ['SimHei']  # 用来正常显示中文标签plt.rcParams['axes.unicode_minus'] = Falseplt.figure(figsize=(20, 8))plt.xlabel('time/seconds')plt.ylabel('alpha')plt.ylim([0,0.4])plt.title("ALPHA-ALIGNMENT (id:%s, range:%s-%s seconds)"%(id,stime,etime))x = np.linspace(stime,etime,len(alpha))plt.plot(x,alpha)plt.plot(AX, AY, 'o',color='red')for i,ax in enumerate(AX):ay = AY[i] + 0.01token = tokens[i]plt.text(ax, ay, token, fontsize=10, color='black',ha='center',fontproperties=zhfont1)plt.savefig(img_path)plt.close()def rebuild_dir(dir):def delete_directory(directory):if os.path.exists(directory):shutil.rmtree(directory)delete_directory(dir)os.makedirs(dir)print(f"Success to create {dir}")def audio_f2i(data,width=16):data = np.array(data)return np.int16(data*(2**(width-1)))def audio_i2f(data,width=16):data = np.array(data)return np.float32(data/(2**(width-1)))def read_audio_file(url):ffmpeg_cmd = ['ffmpeg','-y','-i', url,  '-vn','-f', 's16le','-acodec', 'pcm_s16le','-ar', '16k','-ac', '1','-' ]with subprocess.Popen(ffmpeg_cmd, stdin=subprocess.PIPE, stdout=subprocess.PIPE, stderr=subprocess.PIPE, text=False) as proc:stdout_data, stderr_data = proc.communicate()if stderr_data:audio_data = np.frombuffer(stdout_data,dtype=np.int16)audio_data = audio_i2f(audio_data)return audio_data# 动态规划实现alpha-token强制对齐
def maxSumSubarrayWithGaps(NUMS,K,GAP):N = len(NUMS)# 初始化表单dp = [[-float('inf') for j in range(K+1)] for _ in range(N)]path = [[[] for j in range(K+1)] for _ in range(N)]# 初始化边界for i in range(N): # dp[:,0]dp[i][0] = 0path[i][0] = []for j in range(K+1): # dp[0,:]if j==0:dp[0][j] = 0elif j==1:dp[0][j] = NUMS[0]else: dp[0][j] = -float('inf')# dp填表for i in range(1,N):for j in range(1,K+1):# 不满足G间隔if (j-1)*GAP+1>i+1:dp[i][j] = -float('inf')path[i][j] = []# 满足间隔else:for k in range(j-1,i-GAP+1):# 更新最大值且区间内满足极差(停顿)要求if dp[k][j-1]+NUMS[i]>dp[i][j] and max(NUMS[k:i+1])-min(NUMS[k+1:i])>0.02:dp[i][j] = dp[k][j-1]+NUMS[i]path[i][j] = [k,j-1,dp[k][j-1]]# 回溯max_i = np.argmax([dp[i][K] for i in range(N)])max_val = dp[max_i][K]max_path = []i,j,v = max_i,K,max_valmax_path.append([i,j,v])while 1:if not path[i][j]:breaki,j,v = path[i][j]if j>0:max_path.append([i,j,v])if j==1:breakmax_path.reverse()return max_val,max_pathif __name__ == '__main__':SR = 16000# 参数url = "/home/nvidia/funasr_alpha_token_alignment/funasr_models/iic/speech_seaco_paraformer_large_asr_nat-zh-cn-16k-common-vocab8404-pytorch/example/asr_example.wav"img_dir = 'alpha_align_plot'chunk_seconds = 10cache_dir='./funasr_models'model_name = 'iic/speech_seaco_paraformer_large_asr_nat-zh-cn-16k-common-vocab8404-pytorch'model_quant = Truebatch_size = 60# 1. 加载模型paraformer = SeacoParaformerPlus(model_dir=model_name,quantize=model_quant,batch_size=batch_size,cache_dir=cache_dir)# 2. 音频分块audio_data = read_audio_file(url)audio_length = len(audio_data)chunk_size = chunk_seconds*SRbatch = []for i in range(0,audio_length,chunk_size):s,e = i,min(i+chunk_size,audio_length)chunk = audio_data[s:e]batch.append(chunk)# 3. ASRcontent = paraformer(batch,hotwords='')# 4. alpha对齐rebuild_dir(img_dir)for asr_res in content:id = asr_res['id']text = asr_res['tokens']print(id,text)paraformer.align_with_alpha(asr_res,img_path=f"{img_dir}/{id}.png")print("saved into:",f"{img_dir}/{id}.png")

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/bicheng/19357.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Android12.0 SIM卡语言自适应

文章目录 需求语言设定Settings中语言切换流程检测到SIM卡,更新系统语言最终修改 需求 要求系统语言跟随SIM卡的语言变化。 语言设定 (1)系统预置语言, 即在makefile中指定的语言 (2)重启, 如果未插卡, 则系统语言为预置的语言 (3)重启插入SIM卡开机, 会自适应为…

【前端】vue+element项目中select下拉框label想要显示多个值多个字段

Vue Element项目中select下拉框label想要显示多个值 <el-selectv-model"form.plantId"collapse-tagsfilterableplaceholder"请选择品种种类"style"width: 270px;"><el-optionv-for"item in plantIdArray":key"item.id&…

前端首屏加载速度慢问题?怎么解决

前端首屏加载速度慢是用户体验中的一个关键问题&#xff0c;它直接影响用户对网站的第一印象以及用户留存率。首屏加载时间是指从用户输入网址到页面首屏内容完全呈现在用户面前所需的时间。这个指标对于搜索引擎优化&#xff08;SEO&#xff09;和用户体验都至关重要。下面将探…

CSS:浮动

▐ 文档流&#xff1a; 由于网页默认是一个二维平面&#xff0c;当我们在网页中一行行摆放标签时&#xff0c;块标签会独占一行&#xff0c;行标签则只占自身大小&#xff0c;这种情况下要实现网页布局就很麻烦了&#xff0c;所以我们就需要通过一些方法来改变这种默认的布局方…

centos7离线安装pthon3.8

centos7离线安装pthon3.8 因服务器无外网环境&#xff0c;所以事先需要把所有离线的依赖都准备好。 安装前的准备 先在有外网环境的机器上准备依赖 安装 centos-release-scl 第三方yum源 yum install centos-release-scl安装 yum 依赖下载插件 yum install yum-plugin-do…

Javascript 位运算符(,|,^,<<,>>,>>>)

文章目录 一、什么是位运算&#xff1f;二、如何使用1. 位与&#xff08;AND&#xff09;&#xff1a;&用途&#xff08;1&#xff09;数据清零&#xff08;2&#xff09;判断奇偶 2. 位或&#xff08;OR&#xff09;&#xff1a;|用途&#xff08;1&#xff09;向下取整 3…

GO语言 gin框架 简述

原文地址 基本路由 Go语言中文文档 一、简介 Gin是一个golang的轻量级web框架&#xff0c;性能不错&#xff0c;API友好。 Gin支持Restful风格的API&#xff0c;可以直接从URL路径上接收api参数或者URL参数&#xff0c;也可是使用json或者表单 数据绑定的方式接收参数。 Gin响…

【传知代码】BERT论文解读及情感分类实战-论文复现

文章目录 概述原理介绍BERT模型架构任务1 Masked LM&#xff08;MLM&#xff09;任务2 Next Sentence Prediction (NSP)模型输入下游任务微调GLUE数据集SQuAD v1.1 和 v2.0NER 情感分类实战IMDB影评情感数据集数据集构建模型构建 核心代码超参数设置训练结果注意事项 小结 本文…

AIOps在线评测基准首阶段建设完成,面向社区发布真实运维数据!

本文根据必示科技算法研究员、产品总监聂晓辉博士在2024 CCF国际AIOps挑战赛线下宣讲会上的演讲整理成文。 2024年1月份OpenAIOps社区成立&#xff0c;随着越来越多的社区成员加入&#xff0c;各项工作在有条不紊的推进中。在线评测基准系统&#xff08;AIOps Live Benchmark&a…

积鼎CFDPro水文水动力模型,专为中小流域洪水“四预”研发的流体仿真技术

水动力模型与水文模型是水利工程与水文学研究中不可或缺的两大工具。水动力模型着重于流体运动的动力学机制&#xff0c;通过一系列方程组捕捉水流的时空变化&#xff0c;而概念性水文模型则侧重于流域尺度的水文循环过程&#xff0c;利用物理概念与经验关系进行近似模拟。两者…

Windows系统部署YOLOv5 v6.1版本的训练与推理环境保姆级教程

文章目录 一 概述二 依赖环境(prerequisites)2.1 硬件环境2.2 软件环境 三 环境安装3.1 创建并激活虚拟环境3.2 安装Pytorch与torchvision3.3 校验Pytorch安装3.4 下载 YOLOv5 v6.1 源码3.5 安装 YOLOv5 依赖3.6 下载预训练模型3.7 安装其他依赖3.8 测试环境安装3.9 测试训练流…

jupyter notebook更改位置

1.找到jupyer的配置文件 一般在c盘用户的.jupter文件夹下 2. 用记事本打开这个配置文件&#xff0c;定位到c.NotebookApp.notebook_dir /path_to_your_directory 替换你的位置 3.找到jupyer图标的位置&#xff0c;打开属性 添加要存放的位置在目标文件的末尾&#xff0c;重新…

python | spacy,一个神奇的 Python 库!

本文来源公众号“python”&#xff0c;仅用于学术分享&#xff0c;侵权删&#xff0c;干货满满。 原文链接&#xff1a;spacy&#xff0c;一个神奇的 Python 库&#xff01; 大家好&#xff0c;今天为大家分享一个神奇的 Python 库 - spacy。 Github地址&#xff1a;https:/…

一个全面了解Xilinx FPGA IP核的窗口:《Xilinx系列FPGA芯片IP核详解》(可下载)

随着摩尔定律的逐渐放缓&#xff0c;传统的芯片设计方法面临着越来越多的挑战。而FPGA以其并行处理能力和可编程性&#xff0c;为解决复杂问题提供了新的途径。它允许设计者在同一个芯片上实现多种不同的功能模块&#xff0c;极大地提高了资源的利用率和系统的综合性能。 FPGA…

领域数据模型建设步骤

领域数据模型建设步骤 以某音乐app为例: 1.数据调研和业务调研&#xff0c;识别业务过程&#xff0c;实体&#xff0c;关键指标 业务过程&#xff1a;播放&#xff0c;收藏&#xff0c;下载&#xff0c;点击&#xff0c;购买&#xff0c;支付 实体&#xff1a;音乐&#xff0c…

HCIA-ARP

ARP的由来 ARP这一种协议它会是在我们HCIA中第一个需要完全掌握的一个协议&#xff0c;不然对于数据通讯来说大家都会一直觉得很绕圈 协议栈&#xff0c;网线&#xff0c;网卡&#xff0c;它们组成了我们最小的数据通信的小脉络注&#xff1a;可以了解ARP攻击&#xff08;冒充访…

使用Java和MyBatis获取表头与数据

使用Java和MyBatis获取表头与数据 在数据处理与展示中&#xff0c;经常需要将数据库查询结果中的表头&#xff08;列名&#xff09;与实际数据提取出来。本文将介绍如何通过Java的JDBC和MyBatis来实现这一需求。 1. 使用JDBC获取表头与数据 在JDBC中&#xff0c;可以使用Res…

文献解读-群体基因组第二期|《中国人群中PAX2新生突变的检测及表型分析:一项单中心研究》

关键词&#xff1a;应用遗传流行病学&#xff1b;群体测序&#xff1b;群体基因组&#xff1b;基因组变异检测&#xff1b; 文献简介 标题&#xff08;英文&#xff09;&#xff1a;Detection of De Novo PAX2 Variants and Phenotypes in Chinese Population: A Single-Cente…

new CCDIKSolver( OOI.kira, iks ); // 创建逆运动学求解器

demo案例 new CCDIKSolver(OOI.kira, iks); 在使用某个特定的库或框架来创建一个逆运动学&#xff08;Inverse Kinematics, IK&#xff09;求解器实例。逆运动学在机器人学、动画和计算机图形学等领域中非常重要&#xff0c;它用于根据期望的末端执行器&#xff08;如机器人的…

Compose第四弹 Compose项目

目标&#xff1a; 1.可供学习的Compose项目 一、官方提供项目 谷歌官方提供的Compose项目&#xff1a; GitHub - android/compose-samples: Official Jetpack Compose samples. 项目及主要页面展现 1.1 Reply项目 1.首页底部TAB栏 2.侧边栏菜单&#xff1a;拖动滑出和收起…