使用Python把树莓派改造成一个语音助手

CSDN广告邮件太多了,邮箱已经屏蔽了CSDN,留言请转SegmentFault:https://segmentfault.com/a/1190000014000349

语音助手已经不是什么新事物了。就在两三年前,语音助手的使用体验还不是那么好,尝尝鲜后也就没用过了。但最近发现不管是微软的Cortana、苹果的Siri,还是一些不怎么有名气的,例如MIUI的小爱同学等,使用体验真的改善了很多,确确实实能带来一些方便了。

随着各种云服务、API的面世,语音方面的云服务可以说是十分健全了。你是否也想过自己动手搭建一个语音助手系统呢?本文将总结使用Python把树莓派(3代b型)改造成一个简易语音助手的基本流程。

概述

这次要做的说白了,就是把各种云服务、API串起来,并不涉及任何核心技术、算法的实现,望知悉。

这次将要使用到的服务包括:

  • 谷歌Cloud Speech API
  • 图灵机器人
  • 科大讯飞 语音合成WebAPI

为了实现这个语音助手系统,需要完成的工作每一个都不难,但数量稍多了些。以下是涉及到的一些博客:

  • 使用Google云计算引擎实现科学上网
  • 在Windows命令行、Linux终端使用代理
  • 树莓派学习手记——使用Python录音
  • 在Python中使用谷歌Cloud Speech API将语音转换为文字(另一种方案)
  • 使用Python与图灵机器人聊天
  • 在Python中使用科大讯飞Web API进行语音合成

后文在介绍各部分的具体实现时,只附上代码和进行一些必要的说明,详细内容还需要参考相应博客。

各部分的实现

由于整个项目用到的服务比较多,而且各部分的分工很明显,所以选择各部分分别用一个python程序来实现,最后再用一个程序整合在一起的方式。

录音

参考:树莓派学习手记——使用Python录音

笔者采用了“按住按钮进行录音”的操作方式,如下图所示接线。如果你手头上没有按钮或觉得这么做不方便,可以修改代码改成“按回车键开始/结束录音”之类的操作方式。

另外,树莓派的板载3.5mm耳机接口是不带语音输入功能的,所以你需要另外购买USB声卡。

***** 文件 rec.py

import RPi.GPIO as GPIO
import pyaudio
import wave
import os
import sysdef rec_fun():# 隐藏错误消息,因为会有一堆ALSA和JACK错误消息,但其实能正常录音os.close(sys.stderr.fileno())BUTT = 26	# 开始录音的按钮:一边接GPIO26,一边接地GPIO.setmode(GPIO.BCM)# 设GPIO26脚为输入脚,电平拉高,也就是说26脚一旦读到低电平,说明按了按钮GPIO.setup(BUTT, GPIO.IN, pull_up_down = GPIO.PUD_UP)# wav文件是由若干个CHUNK组成的,CHUNK我们就理解成数据包或者数据片段。CHUNK = 512 FORMAT = pyaudio.paInt16  # pyaudio.paInt16表示我们使用量化位数 16位来进行录音RATE = 44100  # 采样率 44.1k,每秒采样44100个点。WAVE_OUTPUT_FILENAME = "/home/pi/chat/command.wav"print('请按住按钮开始录音...')GPIO.wait_for_edge(BUTT, GPIO.FALLING)# To use PyAudio, first instantiate PyAudio using pyaudio.PyAudio(), which sets up the portaudio system.p = pyaudio.PyAudio()stream = p.open(format = FORMAT,channels = 1,	# cloud speecAPI只支持单声道rate = RATE,input = True,frames_per_buffer = CHUNK)print("录音中...")frames = []# 按住按钮录音,放开时结束while GPIO.input(BUTT) == 0:data = stream.read(CHUNK)frames.append(data)print("录音完成,输出文件:" + WAVE_OUTPUT_FILENAME + '\n')stream.stop_stream()stream.close()p.terminate()wf = wave.open(WAVE_OUTPUT_FILENAME, 'wb')wf.setnchannels(1)wf.setsampwidth(p.get_sample_size(FORMAT))	# Returns the size (in bytes) for the specified sample format.wf.setframerate(RATE)wf.writeframes(b''.join(frames))wf.close()return# 可以直接运行rec.py进行测试,同时保证该文件import时不会自动运行
if __name__ == '__main__':rec_fun()

语音识别

参考:

使用Google云计算引擎实现科学上网

在Windows命令行、Linux终端使用代理

在Python中使用谷歌Cloud Speech API将语音转换为文字(另一种方案)

由于某些原因,笔者选择了使用谷歌Cloud Speech API进行语音识别。既然要用谷歌的服务,自然就涉及到了科学上网、代理、谷歌云平台的使用,如果不想这么折腾,完全可以用国内的讯飞、百度来实现。

