在对信号进行卷积时,为什么在此过程中需要翻转脉冲响应?
在对信号进行卷积时,为什么在此过程中需要翻转脉冲响应?
Answers:
改编自对另一个问题的回答(如评论中所述),希望该问题不会被Community Wiki作为热门问题之一反复抛出。
线性(时间不变)系统没有冲动响应的“翻转”。线性时不变系统的输出是冲激响应的按比例缩放和延时形式的总和,而不是 “翻转”冲激响应。
我们将输入信号分解成总和缩放单元的脉冲信号的。该系统响应于该单位脉冲信号 是脉冲响应或脉冲响应
类似地,单个输入值或创建 X [ 1 ] (⋯ ,0 ,0 ,0 ,1 ,0 ,⋯ )= ⋯ 0 ,0 ,0 ,X [ 1 ] ,0 ,⋯ 创建响应 0 ,x [ 1 ] h [ 0 ] ,x [ 1
在时间输出是什么?
那么您可以通过将第求和答案
这是一个C / C ++示例,该示例显示了可以进行卷积而无需反向使用脉冲响应。如果检查该convolve_scatter()
函数,则任何地方都不会否定变量。这是散射卷积,其中使用冲激响应给定的权重将每个输入样本分散(求和)到内存中的多个输出样本。这是浪费的,因为将需要多次读取和写入输出样本。
通常,卷积是在聚集卷积中完成的,如中所示convolve_gather()
。在这种方法中,每个输出样本是通过将输入样本收集(求和)而得到的,并以反向的脉冲响应作为权重来形成。完成后,输出样本驻留在用作累加器的处理器寄存器中。通常,这是选择的方法,因为每个过滤后的样本只有一个存储器写操作。现在,输入的内存读取次数更多,但散射方法中输出的内存读取次数却与之相同。
#include <stdio.h>
const int Nx = 5;
const int x[Nx] = {1, 0, 0, 0, 2};
const int Ny = 3;
const int y[Ny] = {1, 2, 3};
const int Nz = Nx+Ny-1;
int z[Nz];
void convolve_scatter() { // z = x conv y
for (int k = 0; k < Nz; k++) {
z[k] = 0;
}
for (int n = 0; n < Nx; n++) {
for (int m = 0; m < Ny; m++) {
z[n+m] += x[n]*y[m]; // No IR reversal
}
}
}
void convolve_gather() { // z = x conv y
for (int k = 0; k < Nz; k++) {
int accu = 0;
for (int m = 0; m < Ny; m++) {
int n = k+m - Ny + 1;
if (n >= 0 && n < Nx) {
accu += x[n]*y[Ny-m-1]; // IR reversed here
}
}
z[k] = accu;
}
}
void print() {
for (int k = 0; k < Nz; k++) {
printf("%d ", z[k]);
}
printf("\n");
}
int main() {
convolve_scatter();
print();
convolve_gather();
print();
}
它对序列进行卷积:
1 0 0 0 2
1 2 3
并使用两种卷积方法输出:
1 2 3 0 2 4 6
我无法想象有人使用散射方法,除非滤波器是随时间变化的,在这种情况下,两种方法将产生不同的结果,并且一种方法可能更合适。
它只是“翻转”用于逐点计算。
@Dilip解释了卷积积分/求和表示的含义,但要解释为什么两个输入函数之一(通常h(t)
)出于计算目的而被翻转,请考虑具有输入x[n]
和脉冲响应的离散时间系统h[n]
:
您可以使用输入函数x[n]
,并为每个非零*样本x[n]
计算从样本开始的缩放脉冲响应,n
直到时间平移到h[n]
零为止(假定为因果关系h[n]
)。这将涉及没有“翻转”(或更准确地“时间反转”)的任一x[n]
或h[n]
。但是,最后,您将不得不为每个非零的脉冲响应添加/叠加所有这些比例缩放和移位的“回声” x[n]
。
x[0]
k
h[n]
x[n]
,是x[0]h[0]
。然后,增加k
1将h[n]
移至正确的一个时间步长,以使时间倒数h[n]
的第二个条目(h[1]
)现在位于的顶部x[0]
,等待相乘。就像在以前的方法中所做的那样,这将x[0]h[1]
在时间上产生期望的贡献n=1
。x[n]
h[n]
y[n]