2017-09-15 11:17:22 qq_36047509 阅读数 1921
  • 智能家居与物联网 从入门到精通 HomeAssistant实战...

    本课程通过一步步的实践演示,带领大家在开源项目的基础上,搭建随心所欲的物联网与智能家居平台。在过程实践中,大家会学习与应用到linux、python、云服务、图像识别、智能语音、单片机、数据库、前端开发等多方面的知识,帮助大家成为IT的全栈工程师。以实战为导向结合物联网各类知识要点学习经典框架进行项目实战,快速掌握智能家居、家庭自动化、物联网等必备基础与实战技巧。带你从零玩转智能家居,了解物联网的整体格局,将零散的知识点通过项目快速串联提升自身成就感 【更新规则】  视频与参考文档内容,随时更新,与最新的软件版本/云服务环境匹配。 【课程特色】 1.通俗易懂,快速入门 对物联网、智能家居学习经典实践项目结合技术推导进行形象解释,实例演示。 2. Python主导,实用高效 使用物联网领域最主流语言Python及其homeassistant 开源家庭自动化框架作为课程核心工具。 3. 案例为师,实战护航 基于真实操作展示,从零开始结合homeassistant与python自创组件、树莓派或者nas完成整个案例实战。 4. 持续更新,一劳永逸 会伴随homeassistant的更新与DIY实战项目课程会支持更新下去,逐步加入更多算法与案例。 【联系我们】 官方网站:https://www.hachina.io QQ学习讨论群(仅限学员加入):741140729

    3780 人正在学习 去看看 朱继盛

本软件利用了百度语音识别提供的接口,自行开发出的一个在线的语音识别软件。所以,制作之前需要去百度语音识别的网站去注册一个项目,免费的除非你的需求量特别大不然不需要付费。百度语音识别地址
然后就需要自己写代码去解决以下问题

  • 获取麦克风输入的语音
  • 发送到百度语音识别的接口
  • 得到返还的信息识别。

获取麦克风输入的语音

要获取麦克风的输入,需要调用一些WindowsAPI及其他的东西。下面就慢慢梳理 我会分散的梳理,整合需要自己理解着去整合
首先,我们获取麦克风,使用winmm.dll

//调用wavein的dll
[DllImport("winmm.dll")]
//获取有多少可用输入设备
public static extern int waveInGetNumDevs();
[DllImport("winmm.dll")]
//增加一个缓冲区
public static extern int waveInAddBuffer(IntPtr hwi, ref WaveHdr pwh, UInt32 cbwh);
[DllImport("winmm.dll")]
//关闭麦克风
public static extern int waveInClose(IntPtr hwi);
[DllImport("winmm.dll")]
//打开麦克风
public static extern int waveInOpen(out IntPtr phwi, UInt32 uDeviceID, ref WaveFormatEx lpFormat, WaveDelegate dwCallback, UInt32 dwInstance, UInt32 dwFlags);
[DllImport("winmm.dll")]
//标记为可用的缓冲区
 public static extern int waveInPrepareHeader(IntPtr hWaveIn, ref WaveHdr lpWaveInHdr, UInt32 uSize);
[DllImport("winmm.dll")]
//标记为不可用的缓冲区
public static extern int waveInUnprepareHeader(IntPtr hWaveIn, ref WaveHdr lpWaveInHdr, UInt32 uSize);
[DllImport("winmm.dll")]
//把缓冲区内容重置
 public static extern int waveInReset(IntPtr hwi);
[DllImport("winmm.dll")]
//开始录制
public static extern int waveInStart(IntPtr hwi);
[DllImport("winmm.dll")]
//停止录制
public static extern int waveInStop(IntPtr hwi);

然后 我们要把接收到的波形数据放入到一个缓冲区里面

[StructLayout(LayoutKind.Sequential)]
    //接受的波形数据放入的缓冲区
    public struct WaveHdr
    {

        public IntPtr lpData;//缓冲区
        public UInt32 dwBufferLength;//缓冲区长度
        public UInt32 dwBytesRecorded;//某一刻读取到了多少字节的数据
        public UInt32 dwUser;//自定义数据
        public UInt32 dwFlags;
        public UInt32 dwLoops;//是否循环
        public IntPtr lpNext;//链表的下一缓冲区
        public UInt32 reserved;//没实际意义
    }

    [StructLayout(LayoutKind.Sequential)]
    //波形格式
    public struct WaveFormatEx
    { 
        public UInt16 wFormatTag;//波形的类型
        public UInt16 nChannels;//通道数(1,单声道   2,立体音)
        public UInt32 nSamplesPerSec;//采样率
        public UInt32 nAvgBytesPerSec;//字节率
        public UInt16 nBlockAlign;
        public UInt16 wBitsPerSample;//每个样多少位
        public UInt16 cbSize;//长度
    }

但是在这里我们需要一个delegate的委托事件,其作用是在缓冲区满了或者waveinopen和waveinclose的时候被调用。

public delegate void WaveDelegate(IntPtr hwi, UInt32 uMsg, UInt32 dwInstance, UInt32 dwParam1, UInt32 dwParam2);

上传到百度识别的接口

在全部获取到麦克风语音接收的信息之后,我们需要把识别的波形上传到百度识别的接口上,在这里我们就用HTTP协议来将我们获得的东西上传上去

    /// <summary>
        /// 通过HTTP协议去上传base64数据
        /// </summary>
        /// <param name="URL">服务器的url</param>
        /// <param name="strPostdata">上传的东西</param>
        /// <param name="strEncoding">采用的编码格式</param>
        /// <returns></returns>
        public static string OpenReadWithHttps(string URL, string strPostdata, string strEncoding)
        {
            Encoding encoding = Encoding.Default;
            //默认的编码格式为default(GB2312)
            HttpWebRequest request = (HttpWebRequest)WebRequest.Create(URL);
            //向自定义的URL链接发送请求 request
            request.Method = "post";
            //请求的方式为post
            request.Accept = "*/*";
            //告诉服务器能接受*/*(任意)的参数类型
            request.ContentType = "application/x-www-form-urlencoded";
            //最常见的post提交数据的方式
            byte[] buffer = encoding.GetBytes(strPostdata);
            //用一个byte数组接收发送的数据字节
            request.ContentLength = buffer.Length;
            //告诉服务器自己上传的数组长度
            request.GetRequestStream().Write(buffer, 0, buffer.Length);
            //写入请求流从第一位开始写入buffer数组,写入长度为buffer.Length的数据流
            HttpWebResponse response = (HttpWebResponse)request.GetResponse();
            //从服务器得到的数据为请求获得的数据
            using (StreamReader reader = new StreamReader(response.GetResponseStream(), Encoding.GetEncoding(strEncoding)))
            {
                //返回从URL获得的内容信息
                return reader.ReadToEnd();
            }
        }

