【语音识别】基于matlab GUI拨号语音识别【含Matlab源码 1753期】

举报
海神之光 发表于 2022/05/28 22:42:44 2022/05/28
【摘要】 一、获取代码方式 获取代码方式1: 完整代码已上传我的资源:【语音识别】基于matlab GUI拨号语音识别【含Matlab源码 1753期】 获取代码方式2: 通过订阅紫极神光博客付费专栏,凭支付凭...

一、获取代码方式

获取代码方式1:
完整代码已上传我的资源:【语音识别】基于matlab GUI拨号语音识别【含Matlab源码 1753期】

获取代码方式2:
通过订阅紫极神光博客付费专栏,凭支付凭证,私信博主,可获得此代码。

备注:
订阅紫极神光博客付费专栏,可免费获得1份代码(有效期为订阅日起,三天内有效);

二、DTMF简介

1 含义
双音多频 DTMF(Dual Tone Multi Frequency),双音多频,由高频群和低频群组成,高低频群各包含4个频率。一个高频信号和一个低频信号叠加组成一个组合信号,代表一个数字。DTMF信令有16个编码。利用DTMF信令可选择呼叫相应的对讲机。
双音多频信号(DTMF),电话系统中电话机与交换机之间的一种用户信令,通常用于发送被叫号码。

在使用双音多频信号之前,电话系统中使用一连串的断续脉冲来传送被叫号码,称为脉冲拨号。脉冲拨号需要电信局中的操作员手工完成长途接续。
双音多频信号是贝尔实验室发明的,其目的是为了自动完成长途呼叫。
双音多频的拨号键盘是4×4的矩阵,每一行代表一个低频,每一列代表一个高频。每按一个键就发送一个高频和低频的正弦信号组合,比如’1’相当于697和1209赫兹(Hz)。交换机可以解码这些频率组合并确定所对应的按键。

DTMF编解码器在编码时将击键或数字信息转换成双音信号并发送,解码时在收到的DTMF信号中检测击键或数字信息的存在性。一个DTMF信号由两个频率 的音频信号叠加构成。这两个音频信号的频率来自两组预分配的频率组:行频组或列频组。每一对这样的音频信号唯一表示一个数字或符号。电话机中通常有16个 按键,其中有10个数字键0~9和6个功能键*、#、A、B、C、D。由于按照组合原理,一般应有8种不同的单音频信号。因此可采用的频率也有8种,故称 之为多频,又因它采用从8种频率中任意抽出2种进行组合来进行编码,所以又称之为“8中取2”的编码技术。根据CCITT的建议,国际上采用的多种频率为 687Hz、770Hz、852Hz、941Hz、1209Hz、1336Hz、1477Hz和1633Hz等8种。用这8种频率可形成16种不同的组 合,从而代表16种不同的数字或功能键,具体组合见表1。

在很多应用中都要求进行音调检测,例如:双音多频信号 (DTMF)解码,呼叫过程(拨号音、忙音等)解码,频率响应测试(发送一个音调,同时将结果读回)。在频率响应测试中,如果在一定频率范围内进行测量, 那么得到的频响曲线中可能会包含丰富的信息,例如从电话线的频响曲线可以知道线上是否有负载线圈(电感)。
尽管针对以上应用均有专用IC,但采用软件来实现这些芯片的功能时所需成本比采用专用芯片低很多。然而,很多嵌入式系统都不具备进行连续实时FFT处理的能力,这时就适合采用Goertzel算法。本文将对Goertzel基本算法和Goertzel优化算法进行讨论。
采 用Goertzel基本算法能得出与常规离散傅立叶变换(DFT)或FFT相同的频率实部和虚部。如果需要的话,还可以从该频率实部和虚部中算出幅度和相 位信息。Goertzel优化算法则比Goertzel基本算法更快也更简单,但Goertzel优化算法并不给出频率实部和虚部分量,它只能给出相关的 幅度平方。如果需要幅度信息,可通过对该结果开方得到,但该方法无法得到相位信息。

