最近因为工作原因,接触到了超分以及AMD家出的FSR算法,特意记录了解一下~
前言
超分辨率是通过硬件或软件方法提高原有图像分辨率的方法,通过一幅或者多幅低分辨率的图像来得到一幅高分辨率的图像。
FSR是AMD提出的一种超分辨率方法,这种方法不借助深度学习,采用数学推导的方式实现,目前已经更新到3.0版本,本篇博客记录FSR1.0的学习记录。
FSR分为两个阶段,第一阶段为EASU上采样,第二阶段为RCAS锐化。
EASU上采样
首先,解释一下什么是上采样,什么是下采样。
上采样:原先有一张小尺寸的纹理,然后我们将这个纹理放大到大尺寸中(像素变多),然后使用采样方法(例如线性插值)进行填充。
下采样:原先有一张大尺寸的纹理,然后我们将这个纹理缩小到小尺寸中(像素变少),然后使用采样方法填充。
边缘与非边缘的上采样
对图像进行放大时,放大后的像素有两种情况:
- 非边缘:如果是非边缘,则对于放大后的像素点P,在原图对应像素点Q,则Q附近的像素灰度值应该非常接近,此时只需要对Q周围的像素进行加权平均即可,此时权重均为正值。
- 边缘:如果像素点P为边缘,此时应该采用锐化的方式进行处理,对Q附近的像素灰度值采用高频滤波器类似的加权方法进行加权。与上述非边缘的像素不同的是,对边缘像素进行加权计算的权重有负值。
因此,可以将边缘跟非边缘的计算方法统一成一个表达式:
f
(
P
)
=
∑
i
f
(
Q
i
)
H
(
Q
i
)
∑
i
H
(
Q
i
)
\begin{align} f(P) = \frac{\sum_if(Q_i)H(Q_i)}{\sum_iH(Q_i)} \end{align}
f(P)=∑iH(Qi)∑if(Qi)H(Qi)
H ( Q i ) H(Q_i) H(Qi):权重计算公式,其应当满足当Q点为非边缘时,权重全为正数,Q点为边缘时,权重会包含负值,用来计算高频滤波器。因此接下来就是要找到满足这样条件的权重计算公式。
Lanczos2 函数
EASU引入了Lanczos函数:
L
(
x
)
=
a
s
i
n
(
π
x
)
s
i
n
(
π
x
a
)
π
2
x
2
,
x
∈
[
−
a
,
a
]
\begin{align} L(x) = \frac{asin(\pi x)sin(\frac{\pi x}{a})}{\pi^2x^2},x\in [-a, a] \end{align}
L(x)=π2x2asin(πx)sin(aπx),x∈[−a,a]
当 a = 2 a = 2 a=2时,通常将其称为Lanczos2函数,EASU就是基于Lanczos2函数作为基础处理的,它的图像如下图所示。
Lanczos2函数的值在
x
∈
[
0
,
1
]
x \in [0,1]
x∈[0,1]时函数值大于0,
x
∈
[
1
,
2
]
x\in [1,2]
x∈[1,2]时函数值小于0,符合我们要找的权重函数的要求。但是函数中包含了三角函数,在shader中效率不高,因此EASU用多项式来拟合公式(2)。
L
(
x
)
=
[
25
16
(
2
5
x
2
−
1
)
2
−
(
25
16
−
1
)
]
(
ω
x
2
−
1
)
2
\begin{align} L(x) = \left[ \frac{25}{16}\left( \frac{2}{5}x^2 - 1 \right)^2 - \left( \frac{25}{16} - 1\right) \right](\omega x^2 - 1)^2 \end{align}
L(x)=[1625(52x2−1)2−(1625−1)](ωx2−1)2
其中
ω
\omega
ω参数可以用来控制函数在
x
∈
[
1
,
2
]
x\in [1,2]
x∈[1,2]部分的值,下面是
ω
\omega
ω从0变化到0.5过程中的函数图像
边缘特征
图像中的边缘,一般有如下几种情况:
EASU主要解决的是阶梯状边缘,因此特征越接近阶梯状边缘,对应的 ω \omega ω应该越小,此时当 x ∈ [ 1 , 2 ] x\in [1,2] x∈[1,2]时, L ( x ) L(x) L(x)返回的权重也越小。
Feature的定义与变量 ω \omega ω
我们为像素T定义Feature的计算公式,只计算像素点T上下左右方向的像素点,该Feature可以与变量
ω
\omega
ω一一对应。记EASU的边缘特征的中间值为
F
F
F,它的计算公式为:
F
=
(
F
X
2
+
F
Y
2
)
\begin{align} F = (FX^2 + FY^2)\end{align}
F=(FX2+FY2)
F
X
=
∣
f
(
T
x
−
1
,
y
−
f
(
T
x
+
1
,
y
)
∣
m
a
x
(
∣
f
(
T
x
−
1
,
y
)
−
f
(
T
x
,
y
)
∣
,
∣
f
(
T
x
+
1
,
y
)
−
f
(
T
x
,
y
)
∣
)
F
Y
=
∣
f
(
T
x
,
y
−
1
−
f
(
T
x
,
y
+
1
)
∣
m
a
x
(
∣
f
(
T
x
,
y
−
1
)
−
f
(
T
x
,
y
)
∣
,
∣
f
(
T
x
,
y
+
1
)
−
f
(
T
x
,
y
)
∣
)
FX = \frac{|f(T_{x-1,y} - f(T_{x+1,y})|}{max(|f(T_{x-1,y}) - f(T_{x,y})|, |f(T_{x+1,y}) - f(T_{x,y})|)} \\ FY = \frac{|f(T_{x,y-1} - f(T_{x,y+1})|}{max(|f(T_{x,y-1}) - f(T_{x,y})|, |f(T_{x,y+1}) - f(T_{x,y})|)}
FX=max(∣f(Tx−1,y)−f(Tx,y)∣,∣f(Tx+1,y)−f(Tx,y)∣)∣f(Tx−1,y−f(Tx+1,y)∣FY=max(∣f(Tx,y−1)−f(Tx,y)∣,∣f(Tx,y+1)−f(Tx,y)∣)∣f(Tx,y−1−f(Tx,y+1)∣
其中,这里的 f ( x ) f(x) f(x)是 x x x点做过灰度化处理后的颜色值,通过表达式 f = b ∗ 0.5 + r ∗ 0.5 + g f = b * 0.5 + r * 0.5 + g f=b∗0.5+r∗0.5+g 计算。
在公式(4)中,
F
X
,
F
Y
∈
[
0
,
1
]
FX,FY \in[0,1]
FX,FY∈[0,1],因此
F
∈
[
0
,
2
]
F\in[0,2]
F∈[0,2],为了归一,EASU提出将其映射到
[
0
,
1
]
[0,1]
[0,1]:
F
e
a
t
u
r
e
=
(
F
/
2
)
2
\begin{align} Feature = (F/2)^2 \end{align}
Feature=(F/2)2
我们已经找到了区分边缘的特征值Feature,以及可以通过
ω
\omega
ω调整区间
[
1
,
2
]
[1,2]
[1,2]取值范围的拟合曲线了,接下来就是要建立Feature跟
ω
\omega
ω之间的关系。
公式(3)中的函数 L ( x ) , x ∈ [ − 2 , 2 ] L(x),x\in[-2,2] L(x),x∈[−2,2]是关于 y y y轴对称的,因此这里只分析正半轴(EASU里也只用到了正半轴),在正半轴上 L ( x ) L(x) L(x)有三个根: x = 1 ; x = 2 ; x = 1 ω , ( ω > 0 ) x = 1;x = 2;x = \frac{1}{\sqrt{\omega}},(\omega > 0) x=1;x=2;x=ω1,(ω>0),如下图所示。
当 1 ω ∈ [ 1 , 2 ] \frac{1}{\sqrt{\omega}} \in [1,2] ω1∈[1,2]时, ( ω ∈ [ 1 4 , 1 ] ) (\omega \in[\frac{1}{4},1]) (ω∈[41,1]),区间 [ 1 , 1 ω ] [1,\frac{1}{\sqrt{\omega}}] [1,ω1]中有一个极小值 m m m。
- 1 ω → 1 : m → 0 \frac{1}{\sqrt{\omega}} \rightarrow 1: m \rightarrow 0 ω1→1:m→0
- 1 ω → 2 : m → − 2187 16483 \frac{1}{\sqrt{\omega}} \rightarrow 2: m \rightarrow -\frac{2187}{16483} ω1→2:m→−164832187
注意到当 1 ω ∈ [ 1 , 2 ] \frac{1}{\sqrt{\omega}} \in [1,2] ω1∈[1,2]时, x ∈ [ 1 ω , 2 ] x\in[\frac{1}{\sqrt{\omega}}, 2] x∈[ω1,2]区间出现了一个负的Lobe部分,为了解决这个问题,EASU进行了截断,只取 x ∈ [ 0 , 1 ω ] x\in [0,\frac{1}{\sqrt{\omega}}] x∈[0,ω1]区间。
因此可以通过改变
1
ω
\frac{1}{\sqrt{\omega}}
ω1的值来控制
[
1
,
1
ω
]
[1,\frac{1}{\sqrt{\omega}}]
[1,ω1]区间里负值的大小(用来作公式(1)中的负权重)。
ω
=
1
−
3
4
F
e
a
t
u
r
e
\begin{align} \omega = 1 - \frac{3}{4}Feature \end{align}
ω=1−43Feature
但是由于
1
ω
\frac{1}{\sqrt{\omega}}
ω1在趋近于1时,负权重不够,会导致边缘信息识别不足,因此EASU将
1
ω
\frac{1}{\sqrt{\omega}}
ω1的范围限定在
[
2
,
2
]
[\sqrt{2},2]
[2,2],因此
ω
∈
[
1
4
,
1
2
]
\omega \in[\frac{1}{4}, \frac{1}{2}]
ω∈[41,21],得出新的线性关系:
ω
=
1
2
−
1
4
F
e
a
t
u
r
e
\begin{align} \omega = \frac{1}{2} - \frac{1}{4}Feature \end{align}
ω=21−41Feature
EASU同时限定了 x x x的范围为 x ∈ [ 0 , 1 ω ] x\in[0, \frac{1}{\sqrt{\omega}}] x∈[0,ω1],即 x = m i n ( x , 1 ω ) x=min(x,\frac{1}{\sqrt{\omega}}) x=min(x,ω1)。
Feature获得
EASU计算
Q
Q
Q点特征时,采用的是采样像素点
Q
Q
Q周围12个像素的值来计算。EASU首先会进行批量采样,从而获取
Q
Q
Q周围像素的像素值,待采样的像素如下图所示(标识为z的像素点为多余的像素,在计算时不会用到):
每次使用Gather4指令批量采样4个像素点中的一个通道,例如浅绿色框采样的顺序是ijfe,因为像素有三个通道RGB,因此每次批量采样 4 * 3 次。
然后,计算特征时,分四组分别计算出4个Feature。
使用双线性插值得到最终的Feature。如下图所示, O = f l o o r ( Q ) O = floor(Q) O=floor(Q), u 、 v u、v u、v则是 Q Q Q到 O O O的偏移。
F
e
a
t
u
r
e
=
(
1
−
u
)
(
1
−
v
)
f
1
+
u
(
1
−
v
)
f
2
+
u
v
f
3
+
(
1
−
u
)
v
f
4
\begin{align} Feature = (1-u)(1-v)f_1 + u(1-v)f_2+uvf_3+(1 - u)vf_4 \end{align}
Feature=(1−u)(1−v)f1+u(1−v)f2+uvf3+(1−u)vf4
结合公式(7)和公式(8),便可计算出
ω
\omega
ω的值。
梯度
计算Feature的同时,EASU还计算了 Q Q Q点的像素灰度变化的梯度,同样也是分四组计算梯度,最后用双线性插值得出最终的梯度向量。每组梯度计算的方式如下:
D x = g − e = f ( Q x + 1 , y ) − f ( Q x − 1 , y ) D y = j − b = f ( Q x , y + 1 ) − f ( Q x , y − 1 ) D_x = g - e = f(Q_{x+1,y}) - f(Q_{x-1,y})\\ D_y = j - b = f(Q_{x,y+1}) - f(Q_{x,y-1}) Dx=g−e=f(Qx+1,y)−f(Qx−1,y)Dy=j−b=f(Qx,y+1)−f(Qx,y−1) D ⃗ = ( c o s θ , s i n θ ) = ( D x D x 2 + D y 2 , D y D x 2 + D y 2 ) \begin{align} \vec D = (cos\theta,sin\theta) = (\frac{D_x}{\sqrt{D_x^2 + D_y^2}}, \frac{D_y}{\sqrt{D_x^2 + D_y^2}}) \end{align} D=(cosθ,sinθ)=(Dx2+Dy2Dx,Dx2+Dy2Dy)
采样颜色值
到这里,我们得到了 Q Q Q的梯度,以及Feature,之后,EASU分别对 Q Q Q周围的12个像素,按照梯度角度进行旋转,并进行缩放,最终利用像素点左上角到 Q Q Q点的欧式距离作为 x x x,带入权重公式,即公式(3),得到周围像素的权重。
如上图,像素b跟
Q
Q
Q之间的向量
Q
B
⃗
\vec{QB}
QB按照梯度旋转:
x
r
=
x
Q
B
∗
c
o
s
θ
+
y
Q
B
∗
s
i
n
θ
y
r
=
−
x
Q
B
∗
s
i
n
θ
+
y
Q
B
∗
c
o
s
θ
\begin{align} x_r &= x_{QB} * cos\theta + y_{QB}* sin\theta \notag \\ y_r &= -x_{QB} * sin\theta + y_{QB}*cos\theta \end{align}
xryr=xQB∗cosθ+yQB∗sinθ=−xQB∗sinθ+yQB∗cosθ
旋转完毕后,EASU定义了一个将旋转向量根据梯度和边缘特征进行缩放的公式(注意,这里是直接定义的公式,并没有数学逻辑):
S
t
r
e
t
c
h
=
1
m
a
x
(
∣
s
i
n
θ
∣
,
∣
c
o
s
θ
∣
)
S
x
=
1
+
(
S
t
r
e
t
c
h
−
1
)
∗
F
e
a
t
u
r
e
S
y
=
1
−
0.5
∗
F
e
a
t
u
r
e
\begin{align}Stretch &= \frac{1}{max(|sin\theta|,|cos\theta|)}\\ S_x &= 1 + (Stretch - 1) * Feature \notag \\ S_y &= 1 - 0.5 * Feature \notag \end{align}
StretchSxSy=max(∣sinθ∣,∣cosθ∣)1=1+(Stretch−1)∗Feature=1−0.5∗Feature
然后得出
Q
B
⃗
\vec{QB}
QB旋转缩放后的向量坐标:
S
x
b
=
x
r
∗
S
x
,
S
y
b
=
y
r
∗
S
y
\begin{align}S_{xb} = x_r * S_x,S_{yb} = y_r * S_y\end{align}
Sxb=xr∗Sx,Syb=yr∗Sy
最后求出向量的模:
d
b
=
m
i
n
(
S
x
b
2
+
S
y
b
2
,
1
ω
)
\begin{align}d_b = min(\sqrt{S_{xb}^2 + S_{yb}^2}, \frac{1}{\sqrt\omega})\end{align}
db=min(Sxb2+Syb2,ω1)
将得出的
d
b
d_b
db带入到公式(3),即可求出b像素点的权重值。其他像素点一次按照这样的方式求出对应像素的权重值,最后利用公式(1),即可求出上采样
P
P
P点的像素值。
EASU里最后会对求出的颜色做限制,限制颜色的最大最小值只能在这12个采样点颜色之间,据说可以减少ringing效果。
RCAS锐化
上采样结束后,FSR最后对上采样得到的图像进行一次RCAS(Robust Contrast Adaptive Sharpening在CAS基础上进行改进)的锐化处理,将边缘信息进一步加强,RCAS其实是拉普拉斯算子的变种:
最后像素
P
P
P按照上面的算子进行加权计算即可:
F
(
P
)
=
f
(
P
)
+
ω
∗
(
f
(
P
x
−
1
,
y
)
+
f
(
P
x
+
1
,
y
)
+
f
(
P
x
,
y
−
1
)
+
f
(
P
x
,
y
+
1
)
)
4
ω
+
1
\begin{align}F(P) = \frac{f(P) + \omega * (f(P_{x-1,y}) + f(P_{x+1,y}) + f(P_{x,y-1}) + f(P_{x,y+1}))}{4\omega + 1}\end{align}
F(P)=4ω+1f(P)+ω∗(f(Px−1,y)+f(Px+1,y)+f(Px,y−1)+f(Px,y+1))
对于
ω
\omega
ω权重,RCAS计算方法是获取像素
P
P
P点周围的四个像素,然后根据包括
P
P
P在内五个像素点的最大最小值来计算。
于是有
ω
=
m
a
x
(
−
M
i
n
4
M
a
x
,
1
−
M
a
x
4
M
i
n
−
4
)
∗
S
c
a
l
e
\begin{align}\omega = max(-\frac{Min}{4Max},\frac{1 - Max}{4Min - 4}) * Scale\end{align}
ω=max(−4MaxMin,4Min−41−Max)∗Scale
Scale为采样之后分辨率跟原分辨率的比值。
RCAS中为了确保
ω
\omega
ω为负数,最后对
ω
\omega
ω做了限制:
ω
=
m
a
x
(
−
(
1
4
−
1
16
)
,
m
i
n
(
ω
,
0
)
)
\begin{align}\omega = max(-(\frac{1}{4} - \frac{1}{16}), min(\omega,0))\end{align}
ω=max(−(41−161),min(ω,0))
对于RGB每个通道,都计算一次对应的 ω R 、 ω G 、 ω B \omega_R、\omega_G、\omega_B ωR、ωG、ωB。
总结
参考这份github上用python实现的FSR,可以实现超分效果,如下图所示:
总结一下,FSR一共包含两个阶段,第一阶段为EASU上采样,第二阶段为RCAS锐化,其中EASU上采样是重点。
EASU的基本思想是根据像素点周围颜色变化的梯度,计算出一个可变的权重函数,将周围点加权得出当前像素点的颜色。其中,当该点处于边缘时,权重函数会出现负值,起到一个类似锐化的效果,用于突出边缘像素;当该点处于非边缘时,权重函数全为正值,起到一个类似平均池化的效果。
参考
https://www.xianlongok.site/post/30ae96f7/
https://zhuanlan.zhihu.com/p/401030221