一、简介
Vosk 是一个由 Alpha Cephei 团队开发的开源离线语音识别(ASR)工具包。它的核心优势在于完全离线运行和轻量级,使其非常适合在资源受限的环境、注重隐私的场景或需要低延迟的应用中使用。
二、核心特点
离线运行 (Offline)
这是 Vosk 最突出的特点。所有语音识别过程都在本地设备上完成,无需将音频数据上传到任何远程服务器。这对于保护用户隐私(如医疗、金融应用)或在没有稳定网络连接的环境下工作至关重要。
基于 Kaldi
Vosk 的后端引擎是业界知名的开源语音识别工具包 Kaldi。Kaldi 提供了强大的声学模型和解码器,保证了识别的准确性和鲁棒性。Vosk 可以看作是 Kaldi 的一个封装和简化接口,使其更易于集成到应用程序中。
轻量级与高效
Vosk 模型经过优化,可以在 CPU 上高效运行,对内存和计算资源的需求相对较低。这使得它能在树莓派、手机、嵌入式设备甚至普通笔记本电脑上流畅工作。
多语言支持
Vosk 支持多种语言,包括但不限于:英语、中文(普通话)、西班牙语、法语、德语、俄语、日语、韩语、阿拉伯语等。官方提供了这些语言的预训练模型。
支持流式识别 (Streaming)
Vosk 支持实时流式语音识别。这意味着你可以一边录音,一边将音频数据块(chunk)送入 Vosk 进行处理,并几乎实时地获得部分识别结果。这对于语音助手、实时字幕等应用非常有用。
小词汇量识别 (Keyword Spotting)
除了全量语音识别,Vosk 还支持通过提供一个“词汇表”(即一个包含有限词语的列表)来实现小词汇量识别。这可以显著提高特定关键词(如“打开”、“关闭”、“播放音乐”)的识别速度和准确率,同时降低资源消耗。
开源与免费
Vosk 在 Apache 2.0 许可下开源,可以免费用于商业和非商业项目。
三、主要应用场景
- 智能家居控制(离线语音指令)
- 移动端语音输入(保护隐私)
- 嵌入式设备上的语音交互
- 实时会议/讲座字幕生成
- 语音转写工具(离线版)
- 语音命令接口
四、应用实战
1. 下载Vosk模型
地址:https://alphacephei.com/vosk/models
这里以小个头的中文模型 vosk-model-small-cn-0.22 为例,体积只有42M,手机和树莓派都可以跑。
直接点击链接下载即可,然后解压到任一目录下,比如 D:/asr/model/vosk-model-small-cn-0.22,后边代码要用到这个路径。
2. 安装Python依赖
执行 pip3 install vosk
,等待安装完成后即可开始编码。
3. 编写Python测试代码
离线识别代码示例:
import json
import time
import wavefrom vosk import Model, KaldiRecognizer, SetLogLevelSetLogLevel(-1) # 禁止输出调试日志信息
model = Model("D:/asr/model/vosk-model-small-cn-0.22")# 打开音频文件
audio_file = input("请输入音频文件路径:")
start = time.time()
wf = wave.open(audio_file, "rb")
rec = KaldiRecognizer(model, wf.getframerate())
# 检查音频参数
if wf.getnchannels() != 1 or wf.getsampwidth() != 2:print("警告:音频文件应为单声道,16位")while True:data = wf.readframes(4000)if len(data) == 0:breakrec.AcceptWaveform(data)# if rec.AcceptWaveform(data):# print(rec.Result())# else:# print(rec.PartialResult())wf.close()
# 获取最终结果
print('最终识别结果:', json.loads(rec.FinalResult())['text'])
print(f'识别用时:{time.time() - start:.2f}秒')
Model里边的路径就是第二步解压模型的路径。
程序运行后会提示输入声音文件路径,输入后回车即可识别输出文本内容。
测试音频:test.wav 是测试时录制的一段话。
运行效果
识别效果还是可以的。
更多玩法请参考官方文档:https://alphacephei.com/vosk/
其他功能示例代码
1. 实时语音识别
import sys
from vosk import Model, KaldiRecognizer
import pyaudio# 创建模型对象
model = Model("D:/asr/model/vosk-model-small-cn-0.22")# 创建识别器 (sample_rate 需要与音频流的采样率一致)
rec = KaldiRecognizer(model, 16000)# 初始化音频流
p = pyaudio.PyAudio()
stream = p.open(format=pyaudio.paInt16,channels=1,rate=16000,input=True,frames_per_buffer=8000)
stream.start_stream()print("开始录音,请说话... (按 Ctrl+C 停止)")try:while True:# 读取音频数据块data = stream.read(4000, exception_on_overflow=False)# 将数据送入识别器if rec.AcceptWaveform(data):# 获取最终识别结果(JSON格式)result = rec.Result()print(result) # 通常包含 'text' 字段else:# 获取部分识别结果(可选,用于实时反馈)partial_result = rec.PartialResult()# print(partial_result) # 可以取消注释查看部分结果except KeyboardInterrupt:print("\n停止录音。")finally:# 清理资源stream.stop_stream()stream.close()p.terminate()# 获取最终的识别结果final_result = rec.FinalResult()print("最终识别结果:", final_result)
程序运行时会持续监听麦克风,只要说话就会进行识别并输出识别结果。
2. 小词汇量识别
from vosk import Model, KaldiRecognizer
import pyaudio# 创建模型
model = Model("D:/asr/model/vosk-model-small-cn-0.22")# 传入词汇表(用空格分隔的词语)
# 注意:对于中文,词汇表中的词需要是模型能识别的词语
# 这里假设模型支持这些词
keywords = "打开 关闭 开灯 关灯 播放 暂停 下一首 上一首"
rec = KaldiRecognizer(model, 16000, keywords) # 第三个参数是词汇表p = pyaudio.PyAudio()
stream = p.open(format=pyaudio.paInt16, channels=1, rate=16000, input=True, frames_per_buffer=8000)
stream.start_stream()print("小词汇量识别模式。可说:打开、关闭、开灯、关灯、播放、暂停、下一首、上一首")try:while True:data = stream.read(4000)if len(data) == 0:breakif rec.AcceptWaveform(data):result = rec.Result()print("识别到:", result)
except KeyboardInterrupt:pass
finally:stream.stop_stream()stream.close()p.terminate()