2 Goertzel基本算法
Goertzel 基本算法在每次采样后立即进行处理,在每个第N次采样进行一次音调检测。在采用FFT算法时,我们要对成块的采样进行处理,但这并不意味着必须按块来处理 数据。数字处理的时间很短,因此如果每次采样都存在一次中断,那么这些数字处理完全可以在中断服务程序(ISR)内完成。或者,如果系统中存在采样缓存, 那么可以持续采样,然后进行批处理。
在真正运行Goertzel算法之前,必须进行下面的初步计算:

  1. 决定采样率;
  2. 选择块大小,即N;
  3. 预先进行一次余弦和正弦计算;
  4. 预先计算一个系数。
    这些计算均可以预先完成,然后硬编码到程序中,从而节省RAM和ROM空间,也可以动态方式计算。

3 选择合适的采样率
实际上,采样率可能已经由应用本身决定了。例如,在电信应用中普遍采用8kHz的采样率,即每秒8,000个采样。又如,模数转换器(或编解码器)的工作频率可能是由一个我们无法控制的外部时钟或外部晶振决定。
但如果我们可以选择采样率,那么就必须遵循奈奎斯特采样定理:采样率至少不低于最高信号频率的两倍。这是是因为如果我们要检测多个频率,那么采用更高的采样率可能会得到更好的结果。而且我们都希望采样率与每一个感兴趣的频率之间均呈整数倍关系。

4 块大小的设置
Goertzel算法中的块大小N与相应的FFT中的点数类似,它控制了频率分辨率的大小。例如,若采样率为8kHz,而N为100个采样,那么频率分辨率就是80Hz。
这就可能使我们为了获取最大的频率分辨率而尽量将N取高。然而N越大,检测到每个音调所需的时间就越多,因为我们必须等所有这N个采样都完成后才能开始处理。例如,采样率为8kHz时,累积800个采样需要100ms。若想缩短检测音调的时间,就必须适当调整N的值。
影响N的选择的另一个因素是采样率和目标频率之间的关系。比较理想情况是目标频率在相应的频率分辨率的中点范围内,也就是说,我们希望目标频率是sample_rate/N比值的整数倍。值得庆幸的是,Goertzel算法中的N与FFT中不同,不必是2的整数次幂。

5 预计算常数
在采样率和块大小确定之后,只须通过下面5个简单的计算来得出处理时所需要的常数:
k = (Ntarget_freq)/sample_tate
w = (2
π/N)*k
cosine = cos w
sine = sin w
coeff = 2 * cosine
每一次采样处理中都需要3个变量,我们称其为Q0’、Q1’和Q2。Q1是前一次采样处理的Q0值,Q2是在两次采样前的Q0值(或Q1在本次采样前的值)。
在每个采样块的开始时,都必须将Q1和Q2初始化为0。每个采样都需要按照下面三个等式进行计算:
Q0 = coeff * Q1 - Q2 + sample
Q2 = Q1
Q1 = Q0
在进行N次预采样计算之后,可以检测到音调是否存在。
real = (Q1 - Q2 * cosine)
imag = (Q2 * sine)
magnitude2 = real2 + imag2
这时只需进行一次简单的幅度门限测试就可以判断出是否有音调存在。之后,将Q2和Q1复位到0,开始下一个块的处理。

6 Goertzel优化算法
Goertzel优化算法比Goertzel基本算法所需的计算量小,但这是以损失相位信息为代价。
在 Goertzel优化算法中每个采样处理完全一样,但处理的结果与Goertzel基本算法不同。在Goertzel基本算法中,通常需要计算信号的实部 和虚部,然后将实部和虚部的计算结果转换为相应的幅度平方。而在优化Goertzel算法中则不需计算实部和虚部,直接计算下式:
magnitude2 = Q12 + Q22-Q1Q2coeff

三、部分源代码

function varargout = VoiceRecognition(varargin)
% VOICERECOGNITION MATLAB code for VoiceRecognition.fig
%      VOICERECOGNITION, by itself, creates a new VOICERECOGNITION or raises the existing
%      singleton*.
%
%      H = VOICERECOGNITION returns the handle to a new VOICERECOGNITION or the handle to
%      the existing singleton*.
%
%      VOICERECOGNITION('CALLBACK',hObject,eventData,handles,...) calls the local
%      function named CALLBACK in VOICERECOGNITION.M with the given input arguments.
%
%      VOICERECOGNITION('Property','Value',...) creates a new VOICERECOGNITION or raises the
%      existing singleton*.  Starting from the left, property value pairs are
%      applied to the GUI before VoiceRecognition_OpeningFcn gets called.  An
%      unrecognized property name or invalid value makes property application
%      stop.  All inputs are passed to VoiceRecognition_OpeningFcn via varargin.
%
%      *See GUI Options on GUIDE's Tools menu.  Choose "GUI allows only one
%      instance to run (singleton)".
%
% See also: GUIDE, GUIDATA, GUIHANDLES

