news 2026/9/14 4:53:14

sherpa-onnx C/.NET 示例实战:dotnet-examples 目录全解与 C API 集成指南

作者头像

张小明

前端开发工程师

1.2k 24
文章封面图
sherpa-onnx C/.NET 示例实战:dotnet-examples 目录全解与 C API 集成指南

sherpa-onnx C#/.NET 示例实战:dotnet-examples 目录全解与 C# API 集成指南

【免费下载链接】sherpa-onnxSpeech-to-text, text-to-speech, speaker diarization, speech enhancement, source separation, and VAD using next-gen Kaldi with onnxruntime without Internet connection. Support embedded systems, Android, iOS, HarmonyOS, Raspberry Pi, RISC-V, RK NPU, Axera NPU, Ascend NPU, x86_64 servers, websocket server/client, support 12 programming languages项目地址: https://gitcode.com/GitHub_Trending/sh/sherpa-onnx

本文以 sherpa-onnx 仓库中的 dotnet-examples 目录为主体,系统讲解这套 C# API 示例工程的组成结构、NuGet 集成方式、各功能类别示例(离线/流式语音增强、零样本 TTS、离线 ASR 等)的运行方法,以及如何在解决方案中新增自己的示例项目,帮助 .NET 开发者快速完成 sherpa-onnx 在 C# 项目中的接入与调用。

一、这个目录解决什么问题

sherpa-onnx 是支持离线语音识别(ASR)、语音合成(TTS)、说话人分离、语音增强、声源分离与端点检测(VAD)的推理框架。dotnet-examples 目录提供了官方维护的 C# 端示例集合:每个功能点都是一个独立的可运行 console 项目,通过统一的Common项目引用 NuGet 包org.k2fsa.sherpa.onnx,配合各自的run.sh脚本一键下载模型并运行。

整个示例集以 Visual Studio 解决方案 sherpa-onnx.sln 组织,当前共包含 40 多个子项目,覆盖:

  • 离线语音增强:speech-enhancement-gtcrn、speech-enhancement-dpdfnet
  • 流式(在线)语音增强:streaming-speech-enhancement-gtcrn、streaming-speech-enhancement-dpdfnet
  • 零样本 TTS:zipvoice-tts、zipvoice-tts-play(带播放),以及 pocket-tts-zero-shot、kokoro-tts、kitten-tts、supertonic-tts、offline-tts 等
  • 离线 ASR:offline-decode-files(Paraformer、Whisper、SenseVoice 等多模型)、non-streaming-canary、non-streaming-cohere-transcribe、non-streaming-funasr-nano、non-streaming-moonshine-v2、non-streaming-qwen3-asr 等
  • 流式 ASR:online-decode-files、streaming-hlg-decoding、speech-recognition-from-microphone
  • VAD + ASR 组合:vad-non-streaming-asr-paraformer、vad-non-streaming-funasr-nano、vad-non-streaming-qwen3-asr
  • 标点恢复:offline-punctuation、online-punctuation
  • 说话人相关:speaker-identification、offline-speaker-diarization
  • 其他:offline-audio-tagging、spoken-language-identification、keyword-spotting-from-files / keyword-spotting-from-microphone、source-separation-spleeter / source-separation-uvr、version-test

每个项目内的 Program.cs 文件头部通常都带有完整的操作注释(下载哪个模型、如何运行),是最直接的参考文档。

二、解决方案结构与 NuGet 集成方式

2.1 公共层:Common 项目

所有示例共享一个公共项目 Common.csproj,其内容非常精简:

<Project Sdk="Microsoft.NET.Sdk"> <PropertyGroup> <TargetFramework>net8.0</TargetFramework> <AllowUnsafeBlocks>true</AllowUnsafeBlocks> </PropertyGroup> <ItemGroup> <PackageReference Include="org.k2fsa.sherpa.onnx" Version="*" /> </ItemGroup> </Project>

