数字信号处理是音视频开发所必不可少的一项技能,我会从本篇开始,开启一系列入门文章,分享关于数字信号处理方面的知识。这只是一个精简的知识提炼,供大家进行入门,也是对自己的一个备忘和学习笔记。难免会有纰漏,要深入的同学请务必去看一些经典教材。
文章以 * 来表示乘法,以 ⊗ 表 示 卷 积 \otimes表示卷积 ⊗表示卷积
一、前言
数字信号处理我们日常生活中其实会经常接触到,像音频、视频、机械控制等等。简单来说就是一个信号 x x x,通过系统 S S S后输出信号 y y y,系统 S S S需要对信号进行处理,比如滤除噪音、调节频率等等。数字信号处理讲的就是对 x x x进行操作的学问。
二、线性时不变(LTI)系统
一般我们说数字信号处理都是基于线性时不变(LTI)系统,那么什么是LTI系统呢?顾名思义
1. 线性: 这个线性其实就是我们所用的线性方程中的那个概念,满足叠加定理,比如
x
1
→
y
1
x_1 \rightarrow y1
x1→y1是一个映射(也就是我们常说的函数关系)。假设有
x
2
=
a
x
1
x_2 = ax_1
x2=ax1,经过同样的映射
x
2
→
y
2
x_2 \rightarrow y_2
x2→y2,那么
y
2
=
a
y
1
y_2 = ay_1
y2=ay1。
2. 时不变: 这个就更好理解了。同样一个输入信号,任何时候的输出都是一样的。
三、冲激函数
冲激函数是指在0点上有值,而在其他地方均为0的函数。通常使用 δ \delta δ表示。
连续形式:
δ
(
t
)
=
{
+
∞
t
=
0
0
t
≠
0
\delta(t) = \begin{cases} +\infty & t = 0\\ 0 & t \neq 0 \end{cases}
δ(t)={+∞0t=0t=0
上面的式子比较抽象,其实它只有一个定义,就是在负无穷到正无穷的积分是1。
离散形式:
δ
[
n
]
=
{
1
n
=
0
0
n
≠
0
\delta[n] = \begin{cases} 1 & n = 0\\ 0 & n \neq 0 \end{cases}
δ[n]={10n=0n=0
它们各有一些性质,不过我们马上使用的是一些直观上的数学性质。
需要说明的一点,之后我们推导的很多公式都会以连续信号和离散信号的形式。连续信号我们以 x ( t ) x(t) x(t)表示,离散信号我们以 x [ n ] x[n] x[n]表示
四、阶跃函数
阶跃函数是从0开始到正无穷都为1,从负无穷到0都为0的函数。
连续形式:
u ( t ) = { 1 t > 0 0 t < 0 u(t) = \begin{cases} 1 & t > 0\\ 0 & t < 0 \end{cases} u(t)={10t>0t<0
需要注意的是,阶跃函数在t=0这一点是不连续的。
连续的阶跃函数和冲激函数有这么一层关系,从上面讲的连续冲击函数的定义,就可以得出
u
(
t
)
=
∫
−
∞
t
δ
(
τ
)
d
τ
u(t) = \int^{t}_{-\infty}\delta(\tau)d\tau
u(t)=∫−∞tδ(τ)dτ
因为
δ
(
t
)
\delta(t)
δ(t)在负无穷到正无穷的积分是1。那么
δ
(
t
)
\delta(t)
δ(t)就是
u
(
t
)
u(t)
u(t)的一阶微分。但上面也说过
u
(
t
)
u(t)
u(t)在t=0时是不连续的,因此严格来说不是可导的。但如果将
u
(
t
)
u(t)
u(t)认为是在一个很小的间隔
Δ
\Delta
Δ内从0上升到1的,那就不难理解了。而这种情况,其实在现实世界中才是真正常见的。
离散形式:
u
[
n
]
=
{
1
n
≥
0
0
n
<
0
u[n] = \begin{cases} 1 & n \ge 0\\ 0 & n < 0 \end{cases}
u[n]={10n≥0n<0
显然离散形式要简单多了。同连续形式,我们也可以得出离散的冲击函数和阶跃函数的关系。
u
[
n
]
=
∑
m
=
−
∞
n
δ
[
m
]
u[n] = \sum_{m = -\infty}^{n}\delta[m]
u[n]=m=−∞∑nδ[m]
u
[
n
]
u[n]
u[n]是
δ
[
n
]
\delta[n]
δ[n]的求和
或者
δ
[
n
]
=
u
[
n
]
−
u
[
n
−
1
]
\delta[n] = u[n] - u[n - 1]
δ[n]=u[n]−u[n−1]
δ
[
n
]
\delta[n]
δ[n]是
u
[
n
]
u[n]
u[n]的差分。
从以上形式不难看出一个规律,离散的求和对应连续的积分,离散的差分对应连续的微分,这一点将会在记忆一些性质的时候特别有用。后面我们也将会更加深刻地体验到。
五、卷积
5.1 卷积的推导
让我们以离散信号举例,从上面的冲激函数和阶跃函数来推导。
设有一信号
x
[
n
]
=
.
.
.
+
x
[
−
2
]
+
x
[
−
1
]
+
x
[
0
]
+
x
[
1
]
+
x
[
2
]
+
.
.
.
x[n] = ... + x[-2] + x[-1] + x[0] + x[1] + x[2] + ...
x[n]=...+x[−2]+x[−1]+x[0]+x[1]+x[2]+...
由于我们是从数学上来推导,因此暂且不要关心信号的序号为什么会有负的。
由冲激函数的定义,我们可以稍稍变形
x
[
i
]
=
x
[
i
]
∗
δ
[
n
−
i
]
x[i] = x[i] * \delta[n - i]
x[i]=x[i]∗δ[n−i]
因为当且仅当
i
=
n
i = n
i=n时
δ
[
n
−
i
]
=
1
\delta[n - i] = 1
δ[n−i]=1
那么
x
[
n
]
=
.
.
.
+
x
[
−
2
]
∗
δ
[
n
+
2
]
+
x
[
−
1
]
∗
δ
[
n
+
1
]
+
x
[
0
]
∗
δ
[
n
]
+
x
[
1
]
∗
δ
[
n
−
1
]
+
x
[
2
]
∗
δ
[
n
−
2
]
+
.
.
.
=
∑
k
=
−
∞
+
∞
x
[
k
]
∗
δ
[
n
−
k
]
x[n] = ... + x[-2] * \delta[n + 2] + x[-1] * \delta[n + 1] + x[0] * \delta[n] + x[1] * \delta[n - 1] + x[2] * \delta[n - 2] + ...\\ =\sum_{k=-\infty}^{+\infty}x[k] * \delta[n-k]
x[n]=...+x[−2]∗δ[n+2]+x[−1]∗δ[n+1]+x[0]∗δ[n]+x[1]∗δ[n−1]+x[2]∗δ[n−2]+...=k=−∞∑+∞x[k]∗δ[n−k]
设有一LTI系统对冲激信号
δ
[
n
]
\delta[n]
δ[n]的响应为
h
[
n
]
h[n]
h[n],称为冲激响应。由我们对LTI系统的定义,它是满足叠加性质的,也就是说,对于系统S,它的输入为
δ
[
n
]
\delta[n]
δ[n],输出为
h
[
n
]
h[n]
h[n],根据LTI的线性性质,就有
x
[
i
]
∗
δ
[
n
−
i
]
→
x
[
i
]
∗
h
[
n
−
i
]
x[i] * \delta[n - i] \rightarrow x[i] * h[n - i]
x[i]∗δ[n−i]→x[i]∗h[n−i]
此处我们把
x
[
i
]
x[i]
x[i]看做了一个系数。
因此可以得出系统S对
x
[
t
]
x[t]
x[t]的输出为
y
[
n
]
=
∑
k
=
−
∞
+
∞
x
[
k
]
∗
h
[
n
−
k
]
=
x
[
n
]
⊗
h
[
n
]
y[n] = \sum_{k=-\infty}^{+\infty}x[k] * h[n-k]\\ =x[n] \otimes h[n]
y[n]=k=−∞∑+∞x[k]∗h[n−k]=x[n]⊗h[n]
这便是卷积的定义。由此我们也能得出,只要知道了一个系统的冲激响应,那么就可以得出它对任意输入信号的输出。
需要区分
δ
[
n
]
\delta[n]
δ[n]和
h
[
n
]
h[n]
h[n]的区别,虽然
δ
[
n
]
\delta[n]
δ[n]是一个冲激信号,只在一个时段有值,但它的响应
h
[
n
]
h[n]
h[n]是一个普通的信号,有可能是任何形式的,但是绝大部分来说,
h
[
n
]
h[n]
h[n]都会持续一段时间。
这就好像有一台马达,你在很短的时间内给它电源,断掉之后它还会持续转一会儿。
类似于这样
当然,也有输入时冲激信号,输出也是冲激信号,就是
h
[
n
]
=
K
δ
[
n
]
h[n] = K\delta[n]
h[n]=Kδ[n]
那么这样的系统我们称之为无记忆系统,当前的输出只和当前的输入有关。但现实世界中我们绝大多数都面对的是有记忆系统,当前的输出和之前的输入以及当前的输入有关。上面马达的例子还有图都是有记忆系统。
说到这个,系统还分为因果系统和非因果系统。因果系统是输出仅和之前以及目前的输入有关,而非因果系统是输出和之前、现在以及将来的输入有关。非因果系统实在太过诡异,以至于我目前还无法理解,也没遇到过。我们说的系统,都是因果系统。
5.2 LTI系统卷积的性质
5.2.1 交换律
∑
k
=
−
∞
+
∞
x
[
k
]
∗
h
[
n
−
k
]
=
x
[
n
]
⊗
h
[
n
]
=
h
[
n
]
⊗
x
[
n
]
=
∑
k
=
−
∞
+
∞
h
[
k
]
∗
x
[
n
−
k
]
\sum_{k=-\infty}^{+\infty}x[k] * h[n-k] = x[n] \otimes h[n] = h[n] \otimes x[n] = \sum_{k=-\infty}^{+\infty}h[k] * x[n-k]
k=−∞∑+∞x[k]∗h[n−k]=x[n]⊗h[n]=h[n]⊗x[n]=k=−∞∑+∞h[k]∗x[n−k]
假设有
r
=
n
−
k
r = n - k
r=n−k
那么
∑
k
=
−
∞
+
∞
x
[
k
]
∗
h
[
n
−
k
]
=
∑
r
=
−
∞
+
∞
h
[
r
]
∗
x
[
n
−
r
]
=
h
[
n
]
⊗
x
[
n
]
\sum_{k=-\infty}^{+\infty}x[k] * h[n-k] = \sum_{r=-\infty}^{+\infty}h[r]*x[n - r] = h[n] \otimes x[n]
k=−∞∑+∞x[k]∗h[n−k]=r=−∞∑+∞h[r]∗x[n−r]=h[n]⊗x[n]
5.2.2 分配律
x
[
n
]
⊗
(
h
1
[
n
]
+
h
2
[
n
]
)
=
x
[
n
]
⊗
h
1
[
n
]
+
x
[
n
]
⊗
h
2
[
n
]
x[n] \otimes (h_1[n] + h_2[n]) = x[n] \otimes h_1[n] + x[n] \otimes h_2[n]
x[n]⊗(h1[n]+h2[n])=x[n]⊗h1[n]+x[n]⊗h2[n]
这个就更简单了,便不单独推导了。
用系统框图表示就是
上下两个系统是等价的
5.2.3 结合律
x [ n ] ⊗ h 1 [ n ] ⊗ h 2 [ n ] = x [ n ] ⊗ h 2 [ n ] ⊗ h 1 [ n ] x[n] \otimes h_1[n] \otimes h_2[n] = x[n] \otimes h_2[n] \otimes h_1[n] x[n]⊗h1[n]⊗h2[n]=x[n]⊗h2[n]⊗h1[n]
这个需要从求和公式中推导,这里就不展开了,记住就好。
根据这个式子,有一个很重要的结论。
假设信号
x
[
n
]
x[n]
x[n]先经过冲激响应为
h
1
[
n
]
h_1[n]
h1[n]系统S1,得到输出为
w
[
n
]
w[n]
w[n],然后
w
[
n
]
w[n]
w[n]经过冲激响应为
h
2
[
n
]
h_2[n]
h2[n]系统S2,得到最终输出
y
[
n
]
y[n]
y[n]。那么它也等效于信号
x
[
n
]
x[n]
x[n]先经过S2再经过S1。如下图。
牢记以上的几条性质,对于系统设计会非常有用。
上面都是以离散信号举例,其实对于连续信号来说,也是一样的,只是把求和换成积分。
y
(
n
)
=
∫
−
∞
+
∞
x
(
k
)
∗
h
(
n
−
k
)
d
k
=
x
(
n
)
⊗
h
(
n
)
y(n) = \int_{-\infty}^{+\infty}x(k) * h(n-k)dk\\ =x(n) \otimes h(n)
y(n)=∫−∞+∞x(k)∗h(n−k)dk=x(n)⊗h(n)
由于我们目前将的都是数字信号处理,因此着重讲离散信号,连续信号都会跟着提一下。
至此,讲完了卷积的由来,下一篇我们讲一下傅里叶变换。