% Edit the above text to modify the response to help VoiceRecognition

% Last Modified by GUIDE v2.5 08-Apr-2020 19:08:03

% Begin initialization code - DO NOT EDIT
gui_Singleton = 1;
gui_State = struct('gui_Name',       mfilename, ...
                   'gui_Singleton',  gui_Singleton, ...
                   'gui_OpeningFcn', @VoiceRecognition_OpeningFcn, ...
                   'gui_OutputFcn',  @VoiceRecognition_OutputFcn, ...
                   'gui_LayoutFcn',  [] , ...
                   'gui_Callback',   []);
if nargin && ischar(varargin{1})
    gui_State.gui_Callback = str2func(varargin{1});
end

if nargout
    [varargout{1:nargout}] = gui_mainfcn(gui_State, varargin{:});
else
    gui_mainfcn(gui_State, varargin{:});
end
% End initialization code - DO NOT EDIT
%%

% --- Executes just before VoiceRecognition is made visible.
function VoiceRecognition_OpeningFcn(hObject, eventdata, handles, varargin)
% This function has no output args, see OutputFcn.
% hObject    handle to figure
% eventdata  reserved - to be defined in a future version of MATLAB
% handles    structure with handles and user data (see GUIDATA)
% varargin   command line arguments to VoiceRecognition (see VARARGIN)

% Choose default command line output for VoiceRecognition
handles.output = hObject;

% Update handles structure
guidata(hObject, handles);

% UIWAIT makes VoiceRecognition wait for user response (see UIRESUME)
% uiwait(handles.figure1);
%%

% --- Outputs from this function are returned to the command line.
function varargout = VoiceRecognition_OutputFcn(hObject, eventdata, handles) 
% varargout  cell array for returning output args (see VARARGOUT);
% hObject    handle to figure
% eventdata  reserved - to be defined in a future version of MATLAB
% handles    structure with handles and user data (see GUIDATA)

% Get default command line output from handles structure
varargout{1} = handles.output;
%%

% --- Executes on button press in pushbutton2.
function pushbutton2_Callback(hObject, eventdata, handles)
% hObject    handle to pushbutton2 (see GCBO)
% eventdata  reserved - to be defined in a future version of MATLAB
% handles    structure with handles and user data (see GUIDATA)
TextOut1 = '录音中';
set( handles.edit1, 'String', TextOut1 ); % 显示处理数据在交互界面
myrecorder = audiorecorder(44100,16,1);
recordblocking(myrecorder,8);
recorder_array = getaudiodata(myrecorder);
recorder_array = recorder_array';
% pause(1);
audiowrite('录音文件.wav',recorder_array,44100);
TextOut2 = '录音完成';
set( handles.edit1, 'String', TextOut2 ); % 显示处理数据在交互界面
%%

% --- Executes on button press in pushbutton3.
function pushbutton4_Callback(hObject, eventdata, handles)
% hObject    handle to pushbutton3 (see GCBO)
% eventdata  reserved - to be defined in a future version of MATLAB
% handles    structure with handles and user data (see GUIDATA)
% 初始化相关参数
load('recorder_filter.mat');%load滤波器设置,带通600-1600
bohao = [697,1209;697,1336;697,1477;770,1209;770,1336;770,1477;852 1209;852 1336;852 1477;941 1336];%1-9-0的频率
[recorder,fs]=audioread('生成音频文件.wav');%录音文件
% sound(recorder,fs);
N = length(recorder);%音频文件的长度
% figure(1);plot((1:N)/fs,recorder);

% 对录音进行滤波
recorder = filter(recorder_filter,1,recorder);
recorder(abs(recorder)<0.001) = 0;

