Python 如何使用scipy.signal.spectrogram找到正确的幅值

Python 如何使用scipy.signal.spectrogram找到正确的幅值,python,scipy,fft,Python,Scipy,Fft,我尝试使用scipy.signal.spectogram创建一个量级的spectogram。 不幸的是,我没有让它工作 我的测试信号应该是频率为400 Hz、振幅为1的正弦信号。spect图的大小结果似乎是0.5,而不是1.0。我不知道问题出在哪里 import numpy as np import matplotlib.pyplot as plt from scipy import signal # 2s time range with 44kHz t = np.arange(0, 2, 1

我尝试使用
scipy.signal.spectogram
创建一个量级的spectogram。 不幸的是,我没有让它工作

我的测试信号应该是频率为400 Hz、振幅为1的正弦信号。spect图的大小结果似乎是0.5,而不是1.0。我不知道问题出在哪里

import numpy as np
import matplotlib.pyplot as plt
from scipy import signal

# 2s time range with 44kHz
t = np.arange(0, 2, 1/44000)

# test signal: sine with 400Hz amplitude 1
x = np.sin(t*2*np.pi*440)

# spectogram for spectrum of magnitudes
f, t, Sxx = signal.spectrogram(x,
                               44000,
                               "hanning",
                               nperseg=1000,
                               noverlap=0,
                               scaling="spectrum",
                               return_onesided=True,
                               mode="magnitude"
                              )

# plot last frequency plot
plt.plot(f, Sxx[:,-1])
print("highest magnitude is: %f" %np.max(Sxx))

严格实时的时域信号在频域是共轭对称的。e、 g.将出现在复数结果FFT的正半部分和负半部分(或上半部分)


因此,您需要将FFT结果的两个“一半”相加,以获得总能量(Parseval定理)。或者只是单侧加倍,因为复共轭具有相等的幅度。

这是复F变换(e^(i\omega t)的一个特征。可以得到余弦和正弦项。平方后,可以看到实际频率和负频率的正振幅。(try
return\u oneside=False
)。因此,在你的例子中,你只能看到一半的强度(FFT保留能量,所以你只是没有显示一半)。@roadrunner66:那么,对于非复杂信号,我可以假设“第二面”是镜像的,我可以将幅度加倍?!对于复杂信号(在我的例子中不相关)我会为每个时间片添加翻转的spectrogram的一半?比如'code'Qxx=np.add(np.array_-split(Sxx,2)[0][1:],np.flip(np.array_-split(Sxx,2)[1])是的,也请参见下面的@hotpaw2。