另外,API KEY之类的字符串在这里删除了,还请麻烦修改代码加上你自己申请的API KEY。

***** 文件 speech_api.py

import json
import urllib.request
import base64def wav_to_text():api_url = "https://speech.googleapis.com/v1beta1/speech:syncrecognize?key=替换成你的API密钥"print('语音文件编码中...')audio_file = open('/home/pi/chat/command.wav', 'rb')audio_b64str = (base64.b64encode(audio_file.read())).decode()audio_file.close()voice = {"config":{"languageCode": "cmn-Hans-CN"},"audio":{"content": audio_b64str}}voice = json.dumps(voice).encode('utf8')print('编码完成。正在上传语音...')req = urllib.request.Request(api_url, data=voice, headers={'content-type': 'application/json'})response = urllib.request.urlopen(req)response_str = response.read().decode('utf8')response_dic = json.loads(response_str)if ('results' not in response_dic.keys()):print('您录制的文件似乎没有声音,请检查麦克风。')returntranscript = response_dic['results'][0]['alternatives'][0]['transcript']confidence = response_dic['results'][0]['alternatives'][0]['confidence']result_dic = {'text':transcript ,'confidence':confidence}print('识别完成。以字典格式输出:')print(result_dic)return result_dicif __name__ == '__main__':wav_to_text()

获取文字回答

参考:使用Python与图灵机器人聊天

这个获取回答的程序有些粗糙,只能获得普通的文字回答。实际上图灵机器人回复的内容中包括了文字、问题类型甚至情感等信息,还有很多修改的空间。

***** 文件 turing.py

import json
import urllib.requestdef chat(question):api_url = "http://openapi.tuling123.com/openapi/api/v2"text_input = question['text']req = {"perception":{"inputText":{"text": text_input},"selfInfo":{"location":{"city": "上海","province": "上海","street": "文汇路"}}},"userInfo": {"apiKey": "替换成你的APIKEY","userId": "用户参数"}}# 将字典格式的req转为utf8编码的字符串req = json.dumps(req).encode('utf8')print('\n' + '正在调用图灵机器人API...')http_post = urllib.request.Request(api_url, data=req, headers={'content-type': 'application/json'})response = urllib.request.urlopen(http_post)print('得到回答,输出为字典格式:')response_str = response.read().decode('utf8')response_dic = json.loads(response_str)intent_code = response_dic['intent']['code']# 返回网页类的输出方式if(intent_code == 10023):results_url = response_dic['results'][0]['values']['url']results_text = response_dic['results'][1]['values']['text']answer = {"code": intent_code, "text": results_text, "url":results_url}print(answer)return(answer)# 一般的输出方式else:results_text = response_dic['results'][0]['values']['text']answer = {"code": intent_code, "text": results_text}print(answer)return(answer)if __name__ == '__main__':eg_question = {'text': '今天是几号', 'confidence': 0.9}chat(eg_question)

读出回答(语音合成)

参考:在Python中使用科大讯飞Web API进行语音合成

笔者在使用讯飞Web API时,该服务才开放不到一周,难免以后该API会有所变动,如有问题建议查阅官方文档。

***** 文件 tts.py

import base64
import json
import time
import hashlib
import urllib.request
import urllib.parse
import osdef speak(text_content):# API请求地址、API KEY、APP ID等参数,提前填好备用api_url = "http://api.xfyun.cn/v1/service/v1/tts"API_KEY = "替换成你的APIKEY"APP_ID = "替换成你的APPID"AUE = "lame"# 构造输出音频配置参数Param = {"auf": "audio/L16;rate=16000",	#音频采样率"aue": AUE,	#音频编码,raw(生成wav)或lame(生成mp3)"voice_name": "xiaoyan","speed": "50",	#语速[0,100]"volume": "10",	#音量[0,100]"pitch": "50",	#音高[0,100]"engine_type": "aisound"	#引擎类型。aisound(普通效果),intp65(中文),intp65_en(英文)}# 配置参数编码为base64字符串,过程:字典→明文字符串→utf8编码→base64(bytes)→base64字符串Param_str = json.dumps(Param)	#得到明文字符串Param_utf8 = Param_str.encode('utf8')	#得到utf8编码(bytes类型)Param_b64 = base64.b64encode(Param_utf8)	#得到base64编码(bytes类型)Param_b64str = Param_b64.decode('utf8')	#得到base64字符串# 构造HTTP请求的头部time_now = str(int(time.time()))checksum = (API_KEY + time_now + Param_b64str).encode('utf8')checksum_md5 = hashlib.md5(checksum).hexdigest()header = {"X-Appid": APP_ID,"X-CurTime": time_now,"X-Param": Param_b64str,"X-CheckSum": checksum_md5}# 构造HTTP请求Bodybody = {"text": text_content}body_urlencode = urllib.parse.urlencode(body)body_utf8 = body_urlencode.encode('utf8')# 发送HTTP POST请求print('\n' + "正在调用科大讯飞语音合成API...")req = urllib.request.Request(api_url, data=body_utf8, headers=header)response = urllib.request.urlopen(req)# 读取结果response_head = response.headers['Content-Type']if(response_head == "audio/mpeg"):out_file = open('/home/pi/chat/answer.mp3', 'wb')data = response.read() # a `bytes` objectout_file.write(data)out_file.close()print('得到结果,输出文件: /home/pi/chat/answer.mp3')else:print(response.read().decode('utf8'))# 播放音频print("播放音频中...")print("以下均为mplayer的输出内容\n")os.system("mplayer -ao alsa:device=hw=1.0 /home/pi/chat/answer.mp3")returnif __name__ == '__main__':eg_text_content = "苟利国家生死以,岂因祸福避趋之"speak(eg_text_content)

