首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >使用scipy.signal.spectrogram时出现错误的谱图

使用scipy.signal.spectrogram时出现错误的谱图
EN

Stack Overflow用户
提问于 2018-06-26 12:24:14
回答 3查看 8.9K关注 0票数 11

当我使用matplotlib中的plt.specgram时,生成的谱图是正确的

代码语言:javascript
复制
import matplotlib.pyplot as plt
from scipy import signal
from scipy.io import wavfile
import numpy as np

sample_rate, samples = wavfile.read('.\\Wav\\test.wav')

Pxx, freqs, bins, im = plt.specgram(samples[:,1], NFFT=1024, Fs=44100, noverlap=900)

但是,如果我使用枕页中给出的示例代码生成光谱图,下面的代码如下所示:

代码语言:javascript
复制
import matplotlib.pyplot as plt
from scipy import signal
from scipy.io import wavfile
import numpy as np

sample_rate, samples = wavfile.read('.\\Wav\\test.wav')

frequencies, times, spectrogram = signal.spectrogram(samples[:,1],sample_rate,nfft=1024,noverlap=900, nperseg=1024)

plt.pcolormesh(times, frequencies, spectrogram)
plt.ylabel('Frequency [Hz]')
plt.xlabel('Time [sec]')

为了调试正在发生的事情,我尝试使用第一个方法生成的Pxxfreqsbins,然后使用第二个方法来绘制数据:

代码语言:javascript
复制
plt.pcolormesh(bins, freqs, Pxx)
plt.ylabel('Frequency [Hz]')
plt.xlabel('Time [sec]')

生成的图几乎与第二种方法生成的图相同。因此,似乎scipy.signal.spectrogram毕竟没有问题。问题在于我们绘制图表的方式。我想知道plt.pcolormesh是否是绘制光谱图的正确方法,尽管这种方法是在赋值文件中提出的。

这里也问过一个类似的问题,但还没有解决这个问题的办法。

EN

回答 3

Stack Overflow用户

回答已采纳

发布于 2018-06-26 13:45:19

规格图的默认缩放模式是“dB”(来自散斑文档)

标度:“默认”、“\”、“线性”、“dB”、“”--规范中值的缩放。“线性”不是缩放。‘dB’返回dB比例中的值。当模式是‘psd’,这是dB功率(10 * log10)。否则,这是dB振幅(20 * log10)。默认是‘dB’,如果模式是‘psd’或‘震级’和‘线性’,否则。这必须是‘线性’,如果模式是‘角度’或‘相位’。 模式:‘默认的’\( )-使用什么样的频谱。默认为“psd”,它采用功率谱密度。“复数”返回复值频谱.“震级”返回震级谱。“角”返回相位谱,不需要展开。“相位”通过展开返回相位谱。

为了在pcolormesh中取得类似的结果,您需要对数据进行等效的缩放。

代码语言:javascript
复制
plt.pcolormesh(times, frequencies, 10*np.log10(spectrogram))

我不认为pcolormesh例子的缩放是正确的。您可以在示例中清楚地看到载波,但是添加的噪声信号是不可见的。

票数 18
EN

Stack Overflow用户

发布于 2021-08-04 19:00:43

您应该在您的pcolormesh函数中使用一个非线性颜色图。

尝试设置norm=matplotlib.colors.LogNorm(vmin=np.amin(spectrogram), vmax=np.amax(spectrogram))

norm=matplotlib.colors.PowerNorm(gamma=0.5).

有关更多信息,请参见https://matplotlib.org/stable/tutorials/colors/colormapnorms.html

票数 1
EN

Stack Overflow用户

发布于 2018-10-11 09:19:04

用这个代替:

代码语言:javascript
复制
plt.pcolormesh(times, frequencies, spectrogram, norm = matplotlib.colors.Normalize(0,1))

这将使数据规范化,然后再进行绘图,这样您就可以正确地显示颜色。matplotlib.colors.Colormap上的文档说,“通常用脑图实例将数据值(浮动)从间隔0,1转换为相应的脑图所代表的RGBA颜色。”如果您的值超出此范围,它可能会将其绘制为深色(我相信)。

票数 -1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/51042870

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档