如何在Python中使用可变宽度高斯函数进行卷积?

11

我需要使用高斯函数进行卷积,但高斯函数的宽度需要改变。我的工作不是传统的信号处理,而是基于设备分辨率对完美概率密度函数(PDF)进行“扩散”。

例如,假设我的PDF起初是一个尖峰/δ函数。我将其建模为非常窄的高斯函数。在经过我的设备后,它将根据某个高斯分辨率被扩散。我可以使用scipy.signal卷积函数计算这个值。

    import numpy as np
    import matplotlib.pylab as plt

    import scipy.signal as signal
    import scipy.stats as stats

    # Create the initial function. I model a spike
    # as an arbitrarily narrow Gaussian
    mu = 1.0 # Centroid
    sig=0.001 # Width
    original_pdf = stats.norm(mu,sig)

    x = np.linspace(0.0,2.0,1000) 
    y = original_pdf.pdf(x)
    plt.plot(x,y,label='original')


    # Create the ``smearing" function to convolve with the
    # original function.
    # I use a Gaussian, centered at 0.0 (no bias) and
    # width of 0.5
    mu_conv = 0.0 # Centroid
    sigma_conv = 0.5 # Width
    convolving_term = stats.norm(mu_conv,sigma_conv)

    xconv = np.linspace(-5,5,1000)
    yconv = convolving_term.pdf(xconv)

    convolved_pdf = signal.convolve(y/y.sum(),yconv,mode='same')

    plt.plot(x,convolved_pdf,label='convolved')
    plt.ylim(0,1.2*max(convolved_pdf))
    plt.legend()
    plt.show()

这一切都没有问题。但是现在假设我的原始PDF不是一个尖峰,而是一些更宽泛的函数。例如,具有sigma=1.0的高斯分布。并且现在假设我的分辨率实际上在x上变化:在x = 0.5处,模糊函数是具有sigma_conv = 0.5的高斯分布,但在x = 1.5处,模糊函数是具有sigma_conv = 1.5的高斯分布。并且假设我知道我的模糊高斯函数的x依赖关系的函数形式。天真地说,我认为我会改变上面的行:

    convolving_term = stats.norm(mu_conv,lambda x: 0.2*x + 0.1)

但这行不通,因为norm函数期望的是宽度的值,而不是一个函数。某种程度上,我需要我的卷积函数是一个二维数组,在其中我对原始PDF中的每个点都有一个不同的模糊高斯函数,而原始PDF仍然是一个一维数组。

那么,有没有使用Python中已经定义好的函数来做到这一点呢?我有一些自己编写的代码可以实现这个功能...但我想确保我没有重复造轮子。

提前感谢!

Matt


你的xconv“步长”(last - first) / (length - 1)与x“步长”不同,这会使宽度缩放(即sigmas不在相同的“单位”中),你真的想要这样吗? - H.D.
"我有一些自己编写的代码可以实现这个功能" => "你能展示给我们看这段代码吗?这可能会很有帮助。" - H.D.
1个回答

8
问题简述:
如何与非平稳核进行卷积,例如,对于数据中不同位置的宽度变化的高斯核,并且Python中是否存在现有工具来执行此操作?
回答:
很难证明否定,但我认为scipy或numpy中不存在执行与非平稳核的卷积的函数。无论如何,正如您所描述的那样,它不能很好地向量化,因此您可以做一个循环或编写一些自定义C代码。
可能适合您的一个技巧是,而不是根据位置更改内核大小,使用反比例尺缩放数据(即,在您希望高斯核的基本宽度为0.5的位置处,将数据拉伸到2倍)。这样,您可以对数据进行单个变形操作,使用固定宽度高斯核进行标准卷积,然后将数据还原为原始比例。
这种方法的优点是非常容易编写,并且完全向量化,因此运行速度可能相当快。
通过变形数据(使用插值方法)会导致一些精度损失,但如果您选择使数据在初始变形操作中始终扩展而不是缩小,则损失应该很小。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接