对称数组与 NumPy 的卷积:为什么结果会偏移?

Convolution of symmetric arrays with NumPy: why is the result shifted?

我有两个 numpy 数组。每个包含一个以零为中心的类核函数,完全对称,长度均为 101。当我对这些数组进行卷积时,我是否应该期望另一个数组也以零为中心?我正在使用 numpy.convolve,我总是得到一个不以零为中心的结果内核数组,这不是我想要的:我需要一个也完全居中,没有偏移的内核数组。

我的代码大致是这样的:

import numpy as np
import matplotlib.pyplot as plt

x = np.array([...])        # x-axis
array1 = np.array([...])   # Blue curve
array2 = np.array([...])   # Green curve
# All arrays are one-dimensional
conv_array = np.convolve(array1, array2, mode='same') # Red curve
conv_array /= max(conv_array) # Normalization

plt.plot(x, array1)
plt.plot(x, array2)
plt.plot(x, conv_array)
plt.show()

最终的曲线图是这样的:

如何获得未移位的卷积数组?

恐怕这是一道关于卷积的数学题,我无法回答。但是,如果您只是希望将卷积数组以零(它的最小值)为中心,那么以下将提供 'quick fix':

plt.plot(x + x[np.argmin(conv_array[:conv_array.shape[0]*3/4)]],conv_array)

一个非常简单的替代方法是使用 scipy.ndimage.convolve1d 而不是 numpy.convolve

import numpy as np
import matplotlib.pyplot as plt
from astropy.modeling import models

# Create a model
x = np.arange(101) - 50       # x-axis
g1 = models.Gaussian1D(amplitude=2, mean=0, stddev=4)
g2 = models.Gaussian1D(amplitude=3, mean=0, stddev=3)
array1 = g1(x)
array2 = 1 - g2(x)

from scipy.ndimage import convolve1d

conv_array2 = convolve1d(array1, array2)
conv_array2 /= conv_array2.max()

# One can also use numpy convolve here
conv_array = np.convolve(array1, array2, mode='same') # Red curve
conv_array /= max(conv_array) # Normalization

plt.plot(x, array1)
plt.plot(x, array2)
plt.plot(x, conv_array) # Is centered on 0
plt.plot(x, conv_array2) # Is centered on 0
plt.show()

我想问题是你的数组没有完全以 0 为中心。(所以 x[50] != 0)。并且 numpy 在卷积之前翻转内核,因此你得到一个转变。请注意,如果您尝试我的示例,numpy.convolve 结果也完全以 0 为中心,但我确保 array1array2 以 0 为中心。根据您的情节,我猜 -22<x<27 (不居中)

我推荐scipy的原因是因为我也有类似的问题:-)他们只是使用不同的定义:numpy and scipy注意kernel-index的不同符号。