判断是否在录入音频

每个语音都是一个缓冲区,等缓冲区满了,要提供新缓冲区,等缓冲区满了,要提供新缓冲区

static void waveInHandler(IntPtr hwi, UInt32 uMsg, UInt32 dwInstance, UInt32 dwParam1, UInt32 dwParam2)
        {
            switch (uMsg)
            {
                case 0x3BE: break;
                case 0x3C0:
                    unsafe
                    {
                        var waveHdr = (WaveHdr*)dwParam1;
                     }
                    break;
                case 0x3BF: break;
            }
        }

Main函数总结

小的模块说的差不多了,下面就从Main函数说起,中间还会穿插一些小的模块
首先我们设置波纹的格式

static void Main(string[] args)
        {
            try
            {
                var inputFormat = new WaveFormatEx();//波形格式
                inputFormat.wFormatTag = 1;//波形类型
                inputFormat.nChannels = 1;
                inputFormat.nSamplesPerSec = 8000;
                inputFormat.nAvgBytesPerSec = 16000;
                inputFormat.nBlockAlign = 2;
                inputFormat.wBitsPerSample = 16;
                inputFormat.cbSize = 0;

由于我们是语音识别不是就识别一次,所以我们下面要进入一个死循环

这里我们在等候语音的输入

                for (;;)
                {

                    waveInOpen(out inputDevice, UInt32.MaxValue, ref inputFormat, new WaveDelegate(waveInHandler), 0, 0x00030000);

                    int bufferSize = 960000;
                    var buffer1 = new WaveHdr();
                    buffer1.lpData = Marshal.AllocHGlobal(bufferSize);
                    buffer1.dwBufferLength = (UInt32)bufferSize;
                    buffer1.dwLoops = 1;
                    waveInPrepareHeader(inputDevice, ref buffer1, (UInt32)Marshal.SizeOf(typeof(WaveHdr)));
                    waveInAddBuffer(inputDevice, ref buffer1, (UInt32)Marshal.SizeOf(typeof(WaveHdr)));

                    SpeechRecognitionEngine recognizer = null;
                    foreach (var installed in SpeechRecognitionEngine.InstalledRecognizers())
                    {
                        if (installed.Culture.Name.Equals("zh-CN", StringComparison.CurrentCultureIgnoreCase) && installed.Id.Equals("MS-2052-80-DESK"))
                        {
                            recognizer = new SpeechRecognitionEngine(installed);
                            break;
                        }
                    }
                    var grammars = new GrammarBuilder();
                    grammars.AppendDictation();
                    recognizer.LoadGrammar(new Grammar(grammars));
                    recognizer.SetInputToDefaultAudioDevice();

                    bool recognizeStarted = false;
                    int speechCount = 0;
                    int silenceCount = 0;

                    Console.WriteLine("正在等候语音输入...");
                    recognizer.RecognizeAsync(RecognizeMode.Multiple);
                    waveInStart(inputDevice);

当说话的时候开始分析语音

for (;;)
                    {
                                               if (!recognizeStarted)
                        {
                            if (recognizer.AudioState == AudioState.Speech)
                                speechCount++;
                            else speechCount = 0;
                        }
                        if (!recognizeStarted && speechCount >= 2)
                        {
                            recognizeStarted = true;
                            speechCount = 0;
                            Console.WriteLine("检测到语音输入,正在录制...");
                        }
                        if (recognizeStarted)
                        {
                            if (recognizer.AudioState == AudioState.Silence)
                                silenceCount++;
                            else silenceCount = 0;
                        }
                        //checkingMutex.Set();
                        if (recognizeStarted && silenceCount >= 220)
                        {
                            //checkingMutex.Reset();
                            silenceCount = 0;
                            unsafe
                            {
                                Console.WriteLine("正在分析语音数据...");

                                waveInReset(inputDevice);
                                waveInStop(inputDevice);
                                recognizer.RecognizeAsyncStop();

在上面的代码中有判断环境噪音的代码

if (recognizer.AudioState == AudioState.Silence)
                                silenceCount++;
                            else silenceCount = 0;

silenceCount 就是统计静音状态持续了多久,到了一定值,就可以发送语音到识别平台了

然后我们就要用到百度给予的接口和key了

                          var apiKey = "百key";
                                var secretKey = "百度给的密码key";
                                var token = OpenReadWithHttps("百度给你提供的API接口地址http" + $"?grant_type={ "client_credentials" }&client_id={ apiKey }&client_secret={ secretKey }", String.Empty, "utf-8");
                                var tokenPrefix = "\"access_token\":[\"";
                                int i;
                                token = token.Substring(i = token.IndexOf(tokenPrefix) + tokenPrefix.Length + 1, token.IndexOf("\"", i + tokenPrefix.Length) - i);

                                var postData = new StringBuilder();
                                postData.Append("{").Append($"\"format\":\"pcm\",\"rate\":8000,\"channel\":1,\"token\":\"{ token }\",\"cuid\":\"F96625D0-0FBC-491C-B617-9EC0B3A0D5A6\",\"lan\":\"en\",");
                                var base64Data = new byte[buffer1.dwBytesRecorded];
                                Marshal.Copy(buffer1.lpData, base64Data, 0, (int)buffer1.dwBytesRecorded);
                                var base64 = Convert.ToBase64String(base64Data);
                                postData.Append("\"speech\":\"").Append(base64).Append("\",").Append($"\"len\":{ buffer1.dwBytesRecorded }").Append("}");
                                try
                                {
                                    Console.Write("\n识别结果: ");
                                    Marshal.FreeHGlobal(buffer1.lpData);
                                    var result = OpenReadWithHttps("http://vop.baidu.com/server_api", postData.ToString(), "utf-8");
                                    var prefix = "\"result\":[\"";
                                    result = result.Substring(i = result.IndexOf(prefix) + prefix.Length, result.LastIndexOf("\"]") - i + 1);
                                    string[] restt = result.Split('\"');
                                    var restlt = restt[0];
                                    Console.WriteLine(restlt);
                                    //string resultfinally = Recognize(restlt);
                                    try
                                    {
                                        string resultfinally = Recognize(restlt);
                                        loading(resultfinally, "word.txt");
                                    }
                                    catch (Exception ex)
                                    {
                                        Console.WriteLine(ex.Message);
                                        //(new SpVoiceClass()).Speak("你说的有些不标准,请重新说");
                                    }
                                    Console.WriteLine();
                                }
                                catch (Exception ex)
                                {
                                    Console.WriteLine("无法识别所说的话语。\n");

                                }
                                //checkingMutex.Set();
                            }
                            //checking.Dispose(checkingFinished);
                            break;
                        }
                        Thread.Sleep(1);
                    }

                    //checkingFinished.WaitOne();
                }
            }
            catch (Exception exception)
            {
                Console.WriteLine(exception);
            }

        }
    }
}

