我使用matplotlib.pyplot.specgram和matplotlib.pyplot.pcolormesh来制作地震信号的频谱图。
背景信息 - 使用pcolormesh的原因是我需要在光谱图数据阵列上进行算术,然后重新绘制得到的谱图(对于三分量地震图 - 东,北和垂直 - 我需要工作超出水平光谱幅度并用水平光谱划分垂直光谱。使用频谱图阵列数据比使用单个幅度光谱更容易做到这一点
我发现进行算术运算后的频谱图有意外的值。经过进一步调查后发现,与使用pyplot.pcolormesh制作的频谱图和pyplot.specgram方法返回的数据数据相比,使用pyplot.specgram方法制作的频谱图具有不同的值。两个图/数组都应该包含相同的值,我无法理解为什么它们没有。
实施例:
的情节plt.subplot(513)
PxN, freqsN, binsN, imN = plt.specgram(trN.data, NFFT = 20000, noverlap = 0, Fs = trN.stats.sampling_rate, detrend = 'mean', mode = 'magnitude')
plt.title('North')
plt.xlabel('Time [s]')
plt.ylabel('Frequency [Hz]')
plt.clim(0, 150)
plt.colorbar()
#np.savetxt('PxN.txt', PxN)
与
的情节有所不同plt.subplot(514)
plt.pcolormesh(binsZ, freqsZ, PxN)
plt.clim(0,150)
plt.colorbar()
即使“PxN”数据数组(即每个分段的频谱图数据值)由第一种方法生成并在第二种方法中重复使用。
有人知道为什么会这样吗?
P.S。我意识到我对NFFT的价值不是一个平方数,但在我编码的这个阶段它并不重要。
P.P.S。我不知道“imN”数组(来自pyplot.specgram的第四个返回变量)是什么以及它用于什么....
答案 0 :(得分:5)
首先,让我们展示一下您所描述的内容的一个例子,以便其他人
private IList<Beneficiary> _beneficiaryList;
public IList<Beneficiary> BeneficiaryList
{
get { return _beneficiaryList; }
set { _beneficiaryList= value; RaisePropertyChanged(() => BeneficiaryList); }
}
public ICommand UpdateBeneficiary=> new MvxCommand<Beneficiary>(item =>
{
//item is of type Beneficiary
//But I do not know which index of BeneficiaryList to update
});
您会立即注意到绘制值的大小差异。
默认情况下,import numpy as np
import matplotlib.pyplot as plt
np.random.seed(1)
# Brownian noise sequence
x = np.random.normal(0, 1, 10000).cumsum()
fig, (ax1, ax2) = plt.subplots(nrows=2, figsize=(8, 10))
values, ybins, xbins, im = ax1.specgram(x, cmap='gist_earth')
ax1.set(title='Specgram')
fig.colorbar(im, ax=ax1)
mesh = ax2.pcolormesh(xbins, ybins, values, cmap='gist_earth')
ax2.axis('tight')
ax2.set(title='Raw Plot of Returned Values')
fig.colorbar(mesh, ax=ax2)
plt.show()
不会绘制它返回的“原始”值。相反,它将它们缩放为分贝(换句话说,它绘制了振幅的plt.specgram
)。如果您不想扩展内容,则需要指定10 * log10
。然而,对于频率成分的观察,对数尺度最有意义。
考虑到这一点,让我们模仿scale="linear"
做什么:
specgram
或者,我们可以在图像上使用日志规范并获得类似的结果,但是更清楚地传达颜色值在对数范围内:
plotted = 10 * np.log10(values)
fig, ax = plt.subplots()
mesh = ax.pcolormesh(xbins, ybins, plotted, cmap='gist_earth')
ax.axis('tight')
ax.set(title='Plot of $10 * log_{10}(values)$')
fig.colorbar(mesh)
plt.show()
from matplotlib.colors import LogNorm
fig, ax = plt.subplots()
mesh = ax.pcolormesh(xbins, ybins, values, cmap='gist_earth', norm=LogNorm())
ax.axis('tight')
ax.set(title='Log Normalized Plot of Values')
fig.colorbar(mesh)
plt.show()
vs imshow
最后,请注意我们显示的示例没有应用插值,而原始的pcolormesh
绘图确实如此。 specgram
使用specgram
,而我们一直在使用imshow
进行策划。在这种情况下(常规网格间距)我们可以使用其中之一。
在这种情况下,pcolormesh
和imshow
都是非常好的选择。但是,如果您正在使用大型数组,pcolormesh
将具有明显更好的性能。因此,您可以考虑使用它,即使您不想插值(例如imshow
关闭插值)。
举个例子:
interpolation='nearest'