三个关键信息:

  • 目标框架为 .NET 8.0,即所有示例的运行前提是安装了 .NET 8 SDK(dotnet命令行工具);
  • C# API 通过 NuGet 包org.k2fsa.sherpa.onnx引入,示例中版本号写作*(自动取最新版),实际生产项目中建议锁定具体版本以便复现;
  • 开启了AllowUnsafeBlocks。从 C# 封装层源码(见 scripts/dotnet 下的DenoisedAudio.csWaveReader.cs等文件,它们就是 NuGet 包内 C# API 的原始实现)看,C# 层通过 P/Invoke 调用底层 C 库,因此需要 unsafe 块支持。

Common项目除引入 NuGet 包外,还包含 WaveHeader.cs,提供 WAV 文件头读写支持,供各示例直接读写.wav文件使用。

2.2 示例项目如何组织

以 speech-enhancement-gtcrn.csproj 为例,每个示例项目的 csproj 只有几行:

<Project Sdk="Microsoft.NET.Sdk"> <PropertyGroup> <OutputType>Exe</OutputType> <TargetFramework>net8.0</TargetFramework> <RootNamespace>speech_enhancement_gtcrn</RootNamespace> <ImplicitUsings>enable</ImplicitUsings> <Nullable>enable</Nullable> </PropertyGroup> <ItemGroup> <ProjectReference Include="..\Common\Common.csproj" /> </ItemGroup> </Project>

要点:示例项目不直接引用 NuGet 包,而是通过ProjectReference依赖Common项目间接获得org.k2fsa.sherpa.onnx。这样统一升级版本时只需改一处(Common.csproj)。

三、标准运行流程:run.sh 脚本模式

每个示例目录下都有一个run.sh,遵循统一的"检查 → 下载 → 运行"模式。以 speech-enhancement-gtcrn/run.sh 为例:

#!/usr/bin/env bash set -ex if [ ! -f ./gtcrn_simple.onnx ]; then curl -SL -O https://github.com/k2-fsa/sherpa-onnx/releases/download/speech-enhancement-models/gtcrn_simple.onnx fi if [ ! -f ./inp_16k.wav ]; then curl -SL -O https://github.com/k2-fsa/sherpa-onnx/releases/download/speech-enhancement-models/inp_16k.wav fi dotnet run

可以看到模式为:本地不存在模型/测试音频时才从 sherpa-onnx 官方 Releases 的speech-enhancement-models资产中下载,然后直接dotnet run。这意味着模型文件不进入版本库,首次运行会联网下载,之后离线可复现。

ASR 类示例的模型下载类似,例如 offline-decode-files/run-paraformer.sh 会下载 Paraformer 中文模型包并解压,再以命令行参数方式传给程序:

dotnet run \ --tokens=./sherpa-onnx-paraformer-zh-2023-09-14/tokens.txt \ --paraformer=./sherpa-onnx-paraformer-zh-2023-09-14/model.int8.onnx \ --num-threads=2 \ --files ./sherpa-onnx-paraformer-zh-2023-09-14/test_wavs/0.wav \ ./sherpa-onnx-paraformer-zh-2023-09-14/test_wavs/1.wav \ ./sherpa-onnx-paraformer-zh-2023-09-14/test_wavs/2.wav \ ./sherpa-onnx-paraformer-zh-2023-09-14/test_wavs/8k.wav

offline-decode-files是目录内参数最多的示例,Program.cs 使用 CommandLine 库定义了一组Options,通过--tokens--paraformer--whisper-encoder--whisper-decoder--nemo-ctc--zipformer-ctc--moonshine-*等参数适配 Transducer、Paraformer、Whisper、NeMo CTC、Moonshine 等不同模型族;同目录还配有 run-whisper.sh、run-sense-voice-ctc.sh、run-zipformer.sh 等十余个脚本,分别演示不同模型的参数组合。命令行参数方式适合需要灵活切换模型的批处理场景;而语音增强、TTS 类示例则把模型路径硬编码在Program.cs中,更适合阅读 API 用法。