在这里你会发现,我做了一个语音识别和回复,识别目录下的文档里的内容,然后对比,对比到以后将下一句转换为语音。需要用到两个自定义的函数
第一个是判断你说的话是否是在给定的文本里面

  public static void loading(string listen, string url)
        {
            var file = File.OpenRead(url);
            var sr = new StreamReader(file);
            List<string> include = new List<string>();
            while (!sr.EndOfStream)
            {
                var str = sr.ReadLine();
                foreach (var chara in str)
                    if (!char.IsLetter(chara))
                        str = str.Replace(chara, ' ');
                str = str.Trim();
                include.Add(str);
            }
            for (int i = 0; i < include.Count; i++)
            {
                if (String.Compare(listen.Trim(), include[i].Trim(), StringComparison.CurrentCultureIgnoreCase) == 0)
                {
                    SpeechSynthesizer speaker = new SpeechSynthesizer();
                    speaker.SetOutputToDefaultAudioDevice();
                    speaker.Speak(include[i + 1]);
                    return;
                }
            }
            SpeechSynthesizer speak = new SpeechSynthesizer();
            speak.SetOutputToDefaultAudioDevice();
            speak.Speak("口音有问题,请重说。");
            throw new Exception("口音有问题,请重说。");
        }

第二个是判断是否跟自定义的语句匹配并说出下一句

public static string Recognize(string getin)
        {
            var responses = new string[]
            {
               "楼主帅吗",
               "当然了",
               "聪明吗",
               "必须的",
             //你想写和你想输出的语句
            };
            getin = getin.ToLower();
            foreach (var chara in getin)
                if (!char.IsLetter(chara))
                    getin = getin.Replace(chara, ' ');
            getin = getin.Trim();
            int matches;
            var k = getin.Split();
            for(var i = 0; i < responses.Length; i++)
            {
                responses[i] = responses[i].ToLower();
                foreach (var chara in responses[i])
                    if (!char.IsLetter(chara))
                        responses[i] = responses[i].Replace(chara, ' ');
                responses[i] = responses[i].Trim();
            }
            foreach (var repWord in responses)
            {
                matches = 0;
                var j = repWord.Split();
                foreach (var myword in k)
                {
                    if (j.Contains(myword))
                    {
                        matches++;
                        if (((float)matches / j.Length) >= 0.5F)
                            return repWord;
                    }
                }
            }
            return "你说错了,请重说";
        }

这里还是有一个小问题,就是你说的语句返识别返还回来会有标点符号,这里我们就把符号全部给抛弃了
我这边做的是英语的语音识别,在发送的json串的时候最后的len用的是en,在语种选择的时候是不区分大小写的,但是好像只支持三种默认中文(zh)。 中文=zh、粤语=ct、英文=en。
总的来说就这些东西,如果有什么疑问和建议或者纠正,可以直接告诉我,期待大神们的指点。

此外。在此特别感谢给我这个程序最大的技术支持的人。我们群里的大佬RURI(也叫Azure)。

2012-06-09 00:38:53 wimigame 阅读数 1648
  • 智能家居与物联网 从入门到精通 HomeAssistant实战...

    本课程通过一步步的实践演示,带领大家在开源项目的基础上,搭建随心所欲的物联网与智能家居平台。在过程实践中,大家会学习与应用到linux、python、云服务、图像识别、智能语音、单片机、数据库、前端开发等多方面的知识,帮助大家成为IT的全栈工程师。以实战为导向结合物联网各类知识要点学习经典框架进行项目实战,快速掌握智能家居、家庭自动化、物联网等必备基础与实战技巧。带你从零玩转智能家居,了解物联网的整体格局,将零散的知识点通过项目快速串联提升自身成就感 【更新规则】  视频与参考文档内容,随时更新,与最新的软件版本/云服务环境匹配。 【课程特色】 1.通俗易懂,快速入门 对物联网、智能家居学习经典实践项目结合技术推导进行形象解释,实例演示。 2. Python主导,实用高效 使用物联网领域最主流语言Python及其homeassistant 开源家庭自动化框架作为课程核心工具。 3. 案例为师,实战护航 基于真实操作展示,从零开始结合homeassistant与python自创组件、树莓派或者nas完成整个案例实战。 4. 持续更新,一劳永逸 会伴随homeassistant的更新与DIY实战项目课程会支持更新下去,逐步加入更多算法与案例。 【联系我们】 官方网站:https://www.hachina.io QQ学习讨论群(仅限学员加入):741140729

    3780 人正在学习 去看看 朱继盛

