文章目录
- 1. matlab程序
- 2. mel spectrogram
- 2.1 原始语音
- 2.2 合成语音
- 3. 引用
1. matlab程序
通过延时叠加波生成机器声音的质感
clear;clc;
% 读取原始mp3
filename = 'download.wav';
[original_audio,Fs] = audioread(filename);
original_audio = original_audio(:,1);
audioplayer(original_audio,Fs).playblocking;
T = 1/Fs;
L = length(original_audio);
t = transpose((0:L-1)*T);
% 只进行延时重复
min_delay=500;
max_delay=2000;
num_delayed=2; %重复2次
delay=floor(linspace(min_delay,max_delay,num_delayed));
delayed_audio = zeros(length(original_audio)+max(delay),num_delayed);
delayed_t = transpose((0:length(delayed_audio)-1)/Fs);
for i=1:num_delayed
delayed_audio(delay(i)+1:(size(delayed_audio,1)-(max(delay)-delay(i))),i) = original_audio(:);
end
delayed_audio_sum = sum(delayed_audio,2);%叠加
audioplayer(delayed_audio_sum,Fs).playblocking;%试听叠加效果
%audiowrite("download_repeat2_noise.wav",delayed_audio_sum,Fs)
% 只进行回声
k=0.5;
D=1000;
A=zeros(1,D-1);
%final_audio=filter(1,[1 A -k],delayed_audio_sum);
final_audio=filter(1,[1 A -k],original_audio);
audioplayer(final_audio,Fs).playblocking;%试听机器人声
%audiowrite("download_echo_noise.wav",final_audio,Fs)
% 进行延时重复+回声
k=0.5;
D=1000;
A=zeros(1,D-1);
%final_audio=filter(1,[1 A -k],delayed_audio_sum);
final_audio=filter(1,[1 A -k],delayed_audio_sum);
audioplayer(final_audio,Fs).playblocking;%试听机器人声
%audiowrite("download_repeat2+echo_noise.wav",final_audio,Fs)
语音download
把原始语音延迟若干个不同的时间,然后叠加。采用的参数为:总共叠加 10 份,最小延迟为 500 个采样点,最大延迟为 2000 个采样点。他使用的语音采样率是 16 kHz,那么相邻两份的时间差就是:(2000 - 500) / 9 / 16000 = 0.0104 s = 10.4 ms。
为什么这样处理会产生「都是一声」的听感呢?这就需要用到信号处理里的这个结论了:时域重复等于频域采样。在时域上每隔 10.4 ms 重复一次,相当于在频域中每隔 1 / (10.4 ms) = 96 Hz 采一次样。这其实就是用梳状滤波器对语音进行滤波,梳子的齿所在的频率都是 96 Hz 的倍数。滤波的效果如下面的视频所示:梳状滤波器会破坏掉语谱图原有的谐波结构,而生成一套新的谐波结构,相邻谐波的间距都是 96 Hz。你看,基频变成常数了——所以语音听起来就「都是一声」了。
2. mel spectrogram
- Text:黑化肥发灰会挥发,灰化肥挥发会发黑
语音的音高,是由「基频」决定的。在语谱图上,语音看起来是「排骨」状的,每一根骨头叫做一个「谐波」,相邻谐波的间隔就是基频。比如「黑化肥发灰会挥发,灰化肥挥发会发黑」的语谱图就是下面这样的。注意「黑」这种一声字的谐波基本是水平的,而「化肥」这种声调有升降的字,谐波也有升降。
2.1 原始语音
2.2 合成语音
- 只重复2遍
- 只添加回声
- 重复2遍后添加回声
- 重复10遍后添加回声