整合&测试

现在,你的项目文件夹中应该有这些python代码文件:

接下来我们只需要将他们整合在一起运行。

***** 文件 combine.py

# 这些import进来的模块是同目录下的py文件
import rec	# rec.py负责录制wav音频
import speech_api	# speech_api.py负责wav转文字
import turing	# turing.py负责获得图灵机器人的文字回答
import tts	# tts.py负责读出回答rec.rec_fun()	# 录制音频
recognize_result = speech_api.wav_to_text()	# 识别语音,返回值是字典格式,包含文字结果和信心
turing_answer = turing.chat(recognize_result)	# 得到图灵的回答,返回值仍是字典格式
tts.speak(turing_answer['text'])

如果一切顺利的话,实际运行效果如下:

http://v.youku.com/v_show/id_XMzQ4OTg3MjYzNg==.html

小结

语音助手这边的工作算是告一段落了,结果小结却不知道怎么写了。不管怎么说,很开心最后能得到实际的结果,做的过程中也有一些脑洞想要继续扩展,过段时间应该还会继续!

做这个项目的过程中,项目外的收获或许比这个项目本身还要多。这段时间从很多博客、论坛得到了数不尽的帮助,国内的、国外的、中文的、英文的、日文的都有,深深地感受到了互联网共享精神的力量,这也是促使我开始写这些文章的原因。那么,最后还是说一句:感谢你阅读文章!

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

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

相关文章

AI对话-Free Chat免费无限制

目录 前言 使用方法 提问 推荐线路 前言 chat.4 和 chat.5 线路的响应改成通过在 Netlify 的部署来响应了。Netlify 不像 Vercel 那样还限制 Edge Function 的调用次数,很适合部署本项目。现在这两个线路的成本最低了,最优先推荐大家使用。 使用方法 提问 比如我问他:…

掌握唯米系统ChatGPT批量生成文章的操作技巧

以下是重写后的操作步骤: 1. 购买会员并添加个人的ChatGPT密钥: 首先,您需要购买唯米系统的会员,并获得访问ChatGPT的权限。随后,您可以将个人的ChatGPT密钥添加到系统中,以便使用该功能进行自然语言生成和…

ChatGPT批量生成文章软件:创意无限,智能驱动文章

随着人工智能技术的不断发展,ChatGPT批量生成文章软件成为了当今互联网世界中备受瞩目的创新之一。作为一种基于大规模预训练语言模型的自然语言处理工具,ChatGPT能够以人类般的方式与用户进行对话,并且能够生成高质量的文章。这一技术的出现…

ChatGPT3.5 AI智能高质量原创文章批量生成器 API方式多个key多线程写文章

1、ChatGPT3.5是一种基于自然语言处理技术的模型,可以模拟人类写作和思考的过程,生成通顺、有逻辑、富有创造性的文章。 2、使用ChatGPT3.5,您可以快速轻松地生成各种类型的文章,无论是新闻报道、产品说明、营销宣传、科技评论&a…

技术科普与解读:ChatGPT 大模型硬核解读!(一)家族历史从GPT-1到ChatGPT

多模态,指的是融合文本、图像、视频或音频等多种模态作为输入或输出。 GPT-4是严格意义上的多模态模型,可以支持图像和文字两类信息的同时输入,输出为文本。从学术界的分析来看,无论是知识/能力获取还是与现实物理世界的交互&…

【宏观经济学】chatGPT会让我们失业吗?

文章链接:chatGPT会让我们失业吗?

Transformer模型详解

2013年----word Embedding 2017年----Transformer 2018年----ELMo、Transformer-decoder、GPT-1、BERT 2019年----Transformer-XL、XLNet、GPT-2 2020年----GPT-3 Transformer 谷歌提出的Transformer模型,用全Attention的结构代替的LSTM,在翻译上取得了更…