语音识别很好,而JAVA想要开发一款苦于没有好的引擎,科大讯飞的很好但没有JAVA SDK 是不是很闹心,这篇文章主要是针对新手想要开发一款桌面的语音识别软件。

我知道JAVA开发桌面应用软件并不是那么的强大,但我只会JAVA肿么办呢。

OK , 下面介绍一下方法:


           开发环境:JAVA + 科大讯飞WINDOW    SDK

           我们主要是使用JNI来开发


           首先下载我提供的 哦 不是(是某位仁兄提供的JAR 包)稍后更新这人的网名  并感谢他一下,因为我学会了调用这种东西 哈哈哈

           JAR包的地址我等会更新啊

           JAR包地址:http://download.csdn.net/detail/wimigame/4361888

           然后新建JAVA PROJECT项目

           实例化   MSC

           代码如下

            public void say(){

                  MSC ms=new MSC();

                  ms.TTS(第一个参数是连接地址和appid等参数,第二个是param参数具体参看科大讯飞帮助手册,第三个是要转换的文字,第四个是要保存的文件名);

}

            调用一下say方法    完成后就可看到工程项目下面多了一个第四个参数命名的文件。        

2018-11-28 11:44:27 Aria_Miazzy 阅读数 164
  • 智能家居与物联网 从入门到精通 HomeAssistant实战...

    本课程通过一步步的实践演示,带领大家在开源项目的基础上,搭建随心所欲的物联网与智能家居平台。在过程实践中,大家会学习与应用到linux、python、云服务、图像识别、智能语音、单片机、数据库、前端开发等多方面的知识,帮助大家成为IT的全栈工程师。以实战为导向结合物联网各类知识要点学习经典框架进行项目实战,快速掌握智能家居、家庭自动化、物联网等必备基础与实战技巧。带你从零玩转智能家居,了解物联网的整体格局,将零散的知识点通过项目快速串联提升自身成就感 【更新规则】  视频与参考文档内容,随时更新,与最新的软件版本/云服务环境匹配。 【课程特色】 1.通俗易懂,快速入门 对物联网、智能家居学习经典实践项目结合技术推导进行形象解释,实例演示。 2. Python主导,实用高效 使用物联网领域最主流语言Python及其homeassistant 开源家庭自动化框架作为课程核心工具。 3. 案例为师,实战护航 基于真实操作展示,从零开始结合homeassistant与python自创组件、树莓派或者nas完成整个案例实战。 4. 持续更新,一劳永逸 会伴随homeassistant的更新与DIY实战项目课程会支持更新下去,逐步加入更多算法与案例。 【联系我们】 官方网站:https://www.hachina.io QQ学习讨论群(仅限学员加入):741140729

    3780 人正在学习 去看看 朱继盛

按:本文原作者 Cindi Thompson,美国德克萨斯大学奥斯汀分校(University of Texas at Austin)计算机科学博士,数据科学咨询公司硅谷数据科学(Silicon Valley Data Science,SVDS)首席科学家,在机器学习、自然语言处理等领域具有丰富的学术研究和产业界从业经验。雷锋网编译。

作为 SVDS 研究团队的成员,我们会经常接触各种不同的语音识别技术,也差不多见证了语音识别技术近几年的发展。直到几年之前,最先进的语音技术方案大多都是以语音为基础的(phonetic-based),包括发音模型(Pronunciation models),声学模型(Acoustic Modelling)和语言模型(Language Model)等。通常情况下,这些模型大多都是以隐马尔可夫模型(HMM)和 N-gram 模型为核心的。未来,我们希望以这些传统模型为基础,探索一些诸如与百度 Deep Speech 等最新的语音识别系统相结合的新技术。当然,目前互联网上可以找到许多针对这些基础模型进行解释、汇总的文章和资料,但针对它们之间的差别和特点展开阐述的却并不多。

为此,我们对比了五款基于 HMM 和 N-gram 模型的语音识别工具:CMU Sphinx,Kaldi,HTK,Julius 和 ISIP。它们都是开源世界的顶级项目,与 Dragon 和 Cortana 等商业语音识别工具不同,这些开源、免费的工具可以为开发者提供更大的自由度以及更低的开发成本,因此在开发圈始终保持着强大的生命力。

需要提前说明的是:以下分析大多来源于我们的主观经验,同时也参考了互联网上的其他信息。而且这篇文章也并非一个覆盖所有语音识别开源工具的汇总类文章,我们只是对比了其中五款相对更主流的产品。另外,HTK 并不是严格开源的,它的代码并不能重新组织发布,也不能用于商业用途。

想知道更多语音识别工具的用户请点击以下链接,其中列出了几乎所有开源/非开源的语音识别工具,非常全面。

https://en.wikipedia.org/wiki/List_of_speech_recognition_software

编程语言:
根据你对不同编程语言的熟悉程度,你可能会更偏爱某一种工具。如上图所示,这里列出的五款工具中,除了 ISIP 只支持 C++ 之外,全都支持 Python。你可以直接在它们的官网找到不同语言对应的下载链接。不过,Python 版有可能并不会覆盖工具包的全部功能,有些功能还可能是为其他语言的特性单独设计的。另外值得注意的是,CMU Sphinx 还支持 Java、C 和其他更多语言。

开发者活跃度:
这里列出的五个项目均源于学术研究。

从名字也能看出,CMU Sphinx 是一款源于卡内基梅隆大学的产品。它的研发历史大约可以追溯到 20 年前,目前在 GitHub 和 SourceForge 平台同步更新。在 GitHub 平台有 C 和 Java 两个版本,而且据说分别只有一个管理员维护。但在 SourceForge 平台却有 9 个管理员和十几个开发者。

Kaldi 源于 2009 年的一场研讨会,代码目前在 GitHub 平台开源,共有 121 位贡献者。

HTK 始于 1989 年的剑桥大学,曾一度商业化,但目前又回归剑桥。如前所述 HTK 现在并不是一款严格意义的开源工具,而且更新缓慢(虽然它的最新版本更新于 2015 年 12 月,但前一个版本的更新时间却是 2009 年,中间隔了差不多 6 年时间)。