四、代表性示例源码解析

4.1 离线语音增强(GTCRN)

speech-enhancement-gtcrn/Program.cs 展示了离线降噪 API 的最小调用链:

using SherpaOnnx; class OfflineSpeechEnhancementDemo { static void Main(string[] args) { var model = "./gtcrn_simple.onnx"; var config = new OfflineSpeechDenoiserConfig(); config.Model.Gtcrn.Model = model; // 指定 GTCRN 模型路径 config.Model.Debug = 1; // 打开调试日志 config.Model.NumThreads = 1; // 推理线程数 var sd = new OfflineSpeechDenoiser(config); WaveReader waveReader = new WaveReader("./inp_16k.wav"); var denoisedAudio = sd.Run(waveReader.Samples, waveReader.SampleRate); var outputFilename = "./enhanced.wav"; var ok = denoisedAudio.SaveToWaveFile(outputFilename); // ... } }

调用要点:

  1. 配置对象为OfflineSpeechDenoiserConfig,模型路径挂在config.Model.Gtcrn.Model上;
  2. WaveReader读入 wav 后得到float[]采样和采样率;
  3. sd.Run(samples, sampleRate)一次性处理整段音频,返回DenoisedAudio对象,再SaveToWaveFile输出enhanced.wav

4.2 离线语音增强(DPDFNet)与模型选择

speech-enhancement-dpdfnet/Program.cs 与 GTCRN 示例结构完全一致,仅模型字段不同:

var config = new OfflineSpeechDenoiserConfig(); config.Model.Dpdfnet.Model = "./dpdfnet_baseline.onnx"; config.Model.Dpdfnet.AttenuationLimitDb = 12.0f; // DPDFNet 特有:增益限制(dB)

README 与源码注释对 DPDFNet 模型的选择给出了明确指引:

模型文件适用场景
dpdfnet_baseline.onnxdpdfnet2.onnxdpdfnet4.onnxdpdfnet8.onnx16 kHz 输出,适合下游接 ASR/语音识别
dpdfnet2_48khz_hr.onnx48 kHz 增强输出,适合直接听感/高质量增强

AttenuationLimitDb用于限制增强时噪声衰减的幅度上限,避免人声被过度压制。

4.3 流式语音增强:按帧推送与 Flush

streaming-speech-enhancement-gtcrn/Program.cs 演示了在线(流式)降噪 API 的标准循环模式:

var config = new OnlineSpeechDenoiserConfig(); config.Model.Gtcrn.Model = "./gtcrn_simple.onnx"; config.Model.Debug = 1; config.Model.NumThreads = 1; var sd = new OnlineSpeechDenoiser(config); WaveReader waveReader = new WaveReader("./inp_16k.wav"); var samples = waveReader.Samples; var output = new List<float>(samples.Length); int frameShift = sd.FrameShiftInSamples; // 每次应推送的帧长(采样数) for (int start = 0; start < samples.Length; start += frameShift) { int count = Math.Min(frameShift, samples.Length - start); float[] chunk = new float[count]; Array.Copy(samples, start, chunk, 0, count); var audio = sd.Run(chunk, waveReader.SampleRate); output.AddRange(audio.Samples); } output.AddRange(sd.Flush().Samples); // 冲刷内部缓冲,拿到剩余输出 var ok = DenoisedAudio.SaveToWaveFile(output.ToArray(), sd.SampleRate, "./enhanced-online-gtcrn.wav");

从源码结构看,流式 API 的三个关键点是:

  • 通过sd.FrameShiftInSamples属性获取引擎要求的帧长,而不是自己拍脑袋取 320/480 之类的值,保证与模型内部帧移严格一致;
  • 每次Run传入一帧,返回值是这一帧对应的增强采样;
  • 输入结束后必须调用Flush()取回内部缓冲区里剩余的音频,否则会丢失结尾片段。

streaming-speech-enhancement-dpdfnet示例是同一模式的 DPDFNet 版本,可直接对照阅读。

4.4 ZipVoice 中英文零样本 TTS

zipvoice-tts/Program.cs 演示了零样本(zero-shot)TTS:用一段参考音频"克隆"音色后合成新文本。核心配置:

var config = new OfflineTtsConfig(); config.Model.ZipVoice.Tokens = "./sherpa-onnx-zipvoice-distill-int8-zh-en-emilia/tokens.txt"; config.Model.ZipVoice.Encoder = "./sherpa-onnx-zipvoice-distill-int8-zh-en-emilia/encoder.int8.onnx"; config.Model.ZipVoice.Decoder = "./sherpa-onnx-zipvoice-distill-int8-zh-en-emilia/decoder.int8.onnx"; config.Model.ZipVoice.Vocoder = "./vocos_24khz.onnx"; config.Model.ZipVoice.DataDir = "./sherpa-onnx-zipvoice-distill-int8-zh-en-emilia/espeak-ng-data"; config.Model.ZipVoice.Lexicon = "./sherpa-onnx-zipvoice-distill-int8-zh-en-emilia/lexicon.txt"; config.Model.NumThreads = 2; config.Model.Debug = 1; config.Model.Provider = "cpu";

ZipVoice 需要五件套:tokens、encoder、decoder、vocoder(独立下载的vocos_24khz.onnx)以及 espeak-ng 发音数据目录加 lexicon。

零样本音色由OfflineTtsGenerationConfig提供:

var reader = new WaveReader(referenceWaveFilename); // 参考音频 genConfig.ReferenceAudio = reader.Samples; genConfig.ReferenceSampleRate = reader.SampleRate; genConfig.ReferenceText = "那还是三十六年前, 一九八七年. 我呢考上了武汉大学的计算机系."; genConfig.NumSteps = 4; genConfig.Extra["min_char_in_sentence"] = "10"; // 分句时单句最少字数

合成时还支持带进度回调的生成接口,回调中返回 1 表示继续、0 表示中止:

var myCallback = (IntPtr samples, int n, float progress, IntPtr arg) => { float[] data = new float[n]; Marshal.Copy(samples, data, 0, n); Console.WriteLine($"Progress {progress * 100}%"); return 1; // 1: 继续生成;0: 停止生成 }; var callback = new OfflineTtsCallbackProgressWithArg(myCallback); var audio = tts.GenerateWithConfig(text, genConfig, callback); var ok = audio.SaveToWaveFile("./generated-zipvoice-zh-en.wav");

配套的 zipvoice-tts-play 在同样流程基础上增加了音频播放,pocket-tts-zero-shotsupertonic-ttsoffline-tts-play等示例也遵循"OfflineTtsConfig + GenerateWithConfig + SaveToWaveFile"的一致套路,可按需对照切换模型。

五、在解决方案中新增自己的示例项目

dotnet-examples/README.md 给出了新增项目的两条标准命令(在dotnet-examples目录下执行):

dotnet new console -n offline-tts-play dotnet sln ./sherpa-onnx.sln add ./offline-tts-play

即:先用dotnet new console创建 console 项目,再用dotnet sln add把它挂进现有解决方案。创建后按第二节的模式修改新项目的 csproj:目标框架设为net8.0,并添加对..\Common\Common.csprojProjectReference,即可获得完整的 C# API 依赖。

README 还给出了 NuGet 本地缓存的清理命令,用于排查包版本/缓存导致的异常:

dotnet nuget locals all --list dotnet nuget locals all --clear

--list显示各缓存位置(全局包目录、http-cache、temp 等),--clear清空缓存,之后重新构建时会从 NuGet 源重新拉取org.k2fsa.sherpa.onnx包。

六、落地检查清单

  1. 环境:已安装 .NET 8 SDK(所有示例均为net8.0),dotnet --version可正常输出;
  2. :通过 Common.csproj 引用 NuGet 包org.k2fsa.sherpa.onnx,生产项目建议把Version="*"固定为具体版本号;
  3. 模型:各run.sh会按需从 sherpa-onnx 官方 Releases 下载模型与测试音频(语音增强模型在speech-enhancement-models资产组、TTS 模型在tts-models/vocoder-models资产组、ASR 模型在asr-models资产组);首次运行需要网络;
  4. 运行bash run.sh或手动dotnet run(ASR 类示例注意按脚本传入--tokens--paraformer等参数);
  5. 新示例dotnet new console -n <名称>+dotnet sln ./sherpa-onnx.sln add <名称>+ 引用 Common 项目;
  6. 排障:模型参数(采样率、帧移、线程数)以示例Program.cs中的配置为准;流式场景务必使用FrameShiftInSamples并按需调用Flush();遇到包引用异常先执行dotnet nuget locals all --clear

整套dotnet-examples的价值在于:它把 sherpa-onnx 的 C# API 按功能拆成了可独立编译运行的最小工程,每个目录自带"下载 + 运行"脚本,既可以作为 API 参考手册直接阅读,也可以作为脚手架快速拷贝出适合自己业务的 C# 语音处理程序。

【免费下载链接】sherpa-onnxSpeech-to-text, text-to-speech, speaker diarization, speech enhancement, source separation, and VAD using next-gen Kaldi with onnxruntime without Internet connection. Support embedded systems, Android, iOS, HarmonyOS, Raspberry Pi, RISC-V, RK NPU, Axera NPU, Ascend NPU, x86_64 servers, websocket server/client, support 12 programming languages项目地址: https://gitcode.com/GitHub_Trending/sh/sherpa-onnx

创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考

版权声明: 本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若内容造成侵权/违法违规/事实不符,请联系邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
网站建设 2026/9/14 4:53:01

MQTT Broker选型与自研协议栈:许可证合规和替代方案全面解析

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

作者头像 李华
网站建设 2026/9/14 4:51:45

品优购HTML+CSS实战:电商首页精准还原与GIF兼容处理

简介&#xff1a;本资源是一份高质量的前端开发期末作业实战项目&#xff0c;面向HTML/CSS/JavaScript初学者及高校Web前端课程学习者&#xff0c;聚焦电商类页面开发能力训练。项目完整实现品优购风格的首页、分类列表页与商品详情页三大核心模块&#xff0c;涵盖语义化HTML5结…

作者头像 李华
网站建设 2026/9/14 4:50:53

基于Java毕业选题系统:Spring Boot+Vue前后端分离与并发控制实战

简介&#xff1a;基于Java/JSP的毕业选题系统完整源码&#xff0c;面向Java Web学习者、毕业设计或课程设计学生&#xff0c;覆盖管理员、老师、学生三类角色的核心流程&#xff1a;管理员可维护系主任信息与系统运行&#xff0c;老师录入题目并审核学生选题&#xff0c;学生在…

作者头像 李华
网站建设 2026/9/14 4:50:31

Python信用卡客户高风险识别:从特征工程到评分卡的完整建模实践

简介&#xff1a;这是一份基于Python实现的信用卡客户高风险识别毕业设计项目&#xff0c;面向计算机相关专业在校生、课程设计及实训场景&#xff0c;解决从数据探索、清洗到聚类建模的完整流程。围绕历史信用风险、经济风险与收入风险三个维度&#xff0c;通过K-Means算法构建…

作者头像 李华
网站建设 2026/9/14 4:48:44

Claude 跑 MCP 增强 Selenium:模型 Key 用 TaoToken

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

作者头像 李华
网站建设 2026/9/14 4:48:22

FOC电流采样硬核指南:单/双/三电阻选型与ADC时序避坑

1. 这不是理论推导&#xff0c;是炸过三次MOS管后写下的电流采样实操手册FOC电流采样这件事&#xff0c;说白了就是让控制器“看清”电机绕组里真实流过的电流。但现实很骨感&#xff1a;你按教科书接好单电阻、设好ADC触发点、跑通SVPWM&#xff0c;一上电——“砰”一声&…

作者头像 李华