阐述说明NLP发展历史,以及 NLP与chatgpt的关系

自然语言处理(Natural Language Processing,NLP)是人工智能(AI)领域的一个重要分支,关注计算机与人类(自然)语言之间的交互。NLP的目标是使计算机能够理解、生成和解释自然语言&…

【GPT】你需要了解的 ChatGPT的技术原理- Transformer架构及NLP技术演进

目录 概述 The Concept of Transformers and Training A Transformers ModelTransformers 的概念和训练 Transformers 模型

思科模拟器之端口聚合技术

端口聚合也叫做以太通道(ethernet channel),主要用于交换机之间连接。由于两个交换机之间有多条冗余链路的时候,STP会将其中的几条链路关闭,只保留一条,这样可以避免二层的环路产生。 工作原理&#xff1a…

如何在群晖NAS上安装cpolar内网穿透

系列文章 做内网穿透外网远程访问群晖NAS 1-2做内网穿透外网远程访问群晖NAS 2-2如何在群晖NAS上安装cpolar内网穿透配置群晖NAS中的cpolar开机自启动 1-2配置群晖NAS中的cpolar开机自启动 2-2为公网远程访问群晖NAS配置固定域名 1-2为公网远程访问群晖NAS配置固定域名 2-2 上…

如何使用cpolar内网穿透群晖NAS套件

系列文章 如何安装cpolar内网穿透群晖NAS套件如何使用cpolar内网穿透群晖NAS套件 上一篇: 如何安装cpolar内网穿透群晖NAS套件 在上一篇介绍里,我们在群晖系统中成功安装了图形化界面的cpolar,由于cpolar从命令行界面转入图形化界面&#xf…

QNAP威联通NAS搭建SFTP服务,并内网穿透实现公网远程访问

文章目录 前言1. 威联通NAS启用SFTP2. 测试局域网访问3. 内网穿透3.1 威联通安装cpolar内网穿透3.2 创建隧道3.3 测试公网远程访问 4. 配置固定公网TCP端口地址4.1 保留一个固定TCP端口地址4.2 配置固定TCP端口地址4.3 测试使用固定TCP端口地址远程连接威联通SFTP 转载自远程内…

cpolar内网穿透将本地的论坛网站发布公网访问 2/2

在上篇文章中,我们成功的在本地部署了一个论坛网站,我们有了邀请同事或游友加入并分享各自的想法和乐趣的基础。现在,我们就要通过cpolar建立一条长期稳定存续的数据隧道,并通过这个数据隧道,将这个论坛发布到公共互联…

华为防火墙地址映射(NATserver)

287、实验:NATserver映射 实验topo: 将内网DMZ安全域的http服务映射出外网,并且不让DMZ的服务器主动去访问外网: 做完策略之后点击诊断,测试服务器的存活性: 做安全策略,允许local访问dmz&#…

如何在群晖nas中使用cpolar内网穿透

系列文章 cpolar内网穿透远程访问连接群晖nas如何在群晖nas中使用cpolar内网穿透 上一篇: cpolar内网穿透远程访问连接群晖nas 在上一篇介绍里,我们在群晖系统中成功安装了图形化界面的cpolar,由于cpolar从命令行界面转入图形化界面&#xf…

使用cpolar内网穿透远程访问家里的群晖NAS

在现代企业中,协同办公和数据共享的作用已经受到广泛认可,而群晖作为小型数据处理中心,也已经进入很多公司,并成为局域网内的数据存储和处理中心。但如果需要在公共互联网访问公司内的群晖NAS的情况时,公网设备无法直接…

群晖NAS使用VPN套件实现异地映射

目前异地访问NAS数据越来越频繁,之前分享的使用WebDAV实现异地访问的方法虽然可以满足小文件的传输,由于WebDAV协议限制,无法实现大文件的传输,此教程指导大家如何使用群晖VPN Server来实异地映射传输大文件。 由于政策所限&#…

如何安装cpolar内网穿透群晖NAS套件

系列文章 如何安装cpolar内网穿透群晖NAS套件如何使用cpolar内网穿透群晖NAS套件 cpolar作为一款高效安全的内网穿透软件,在很多场景中都可以得到应用,特别对于开发人员,更是增加工作效率的好帮手。但对于一般用户,cpolar的命令行…

Cisco Packet Tracer 思科模拟器利用NAT实现外网主机访问内网服务器

前两篇讲解了动态NAT地址转换,以及静态NAT地址转换,本篇文章主要讲解如何理由NAT实现外网主机访问内网服务器,含有重分布教学 情境分析 公司只申请了一个公网IP地址,基于私有地址与公有地址不能直接通信的原则,公网的…