Julius 始于 1997 年,最后一个主要版本更新于 2016 年 9 月,据称其 GitHub 平台有三名管理员维护。

ISIP 是第一个比较先进的开源语音识别系统,起源于密西西比州。它主要在 1996 年到 1999 年之间研发,最后一个版本发布于 2011 年,在 GitHub 平台出现之前就已经停止更新了。

社区活跃度:
这一部分我们考察了上述五个工具的邮件和社区讨论情况。

CMU Sphinx 的论坛讨论热烈,回帖积极。但其 SourceForge 和 GitHub 平台存在许多重复的 repository。相比之下,Kaldi 的用户则拥有更多交互方式,包括邮件、论坛和 GitHub repository 等。HTK 有邮件列表,但没有公开的 repository。Julius 官网上的论坛链接目前已经不可用,其日本官网上可能有更详细的信息。ISIP 主要用于教育目的,其邮件列表目前已不可用。

教程和示例:
CMU Sphinx 的文档简单易读,讲解深入浅出,且贴近实践操作。

Kaldi 的文档覆盖也很全面,但是在我看来更难理解。而且,Kaldi 同时包括了语音识别解决方案中的语音和深度学习方法。

如果你并不熟悉语音识别,那么可以通过对 HTK 官方文档(注册后可以使用)的学习对该领域有一个概括的认识。同时,HTK 的文档还适用于实际产品设计和使用等场景。

Julius 专注于日语,其最新的文档也是日语,但团队正在积极推动英文版的发布。

以下链接提供了一些基于 Julius 的语音识别样例。

https://github.com/julius-speech/dictation-kit

最后是 ISIP,虽然它也有一些文档,但是并不系统。

预训练模型:
即使你使用这些开源工具的主要目的是想要学习如何去训练一个专业的语音识别模型,但一个开箱即用的预先训练好的模型仍然是一个不可忽略的优点。

CMU Sphinx 包括英语、法语、西班牙语和意大利语在内的诸多可以直接使用的模型,详情可以参考它的说明文档。

Kaldi对现有模型进行解码的指令深藏在文档中,不太容易找到,但我们仍然发现了贡献者在 egs/voxforge 子目录下基于英文 VoxForge 语料库训练好的一个模型,并且还可以通过 online-data 子目录下的一个脚本直接运行。详情可以参考 Kaldi 项目的 repository。

我们没有深入挖掘其他三个软件包的模型训练情况,但它们应该至少包含一些简单可用的预训练模型,而且与 VoxForge 兼容(VoxForge 是一个非常活跃的众包语音识别数据库和经过训练的模型库)。

转载于:https://blog.csdn.net/godloveyuxu/article/details/77416017 原作者:方克明

2019-11-27 16:18:35 ciel_arc 阅读数 20
  • 智能家居与物联网 从入门到精通 HomeAssistant实战...

    本课程通过一步步的实践演示,带领大家在开源项目的基础上,搭建随心所欲的物联网与智能家居平台。在过程实践中,大家会学习与应用到linux、python、云服务、图像识别、智能语音、单片机、数据库、前端开发等多方面的知识,帮助大家成为IT的全栈工程师。以实战为导向结合物联网各类知识要点学习经典框架进行项目实战,快速掌握智能家居、家庭自动化、物联网等必备基础与实战技巧。带你从零玩转智能家居,了解物联网的整体格局,将零散的知识点通过项目快速串联提升自身成就感 【更新规则】  视频与参考文档内容,随时更新,与最新的软件版本/云服务环境匹配。 【课程特色】 1.通俗易懂,快速入门 对物联网、智能家居学习经典实践项目结合技术推导进行形象解释,实例演示。 2. Python主导,实用高效 使用物联网领域最主流语言Python及其homeassistant 开源家庭自动化框架作为课程核心工具。 3. 案例为师,实战护航 基于真实操作展示,从零开始结合homeassistant与python自创组件、树莓派或者nas完成整个案例实战。 4. 持续更新,一劳永逸 会伴随homeassistant的更新与DIY实战项目课程会支持更新下去,逐步加入更多算法与案例。 【联系我们】 官方网站:https://www.hachina.io QQ学习讨论群(仅限学员加入):741140729

    3780 人正在学习 去看看 朱继盛

一、云狐简介

云狐语音识别软件是基于百度智能云,由进击的狐狸进行开发的一款软件。注意,因为核心类代码是2017年就已经写好的了,所以使用的C# SDK包不是最新的。云狐目前支持的平台是Windows系统平台,使用时需要安装微软最新的.net framework 。云狐的主要功能是长时间的语音识别,支持时长超过一分钟的各种类型的语音文件识别,缺点就是速度较慢一些。

云狐视频演示及代码解析的视频链接:

https://v.qq.com/x/page/j3023vgs9yz.html

云狐语音识别软件下载:

https://blog.csdn.net/ciel_arc/article/details/103172138

另外,云狐和云猫实际上是姐妹软件,因为他们都是基于百度智能云,用C#进行开发的,使用的是百度最新的人工智能技术。而且他们目前都是免费的。这里联动一下,对云猫OCR和云狐语音感兴趣的同学,可以百度搜索“云猫OCR”或“云狐语音” 进行了解。

二、云狐的简单评测

云狐软件自带有计时功能,我们可以简单做一下评测。从上文视频演示的结果可以看出,1分钟左右的语音文件,云狐可以在10秒以内识别完毕,而30分钟左右的语音文件,云狐需要120秒即2分钟左右,才能识别完毕。从中推算出识别速度大概是4秒/分钟。

三、云狐软件的代码原理

    百度智能云给出的长语音识别接口只支持一分钟以内的语音文件的识别。而对于超过一分钟的语音文件识别,我们需要怎么做呢?

   云狐软件的原理就是:把超过一分钟的文件进行切片,切成若干个小于或者等于一分钟时长的语音文件。对每个切片文件调用百度云语音识别接口进行识别,再把结果串联起来即可。

