目录

  • 一、写在前面:
  • 二、代码展示:
  • 三、代码调整的思路:
  • 四、总结:
  • 五、网盘链接:



Author:qyan.li

Date:2022.5.15

Topic:简单记录阿里云语音识别API调用


一、写在前面:

java 对接阿里实时语音识别 阿里云语音识别api免费不_API最近的课程设计需要语音识别算法,但由于自己实现能力不够,只能借助于现成的API资源,目前国内比较成熟的包括百度云,阿里云,科大讯飞等等。由于百度云自己之前使用过,无法免费调用,故此次转到阿里云API尝试。

java 对接阿里实时语音识别 阿里云语音识别api免费不_API本篇博文主要记录自己在阿里云API调用中遇到的问题及解决方案。但是需要提醒的是,下述的方案可以保证大家能够使用阿里云API,但肯定不是最优甚至正确的方案,也希望有大佬可以贡献下思路和调用方法。

二、代码展示:

java 对接阿里实时语音识别 阿里云语音识别api免费不_API废话不多说,先上代码,方便大家参考使用,至于为什么这么改,后面会详细说,修改代码操作包含以下三步:

  • 首先,在下载下的SDK文件夹下新建CodeTest.py文件,并将下面的代码拷贝至文件中,保存
# -*- coding = utf-8 -*-

import time
import threading
import sys
import nls

## 阿里云语音识别调用规范(此处信息更换为个人)
URL="********"
AKID="*******"
AKKEY="*********"
APPKEY="*******"

class TestSr:
    def __init__(self,test_file):
        self.__test_file = test_file
   
   ## 读取音频文件内容,存放在self.__data中
    def loadfile(self, filename):
        with open(filename, "rb") as f:
            self.__data = f.read()
    
    def getResult(self):
        self.loadfile(self.__test_file)
        ## type == str而非dict,因此需按照字符串格式进行内容提取
        return self.__test_run().split('"')[-4]

    def __test_run(self):
        sr = nls.NlsSpeechRecognizer(
                    url=URL,
                    akid=AKID,
                    aksecret=AKKEY,
                    appkey=APPKEY
                )
        r = sr.start(aformat="pcm", ex={"hello":123})
        
        ## 将文件数据传递NlsSpeechRecognizer
        self.__slices = zip(*(iter(self.__data),) * 640)
        for i in self.__slices:
            sr.send_audio(bytes(i))
            time.sleep(0.01)

        r = sr.stop()
        
        return sr.result    

t = TestSr("./test.wav") # 参数传入待识别的语音文件
result = t.getResult()
print(result)

'''
识别结果:
省点钱还能买回点东西来行了嗯上海天气超市买东西
'''
  • 在SDK的文件夹下找到_speech_recognizer.py文件(在子文件夹nls下),并在python文件中添加两行代码:
  1. NlsSpeechRecognizer类的构造函数函数末尾添加代码self.result = None,大概在121行左右的位置,注意在构造函数内部,缩进
  2. 在147行左右__sr_core_on_msg函数的末尾添加代码:self.result = msg

致此,代码的修改已经全部完成,你可以测试一下,理论上将应该是可以成功运行获得语音识别的结果。

三、代码调整的思路:

java 对接阿里实时语音识别 阿里云语音识别api免费不_APIOK,首先,代码中删除多线程部分,主要原因在于自己对多线程了解不多,代码难以掌控,其次,自己仅作简单的语音识别,实在也是没有必要添加多线程的处理,故去除此处多线程的代码。

java 对接阿里实时语音识别 阿里云语音识别api免费不_API另外,我解释一下我为什么要添加后面的代码?

java 对接阿里实时语音识别 阿里云语音识别api免费不_API首先,如果你粘贴阿里云官方文档上的代码直接运行,你大概率会看到一连串的语句输出,并且循环往复不停的在执行。并且输出诸多红色字体的语句并在前方伴随着时间信息和DEBUG字符,如下面:

2022-05-29 17:00:23,573 - DEBUG - get token baa04102311f4d099986b83636281002
2022-05-29 17:00:23,574 - DEBUG - ws run...
2022-05-29 17:00:23,574 - DEBUG - wait cond wakeup
2022-05-29 17:00:24,862 - DEBUG - core_on_open:(<nls._core.NlsCore object at 0x00000256C37B3C48>, '{"header": {"message_id": "5441d027d9c7468cb3fcf85b80d78f30", "task_id": "87e6f295fd584e0fa716362c2f0d0aab", "namespace": "SpeechRecognizer", "name": "StartRecognition", "appkey": "kK77KCDsoBijyG7y"}, "payload": {"format": "pcm", "sample_rate": 16000, "enable_intermediate_result": false, "enable_punctuation_prediction": false, "enable_inverse_text_normalization": false, "hello": 123}}')
2022-05-29 17:00:24,862 - DEBUG - notify on open
2022-05-29 17:00:24,862 - DEBUG - wakeup without timeout
2022-05-29 17:00:24,862 - DEBUG - __sr_core_on_open