% 求短时能量
wlen=200; inc=80;          % 给出帧长和帧移
win=hanning(wlen);         % 给出海宁窗
X=enframe(recorder,win,inc)';     % 分帧
fn=size(X,2);              % 求出帧数
time=(0:N-1)/fs;           % 计算出信号的时间刻度
for i=1 : fn
    u=X(:,i);              % 取出一帧
    u2=u.*u;               % 求出能量
    En(i)=sum(u2);         % 对一帧累加求和
end
frameTime=frame2time(fn,wlen,inc,fs);   % 求出每帧对应的时间
figure(2);
subplot 211; plot(time,recorder); % 画出时间波形 
title('MORSE语音波形');
ylabel('幅值'); xlabel(['时间/s' 10 '(a)']);
subplot 212; plot(frameTime,En)     % 画出短时能量图
title('短时能量');
ylabel('幅值'); xlabel(['时间/s' 10 '(b)']);

% 通过对短时能量求反,利用findpeaks函数找波谷
En_reverse = [];
En_reverse = max(En)*3 - En;%取反
[minv,minl]=findpeaks(En_reverse,'minpeakdistance',100);%找波谷,波谷间隔为100帧
hold on;plot(frameTime(minl),En(minl),'o','color','r');hold off;

% 对音频进行分割,得到单独的单一拨号的片段
En(En<0.00001) = 0;
target = En(minl);
point = [];
for i =1:length(minl)
    point(i) = find(time==frameTime(minl(i)));
end

  
 
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14
  • 15
  • 16
  • 17
  • 18
  • 19
  • 20
  • 21
  • 22
  • 23
  • 24
  • 25
  • 26
  • 27
  • 28
  • 29
  • 30
  • 31
  • 32
  • 33
  • 34
  • 35
  • 36
  • 37
  • 38
  • 39
  • 40
  • 41
  • 42
  • 43
  • 44
  • 45
  • 46
  • 47
  • 48
  • 49
  • 50
  • 51
  • 52
  • 53
  • 54
  • 55
  • 56
  • 57
  • 58
  • 59
  • 60
  • 61
  • 62
  • 63
  • 64
  • 65
  • 66
  • 67
  • 68
  • 69
  • 70
  • 71
  • 72
  • 73
  • 74
  • 75
  • 76
  • 77
  • 78
  • 79
  • 80
  • 81
  • 82
  • 83
  • 84
  • 85
  • 86
  • 87
  • 88
  • 89
  • 90
  • 91
  • 92
  • 93
  • 94
  • 95
  • 96
  • 97
  • 98
  • 99
  • 100
  • 101
  • 102
  • 103
  • 104
  • 105
  • 106
  • 107
  • 108
  • 109
  • 110
  • 111
  • 112
  • 113
  • 114
  • 115
  • 116
  • 117
  • 118
  • 119
  • 120
  • 121
  • 122
  • 123
  • 124
  • 125
  • 126
  • 127
  • 128
  • 129
  • 130
  • 131
  • 132
  • 133
  • 134
  • 135
  • 136
  • 137
  • 138
  • 139
  • 140
  • 141
  • 142

四、运行结果

在这里插入图片描述

五、matlab版本及参考文献

1 matlab版本
2014a

2 参考文献
[1]韩纪庆,张磊,郑铁然.语音信号处理(第3版)[M].清华大学出版社,2019.
[2]柳若边.深度学习:语音识别技术实践[M].清华大学出版社,2019.

文章来源: qq912100926.blog.csdn.net,作者:海神之光,版权归原作者所有,如需转载,请联系作者。

原文链接:qq912100926.blog.csdn.net/article/details/123290357

【版权声明】本文为华为云社区用户转载文章,如果您发现本社区中有涉嫌抄袭的内容,欢迎发送邮件进行举报,并提供相关证据,一经查实,本社区将立刻删除涉嫌侵权内容,举报邮箱: cloudbbs@huaweicloud.com
  • 点赞
  • 收藏
  • 关注作者

评论(0

0/1000
抱歉,系统识别当前为高风险访问,暂不支持该操作

全部回复

上滑加载中

设置昵称

在此一键设置昵称,即可参与社区互动!

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。