四、云狐的代码简明解析

(一)核心类foxSpeechDemo

namespace foxAudio2Word

{

    class foxSpeechDemo

    {

        private readonly Asr _asrClient;

        public foxSpeechDemo(string myAPIKey,string mySecretKey)

        {

            _asrClient = new Asr(myAPIKey,mySecretKey);

        }

        // 识别本地文件

        public string AsrData(string pcmFilePath)

        {

            var data = File.ReadAllBytes(pcmFilePath);

            var result = _asrClient.Recognize(data, "pcm", 16000);

            return result.ToString();

        }

}

}

   上面的代码是根据百度SDK包文档,进行少量改动实现的。注意为了简便,这里贴出的代码段可能跟具体的云狐实现代码有一些出入。

   不是任何一个语音文件都可以交给百度智能云直接识别。文件需要预处理,不然识别效果会很差。具体来说,作者用FFmpeg对语音文件进行预处理,然后再用百度接口识别。FFmpeg的命令行预处理类似下面的形式:

ffmpeg -y  -i 003_16k.wav  -acodec pcm_s16le -f s16le -ac 1 -ar 16000 16k.pcm

(二)预处理的辅助函数

   共有大概4个关于预处理的辅助函数,代码如下:

1.此函数的主要功能是用C#程序自动执行命令行语句,它可执行任何语句的命令行,string cmdStr是形参,可以将命令行语句赋值给cmdStr进行执行。

 private string myCmdFun(string cmdStr)

        {

            try

            {

                Process CmdProcess = new Process();

                CmdProcess.StartInfo.FileName = "cmd.exe";

                CmdProcess.StartInfo.CreateNoWindow = true;         // 不创建新窗口    

                CmdProcess.StartInfo.UseShellExecute = false;       //不启用shell启动进程  

                CmdProcess.StartInfo.RedirectStandardInput = true;  // 重定向输入    

                CmdProcess.StartInfo.RedirectStandardOutput = true; // 重定向标准输出    

                CmdProcess.StartInfo.RedirectStandardError = true;  // 重定向错误输出  

                //CmdProcess.StartInfo.Arguments = "/c " + "=====cmd命令======";//“/C”表示执行完命令后马上退出

                //string cmdStr = "ffmpeg -y  -i 003_16k.wav  -acodec pcm_s16le -f s16le -ac 1 -ar 16000 16k.pcm";

                CmdProcess.StartInfo.Arguments = "/c " + cmdStr;//“/C”表示执行完命令后马上退出  

                CmdProcess.Start();//执行  

                string temp = CmdProcess.StandardOutput.ReadToEnd();//输出  

                CmdProcess.WaitForExit();//等待程序执行完退出进程  

                CmdProcess.Close();//结束

                return temp;

            }

            catch (Exception ex)

            {

                return ex.ToString();

            }

        }

2.此函数表示利用ffprobe命令行获取语音文件的时长信息,以便对语音文件进行分割,注意返回值是整形变量。比如语音时长有1.5分钟,这个函数就会返回2 ,以此类推。

/// 

 

        /// 获取音频文件的持续时间信息

        /// 

 

        /// 

        /// 

        private int foxGetAudioDuration(string filename)

        {

            //使用命令行要非常小心对空格的处理

            string tempCmdStr = "ffprobe -v quiet -print_format json -show_streams "

                + filename;

            string result = myCmdFun(tempCmdStr);

            //结果使用json格式解析

            JObject jo = (JObject)JsonConvert.DeserializeObject(result);

            string audioDuration = jo["streams"][0]["duration"].ToString();

            //直接返回整形数据,单位是秒

            int durationSecond = (int)Math.Ceiling(System.Convert.ToDouble(audioDuration));

            //转成分钟表示

            int durationMinute = (durationSecond / 60) + 1;

            return durationMinute;

        }

3.此函数主要功能是对语音文件进行分割,时间单位是秒。比如我有一个2分钟的语音文件,程序就把这个文件分成2块,每块60秒即1分钟,以此类推。

///分割的时间单位应该是秒

        ///分割音频文件

        private void foxAudioCut(string filename,int timePos,int duration,int fileIndex)

        {

            //string tempCmdStr = "ffmpeg -i 003_16k.wav -ss 10 -t 10 003_1.wav";

            string tempCmdStr = "ffmpeg -y -i "+filename+

                " -ss "+timePos.ToString()

                +" -t "+duration.ToString()

                +" "+ "temp\\" + fileIndex.ToString()+".wav";

 

            myCmdFun(tempCmdStr);

        }

4.此函数的主要功能是把切片文件转换成百度云能够进行正常识别的文件格式。

/// 

 

        /// 把目标音频文件转换为百度语音能够识别的文件

        /// 

 

        /// 

        private string foxAudioConvert(string filename,int fileIndex)

        {

            //临时工作夹目录设置为“temp”

            string resultFileName = "Convert_" + fileIndex.ToString() + ".wav";

            //注意这句含有两个“temp\\”

            string tempCmdStr = "ffmpeg -y  -i "+ "temp\\" + filename

                +"  -acodec pcm_s16le -ac 1 -ar 16000 " 

                + "temp\\" +resultFileName;

            myCmdFun(tempCmdStr);

 

            return resultFileName;

        }

(三)主函数的代码逻辑

//注意:文件路径里面不能含有空格

                    string tempFilePath = Path.GetFullPath(openFileDialog1.FileName);

                    //获取音频文件持续时间信息

                    int duration = foxGetAudioDuration(tempFilePath);

                    //主要的长语音识别逻辑

                    //将音频文件分成块,每块的长度默认为1分钟

                    for (int i = 0; i < duration; i++)

                    {

                        //首先分割文件

                        foxAudioCut(tempFilePath, i * 60, 60, i);

                        //然后转换格式

                        string tempConvertFileName = foxAudioConvert(i.ToString() + ".wav", i);

                        //最后进行识别

                        //tempResult += fd.AsrData("temp\\" + tempConvertFileName);

                        //解析json

                        string tempStr = fd.AsrData("temp\\" + tempConvertFileName);

                        JObject jo = (JObject)JsonConvert.DeserializeObject(tempStr);

                        if (jo["err_no"].ToString().Equals("0"))

                        {

                            string result = jo["result"][0].ToString();

                            tempResult += result;

                        }

                    }

                    richTextBox1.Text = tempResult;

    上面是主函数里面的核心代码段,里面有很多的注释,大家可以仔细看看。主要功能就是整合预处理辅助函数的作用,把文件切片并转换格式,最后提交给百度智能云进行识别,并对识别结果进行解析,把json转换成对人类友好的文本格式。

 

