您的量化信号超出了 16 位整数的范围,并且正在削波。
我将在 Octave 中复制并解释这里的情况。任何推论都可以轻松转移到 Python。
Fs = 2000; %Sampling frequency in Hz
T = 2; % Total duration of the a signal in seconds
t = 0:(1./Fs):(T - (1./Fs)); %Time vector in steps of Ts = 1./Fs;
p = 2.0*pi.*t; %Phase vector in radians.
%
% Define the signal
%
s = hamming(length(t))'.*sin(50.*p); %Hamming modulated, 50Hz signal
%
% Let's have a quick look at it
%
subplot(121);plot(s);xlabel('Time');ylabel('Amplitude');grid on;subplot(122);semilogy(abs(fft(s)));xlabel('Frequency bin');ylabel('Amplitude');grid on;
这会产生一些可预测的内容,并且与您在情节左侧呈现的内容一致。

唯一的区别是我使用semilogy的是离散傅里叶变换,它比简单的线性图更好地绘制光谱,因为 DFT 可能产生的总和差异很大。
所以,这并不奇怪,50Hz 干净如哨。现在,让我们以一种直接的方式量化s。
q = int16(round(s.*((2^15)-1))); % Signed integer max is 2^15 MINUS 1
现在,替换上面q的s小绘图线,让我们再看一下信号。

仍然是口哨,但现在不那么干净了。事实上,如果你将它稍微推到int16范围之外,你会得到:
q = int16(round(s.*((2^15)+20)));

虽然,对于人眼来说,它还不能察觉,但波形正在削波,因为从那些奇次谐波的出现中可以明显看出。
如果你继续推...
q = int16(round(s*((2^15)+8000)));

...结果现在几乎相同。
裁剪是intXX函数的结果。如果您尝试“手动”转换为舍入整数,这可能会显示为环绕错误。
希望这可以帮助。
编辑:
下面由 Olli Niemitallo 进行的额外工作足以说服我对此进行更多研究。仍然在 Octave 中,我决定绘制量化残差图。我认为令人惊讶的一点是 16 位量化噪声的幅度。这是我在 Octave 中得到的结果:
Fs = 2000; %Sampling frequency in Hz
T = 2; % Total duration of the a signal in seconds
t = 0:(1./Fs):(T - (1./Fs)); %Time vector in steps of Ts = 1./Fs;
p = 2.0*pi.*t; %Phase vector in radians.
%
% Define the signal
%
s = hamming(length(t))'.*sin(50.*p); %Hamming modulated, 50Hz signal
%
%Up to here the script is the same and it produces the same output (of course). In the following two lines, I quantise in a very straightforward way and obtain the difference between the non-quantised and quantised waveforms
%
sq = int16(round(s*((2^15)-1))); %Signal Quantised
sqdq = double(sq)./((2^15)-1); % Signal quantised and then "de-quantised", notice the division by the absolute maximum, the maximum of the frame of reference, not the maximum of the waveform, this is important.
residual = sqdq-s;
现在,如果我看一下两个域中的残差,它看起来像这样:

这个频谱中有“结构”吗?是的,这个频谱中有(熟悉的)结构,毫无疑问,但是有一个数量级的“结构”e−5原始帖子显示出相当大的峰值。
编辑2:
Olli Niemitalo 发现了不同之处。事实上,如果我们对量化波形进行窗口化,那么我们会看到不同的情况:
Fs = 2000; %Sampling frequency in Hz
T = 2; % Total duration of the a signal in seconds
t = 0:(1./Fs):(T - (1./Fs)); %Time vector in steps of Ts = 1./Fs;
p = 2.0*pi.*t; %Phase vector in radians.
%
% Define the signal
%
s = sin(50.*p); %Hamming modulated, 50Hz signal
%
%Up to here the script is the same and it produces the same output (of course). In the following two lines, I quantise in a very straightforward way and obtain the difference between the non-quantised and quantised waveforms
%
sq = int16(round(s*((2^15)-1))); %Signal Quantised (ONLY THE SINUSOID)
sq2 = int16(round(sq.*hamming(length(sq))')); %Quantised signal windowed
sq2dsq = double(sq2)/((2^15)-1); %"De-quantise"
residual = sq2dsq-(s.*hamming(length(s))');
现在,这描绘了一幅略有不同的画面:

在这种情况下,我认为我自己和 Olli Niemitallo 都被我们所看到的东西所震撼。
“谐波”的真正原因似乎是“调制”。
当您量化时,您确实会使用“锯齿状线”进行波形整形。但是当你在那之后开窗(调制)时,那条“锯齿线”的台阶不再是水平的,而是倾斜的。
这可能真的是我们看到的那些谐波背后的原因。既不是削波,也不是量化,这两者当然都是真正的问题。
我唯一的保留意见是关于这种情况发生的幅度,但我认为对于我们所看到的原因没有任何疑问。
编辑 3:
只需从评论中添加图像,就可以进一步阐明确切的处理类型及其对量化的影响:
