使用scipy.interpolate计算FWHM时的问题
我在找一些数据的全宽半最大值(FWHM)时遇到了问题。一开始,我试着用 interpolate.interp1d
来拟合曲线。这样我就能创建一个函数,当我输入一个 x 值时,它会返回一个插值的 y 值。问题是,我需要这个功能的反向,也就是说,我想把自变量和因变量对调。但是当我尝试这样做时,出现了错误,因为自变量的数据必须是排序的。如果我对数据进行排序,就会丢失索引,从而失去图形的形状。
我尝试了:
x = np.linspace(0, line.shape[0], line.shape[0])
self.x_curve = interpolate.interp1d(x, y, 'linear')
这里的 y
是我的数据。
为了得到反向,我尝试了:
self.x_curve = interpolate.interp1d(sorted(y), x, 'linear')
但得到的值不对。
然后我继续尝试使用 UnivariateSpline 来找到根,从而找出全宽半最大值(参考这个问题:寻找峰值的全宽半最大值),但是 roots() 方法总是给我一个空列表 []
。
这是我使用的:
x_curve = interpolate.UnivariateSpline(x, y)
r = x_curve.roots()
print(r)
这里是数据的图像(使用 UnivariateSpline):
有什么想法吗?谢谢。
1 个回答
3
使用 UnivariateSpline.roots()
来计算全宽半高(FWHM)时,数据必须先调整,使得在全宽半高的位置值为0。
由于数据的背景比较嘈杂,我会先估算一下基线。比如说:
y_baseline = y[(x<200) & (x>350)].mean()
(根据需要调整 x
的范围)。然后将数据调整,使得基线的中间和峰值都在0的位置。因为你的数据有一个最小值,而不是像例子中那样有最大值,所以我使用 y.min()
:
y_shifted = y - (y.min()+y_baseline)/2.0
现在对这个调整后的数据进行样条拟合,这样 roots()
就能找到根值,而根值之间的差就是全宽半高。
x_curve = interpolate.UnivariateSpline(x, y_shifted, s=0)
x_curve.roots()
如果你想从平滑的数据中估算全宽半高,可以增加 s
参数的值。