2012-05-25 10:14:57 brucexu1978 阅读数 16955
  • 智能家居与物联网 从入门到精通 HomeAssistant实战...

    本课程通过一步步的实践演示,带领大家在开源项目的基础上,搭建随心所欲的物联网与智能家居平台。在过程实践中,大家会学习与应用到linux、python、云服务、图像识别、智能语音、单片机、数据库、前端开发等多方面的知识,帮助大家成为IT的全栈工程师。以实战为导向结合物联网各类知识要点学习经典框架进行项目实战,快速掌握智能家居、家庭自动化、物联网等必备基础与实战技巧。带你从零玩转智能家居,了解物联网的整体格局,将零散的知识点通过项目快速串联提升自身成就感 【更新规则】  视频与参考文档内容,随时更新,与最新的软件版本/云服务环境匹配。 【课程特色】 1.通俗易懂,快速入门 对物联网、智能家居学习经典实践项目结合技术推导进行形象解释,实例演示。 2. Python主导,实用高效 使用物联网领域最主流语言Python及其homeassistant 开源家庭自动化框架作为课程核心工具。 3. 案例为师,实战护航 基于真实操作展示,从零开始结合homeassistant与python自创组件、树莓派或者nas完成整个案例实战。 4. 持续更新,一劳永逸 会伴随homeassistant的更新与DIY实战项目课程会支持更新下去,逐步加入更多算法与案例。 【联系我们】 官方网站:https://www.hachina.io QQ学习讨论群(仅限学员加入):741140729

    3780 人正在学习 去看看 朱继盛
开源语音识别软件
2009-02-24 9:47

开源语音识别软件simon的第一个测试版已经发布,simon用Julius作实际的语音识别处理引擎,HTK toolkit作为主要的语言模型。这些组件被一个易于使用的图形用户界面连接在一起。simon能够直接输入wiktionary(维基百科的子项目)词典,或者是将个人文本转换成HADIFIX或HTK格式和文法结构后导入。它还提供了一种方法,用新样本和新文字训练语言模型。http://sourceforge.net/projects/speech2text/
     http://julius.sourceforge.jp/en_index.php

     http://htk.eng.cam.ac.uk/

IBM 开发的支持Linux的ViaVoice
    
http://www.nuance.com/viavoice/

2. GPL下的Xvoice

   http://xvoice.sourceforge.net/

    很久以来,与计算机进行交谈一直是科幻小说惯用的故事情节,直到今天真正的交谈也只有在小说中才能实现。但是在过去的十年中,语音识别软件的发展速度非常迅速。目前,市面上出现了多种支持不同操作系统的语音识别控制软件。也许许多人并没有意识到Linux桌面系统也完全可以用声音来控制,并且软件开发人员们已经取得了一定的成果。下面我们就对Linux系统下的语音识别软件进行分析概括,以便帮助大家了解其优势和缺陷。

Linux上的语音识别软件

  Linux系统下的语音控制软件可以为身患残疾或由于过度使用计算机而患计算机综合症的人提供使用Linux系统的机会。此前他们不得不改装其它的操作系统,以获得语音识别技术支持。即使不考虑特殊因素,普通人也可以通过使用语音识别软件,使操作计算机变得更为简单有趣。尽管本文对语音识别系统未来的发展趋势深表忧虑(原因是它们并不能完全把手解放出来),但是它们的确可以分担一部分手的工作。

  目前已经有两种套装软件中含有支持Linux系统的语音控制软件。一种是IBM 开发的支持Linux的ViaVoice,它可以提供一些基本的语音识别功能;另一种是GPL下的Xvoice,它通过ViaVoice库来为桌面系统和应用程序提供语音控制功能。

  IBM 的Linux ViaVoice是美语版本,目前只在美国和加拿大销售。它的售价大约是40美元,包括送货费和一副耳机。用户也可以从IBM的网站上下载ViaVoice,并可享受一定的价格优惠。新版本的ViaVoice在Mandrake 8.0 PowerPack和ProSuite中也可以找到。目前,Mandrake ViaVoice既可以支持英国英语,也可以支持美国英语、法语和德语。Mandrake 8.0以后的版本将不再包含ViaVoice。本文将着重介绍IBM ViaVoice的安装和使用。

应用ViaVoice

  Linux ViaVoice需要机器的配置为:Pentium MMX 233以上的CPU、128MB的内存,以及16位的声卡。实际上,ViaVoice是专门为Red Hat 6.2设计开发的,但是用户在Red Hat 7.3环境和其它Linux版本中也可以正常地运行ViaVoice。当然用户也有可能在安装过程中遇到一些问题。

  在安装ViaVoice语音识别软件前,要首先安装Java运行环境。ViaVoice 1.0和1.1版本是在JRE-1.2.2环境下进行测试的。使用正确的版本可以避免在不同JRE环境下的不兼容。

  JRE安装完毕后,将安装盘放入光驱并运行根目录下的vvsetup,然后再运行vvstartuser将自己设为ViaVoice用户,并且设置好适当的音量,最后便是反复练习,使软件适应自己的声音。切记安装顺序决不能颠倒。