java 对接阿里实时语音识别 阿里云语音识别api免费不_API按照自己的猜测这应该就是所谓的程序日志。虽然有所耳闻,但毕竟作为学生仅写些小代码的自己哪里见过这等阵仗,但是不要慌:

java 对接阿里实时语音识别 阿里云语音识别api免费不_API仔细观察,会发现其中存在这样的输出:

2022-05-29 17:00:33,017 - DEBUG - core_on_msg:{"header":{"namespace":"SpeechRecognizer","name":"RecognitionCompleted","status":20000000,"message_id":"e277e5e9f9c3403aa8a56c6edb22e854","task_id":"87e6f295fd584e0fa716362c2f0d0aab","status_text":"Gateway:SUCCESS:Success."},"payload":{"result":"省点钱还能买回点东西来行了嗯上海天气超市买东西","duration":9980}}
2022-05-29 17:00:33,017 - DEBUG - __sr_core_on_msg:msg={"header":{"namespace":"SpeechRecognizer","name":"RecognitionCompleted","status":20000000,"message_id":"e277e5e9f9c3403aa8a56c6edb22e854","task_id":"87e6f295fd584e0fa716362c2f0d0aab","status_text":"Gateway:SUCCESS:Success."},"payload":{"result":"省点钱还能买回点东西来行了嗯上海天气超市买东西","duration":9980}} args=()

java 对接阿里实时语音识别 阿里云语音识别api免费不_API看到其中我们喜欢的部分了吗?就是其中的result所对应的value,这不就是我们目标识别的语音内容吗?但是怎么提出出来呢!既然能够显示在python的输出中,就意味着代码中一定存在某个部分是负责这个输出的。那么接下来的任务就变的纯粹,那就是找到这个输出。

java 对接阿里实时语音识别 阿里云语音识别api免费不_API很明显,CodeTest.py的代码中是不可能负责它的输出的,一定是调用的某个文件中存在日志的输出,观察CodeTest.py的代码,代码中出现NlsSpeechRecognizer类的构造,那就从它入手,在CodeTest.py中选中NlsSpeechRecognizer,鼠标右键选择implements即可自动跳转至类的实现。

java 对接阿里实时语音识别 阿里云语音识别api免费不_API在回来观察日志输出,会发现这两个包含语音识别输出的部分前部字符均与core_on_msg有关,那就在_speech_recognizer.py文件中ctrl+f搜索上述字符,会自动对应到一个叫做__sr_core_on_msg的函数的位置,我们仔细观察这个函数:

def __sr_core_on_msg(self, msg, *args):
    _logging.debug("__sr_core_on_msg:msg={} args={}".format(msg, args))
    self.__handle_message(msg)

java 对接阿里实时语音识别 阿里云语音识别api免费不_API发现,这个_logging.debug("__sr_core_on_msg:msg={} args={}".format(msg, args))的代码不就是和我们上面输出的第二个相互对应的嘛?

2022-05-29 17:00:33,017 - DEBUG - __sr_core_on_msg:msg={"header":{"namespace":"SpeechRecognizer","name":"RecognitionCompleted","status":20000000,"message_id":"e277e5e9f9c3403aa8a56c6edb22e854","task_id":"87e6f295fd584e0fa716362c2f0d0aab","status_text":"Gateway:SUCCESS:Success."},"payload":{"result":"省点钱还能买回点东西来行了嗯上海天气超市买东西","duration":9980}} args=()

java 对接阿里实时语音识别 阿里云语音识别api免费不_API只不过此时参数msg以字典的形式给出,参数args没有,ok,我们定位到这里,接下来问题容易解决,既然传入的msg中包含我需要的目标信息(语音识别结果),那么我给出一个接口,外部可以访问msg变量,在进行适当的解析不就可以获得语音识别结果嘛?

java 对接阿里实时语音识别 阿里云语音识别api免费不_API据此,我们添加上面的代码,自定义self.result变量,并在此函数中将msg赋值给self.result变量,外部可访问,即可获得对应的语音识别结果。但需要提醒result并非语音识别的结果,而是包含结果的一串字符串,还需要经过字符串处理才能实现语音识别结果的分离:

result.split('"')[-4]
四、总结:

java 对接阿里实时语音识别 阿里云语音识别api免费不_API上述经过改动的代码可以正常获得语音识别结果的输出,但是识别的速度会比较慢,预估可能需要十秒左右的时间,从识别的时间来看,上述代码基本也没有办法使用。但是这并不影响我们在这其中学习知识,掌握分析代码结构的方式,从这一点上来说,写这篇博文收获也还是有的。

java 对接阿里实时语音识别 阿里云语音识别api免费不_API

五、网盘链接:

自行修改的代码已经上传至网盘,百度网盘链接:

链接:https://pan.baidu.com/s/1sFUhXYUTBElgpSS8v3D2Lg 提取码:uc5e