“调教”ViaVoice

  与其它语音识别软件一样,第一次安装的ViaVoice并不能对用户的声音识别得十分准确。使用者必须对它进行一番“调教”,然后才能使它识别使用者的声音。

  “调教”ViaVoice的一种方法就是按照用户手册中的词语反复的朗读。对于大多数用户来说,这一点并不难,但是手册中的词语也许并不是用户经常用到的,因此这个方法的效率并不是很高。

  比较好的方法是在工作时利用ViaVoice的Dictation应用软件。它是用Java语言写成的。当用户进行口述时,一些词语也许不能被正确识别,当这种情况发生时,用户可以使用Dictation中的适当工具对其进行修改。这样ViaVoice便可以对识别工具进行修正,以便更精确地识别用户的声音。这种方法也许会花费较多的力气,但是类似的修改可以用语音命令来完成。不过请注意随时存盘,因为Dictation并不十分稳定。

  曾经有一位专家说,目前的语音识别软件只要经过10到60小时的“调教”,便可以达到98%的正确率。但是到目前为止,对Linux环境下的ViaVoice进行测试的结果是,它的正确率只有92%到95%,绝大多数的语音命令都可以被正确识别。即使用户只花费几个小时进行练习,也可以发现ViaVoice的正确率明显提高。不过用户在使用时要特别注意,词语的发音、麦克风的质量和周围环境都会影响语音识别的正确率。

XVoice控制Linux桌面

  当用户完成ViaVoice的安装并训练了一段时间后,便可以安装Xvoice了。Xvoice的作用是对桌面系统及应用软件进行控制。ViaVoice则没有这些功能。用户可以到xvoice.sourceforge.net去下载Xvoice软件,注意一定要事先安装RPM,因为源程序需要Linux SDK中的ViaVoice中断运行。

  安装完成后,在最后出现的窗口中输入xvoice m,注意不要运行Dictation。这时用户可以做一个简单的测试,口述命令“下一窗口”,桌面上应该出现另一个窗口。

  Xvoice允许用户事先设定好一些操作的口述命令。一套口述命令被称为一个语法组。语法组可以与确定的应用程序、窗口或者应用程序中的某一模块联系在一起,也可以由上下文产生。由口述命令调用的操作可以包括敲键盘、鼠标事件、运行外部命令或三者的任意结合。

  Xvoice使用ViaVoice语音库来识别命令和常规文字。xvoice.xml配置文件可以对命令进行定义。Xvoice使用标准的配置文件,其位置是/usr/share/xvoice/xvoice.xml。当然用户也可以对其位置进行修改,例如可以改为~/.xvoice/xvoice.xml。

  Xvoice的窗口可以显示哪一个命令语法是被击活的,并且窗口中还包括一个面板可以显示最近口述的命令。如果Xvoice认为用户口述的一些词语与某个命令十分相似难以识别,那么在面板中显示的这一命令将是灰色的,以便提醒用户,并且这条命令不会被执行。

  对于任何应用程序窗口,Xvoice都有4种不同的状态。在命令模式下,Xvoice只对命令进行识别;在听写模式下,Xvoice不识别特定的应用程序命令,只是显示出它能识别的词语;在空闲模式下,只有一般命令可以被识别;最后,在命令和听写模式下,口述词语和命令都可以被识别,这时用户需要在命令的前后稍加停顿,以便与文本相区别。

  当用户第一次运行某一应用程序时,Xvoice会自动启动命令模式。如果用户想同时打开听写模式,只需要说“听写模式”便可以了;如果想关闭听写模式,也只需要说“停止听写模式”就万事大吉了。

  当然,最好的方法是将Xvoice窗口置于系统的窗口管理器中,这样你就可以随时了解它的工作情况了。如果你想在开机时便自动运行Xvoice,只要将xvoice m 放入窗口管理器的启动程序中就行了。

声控应用程序

  下面来看一看如何为应用程序定义语法。首先,将要定义语法的软件定义为一个可读的名字,然后为程序的窗口命名一个语句,这样Xvoice便可以识别哪个语法命令是要激活的。在第一行,可以看到一个特殊的固定应用程序名,而它并不是窗口标题。这一特殊的应用程序名必须上下文统一。

  应用程序的标签中包含有听写属性。如果条件为真,则首次运行语句时,Xvoice自动进入听写模式。语句的第二行包含有一些在<define name='numbers'>;区中已经定义过的值。用户可以在定义区中自行定义标记,并应用于整个配置文件中。

  语句的第3行举例说明定义区内可以包含的内容,而这里的命令标记只能在本命令范围内使用。这一行的主要作用是通过语音命令各自的箭头键将彼此互联系起来。当执行命令时,系统会将语音命令与相应的键盘命令对应起来。语音命令的识别转换过程从第4行语句开始。第4行到第8行都是与键盘操作相关的语句,与鼠标相关的语句在第9行到第15行,第16行到第22行是与其它应用程序相关的命令语句,第23行是结束行。

  通过对个人配置文件的编辑,用户几乎可以自动完成过去需要键盘和鼠标才能完成的所有操作过程。许多普通应用软件的语法组,事先已经包含在缺省的配置文件中了,成为用户良好的范例。

语音识别的发展

  Xvoice无法控制一些特殊的应用软件和一些主流游戏软件。对于一些诸如GIMP和Netscape软件来说,虽然Xvoice可以对其进行控制,但是由于此类软件需要大量的鼠标操作,用户会对用语音控制鼠标感到十分厌烦。

  虽然语音识别软件对于大多数命令和一般的文本都可以正确地识别,但是在某些情况下,即使是一个微小的错误也是不允许。语音软件的使用者必须使自已的声音保持稳定。

  另外,虽然XVoice 和ViaVoice可以完成大量的工作,但是用户却无法通过声音控制整个Linux桌面环境。

  IBM公司已经发布了新的ViaVoice,但是只支持Mac 和Windows

 

 

 

开源语音识别软件simon的第一个测试版已经发布,simon用Julius作实际的语音识别处理引擎,HTK toolkit作为主要的语言模型。这些组件被一个易于使用的图形用户界面连接在一起。simon能够直接输入wiktionary(维基百科的子项目)词典,或者是将个人文本转换成HADIFIX或HTK格式和文法结构后导入。它还提供了一种方法,用新样本和新文字训练语言模型。

 

 

 

http://down.htcnc.net/Software/catalog30/1032.html

 

没有更多推荐了,返回首页