概述
经典论文Colorization using Optimization来自于siggraph2004,论文旨在通过简单的交互实现灰度图的全局彩色化,论文短小精悍、思路新颖、实现简单、效果优良。短短6页纸的论文,引用1300+。
论文链接:https://webee.technion.ac.il/people/anat.levin/papers/colorization-siggraph04.pdf
代码链接:https://github.com/lightalchemist/colorize-image
输入:原始灰度图 (下图第一张图) + 局部着色(下图第二张图)
输出:全局着色效果(下图第三张图)
算法工作在YUV空间,简单来讲,YUV适用于电视信号传输,Y表示亮度,UV表示色度。YUV与RGB颜色空间的相互转化参见:https://www.jianshu.com/p/cf583040c930。论文核心思想:亮度近似的像素应当具有相近的颜色。
两个核心能量公式如下所示:
J ( U ) = ∑ r ( U ( r ) − ∑ s ∈ N ( r ) w r s U ( s ) ) 2 (1) J(U) = sumlimits_r{(U(r) - sumlimits_{sin N(r)}{w_{rs}U(s)})^2} tag1 J(U)=r∑(U(r)−s∈N(r)∑wrsU(s))2(1)
J ( V ) = ∑ r ( V ( r ) − ∑ s ∈ N ( r ) w r s V ( s ) ) 2 (2) J(V) = sumlimits_r{(V(r) - sumlimits_{sin N(r)}{w_{rs}V(s)})^2} tag2 J(V)=r∑(V(r)−s∈N(r)∑wrsV(s))2(2)
这里, s s s是 r r r的邻居,一般限定在一个3*3的邻域内, w r s w_{rs} wrs是像素 r r r 和 s s s 根据 Y通道计算的相似度, 并且有 ∑ s ∈ N ( r ) w r s = 1.0 sum_{sin N(r)}{w_{rs}} = 1.0 ∑s∈N(r)wrs=1.0, w r s w_{rs} wrs计算公式如下:
w r s = e x p ( − ( Y ( r ) − Y ( s ) ) 2 / 2 σ r 2 ) (3) w_{rs} = exp(-(Y(r)-Y(s))^2 / 2sigma_r^2)tag3 wrs=exp(−(Y(r)−Y(s))2/2σr2)(3)
以上述公式(1)为例,其实等效于求解一个大型线性方程数组 A x = b Ax= b Ax=b,(2)的解法是一样的,下面对这个过程进行推导。
公式(1)其实是一些平方项的和,我们令:
{
K
(
1
)
=
U
(
1
)
−
∑
s
∈
N
(
1
)
w
r
s
U
(
s
)
K
(
2
)
=
U
(
2
)
−
∑
s
∈
N
(
2
)
w
r
s
U
(
s
)
.
.
.
K
(
n
)
=
U
(
n
)
−
∑
s
∈
N
(
n
)
w
r
s
U
(
s
)
(4)
left{ begin{aligned} K(1) =U(1) - sumlimits_{sin N(1)}{w_{rs}U(s)}\ K(2) =U(2) - sumlimits_{sin N(2)}{w_{rs}U(s)}\ ...\ K(n) =U(n) - sumlimits_{sin N(n)}{w_{rs}U(s)}\ end{aligned} right.tag4
⎩⎪⎪⎪⎪⎪⎪⎪⎪⎪⎪⎨⎪⎪⎪⎪⎪⎪⎪⎪⎪⎪⎧K(1)=U(1)−s∈N(1)∑wrsU(s)K(2)=U(2)−s∈N(2)∑wrsU(s)...K(n)=U(n)−s∈N(n)∑wrsU(s)(4)
那么,
K
=
[
K
(
1
)
,
k
(
2
)
,
.
.
.
,
K
(
n
)
]
T
K = [K(1),k(2),...,K(n)]^T
K=[K(1),k(2),...,K(n)]T 可以写成如下的线性方程组的形式 (如果
j
∉
N
(
i
)
,
w
i
j
=
0
j notin N(i), w_{ij} = 0
j∈/N(i),wij=0):
K
=
[
1
−
w
12
.
.
.
−
w
1
n
−
w
21
1
.
.
.
−
w
2
n
.
.
.
.
.
.
.
.
−
w
n
1
−
w
n
2
.
.
.
1
]
[
U
(
1
)
U
(
2
)
.
.
.
.
U
(
n
)
]
(5)
K = begin{bmatrix} 1 & -w_{12}&... & -w_{1n}\ -w_{21} & 1&... & -w_{2n}\ . & .& . & .\ . & .& . & .\ -w_{n1} & -w_{n2}&... & 1 end{bmatrix} begin{bmatrix} U(1)\ U(2)\ ..\ ..\ U(n) end{bmatrix} tag5
K=⎣⎢⎢⎢⎢⎡1−w21..−wn1−w121..−wn2...........−w1n−w2n..1⎦⎥⎥⎥⎥⎤⎣⎢⎢⎢⎢⎡U(1)U(2)....U(n)⎦⎥⎥⎥⎥⎤(5)
公式(1)实际对应
K
K
K中每一项的平方和,也就是:
J
(
U
)
=
∑
i
=
1
n
K
(
i
)
2
=
K
T
K
(6)
J(U) = sum^n_{i=1}K(i)^2 = K^TK tag6
J(U)=i=1∑nK(i)2=KTK(6)
令(5)中包含权重的稀疏矩阵为
L
L
L, 那么上式(6)可以进一步改写为:
J
(
U
)
=
K
T
K
=
(
L
U
)
T
(
L
U
)
=
U
T
L
T
L
U
(7)
J(U) = K^TK = (LU)^T(LU) = U^TL^TLUtag7
J(U)=KTK=(LU)T(LU)=UTLTLU(7)
其中,
U
=
[
U
(
1
)
,
U
(
2
)
,
.
.
.
U
(
n
)
]
T
U = [U(1),U(2),...U(n)]^T
U=[U(1),U(2),...U(n)]T是待求的未知量, 接下来对上式求导:
∂
J
(
U
)
∂
U
=
2
L
T
L
U
(8)
frac{ partial J(U) }{ partial U } = 2L^TLUtag8
∂U∂J(U)=2LTLU(8)
令导数等于0,得到关于
U
U
U的齐次线性方程组:
L
T
L
U
=
0
(9)
L^TLU = 0tag9
LTLU=0(9)
可以直接计算上述方程组, 但需要计算大型矩阵的乘积
L
T
L
L^TL
LTL较为不便,因此一般不这样求,而是改为计算:
L
U
=
0
(10)
LU = 0tag{10}
LU=0(10)
那么,一个问题是(9)跟(10)是否等价呢?也就是两个方程是否同解呢?看上去等式(10)成立,等式(9)必然成立,那么(9)能否推出(10)呢? 答案是肯定的。
我们对一般的情况进行推导,即证明 (i) A T A X = 0 A^TAX = 0 ATAX=0 与 (ii) A X = 0 AX = 0 AX=0 同解。因为(ii) → to → (i)是显然的,所以只推 (i) → to → (ii).
A T A X = 0 → X T A T A X = 0 → ( A X ) T ( A X ) = 0 A^TAX = 0 to X^TA^TAX = 0 to (AX)^T(AX) = 0 ATAX=0→XTATAX=0→(AX)T(AX)=0令 Y = A X = [ y 1 , y 2 , . . . , y n ] T Y = AX = [y_1, y_2,..., y_n]^T Y=AX=[y1,y2,...,yn]T, 那么 ( A X ) T ( A X ) = y 1 2 + y 2 2 + . . . + y n 2 = 0 → y i = 0 → A X = 0 (AX)^T(AX) = y^2_1 + y^2_2 +...+y^2_n = 0 to y_i = 0 to AX =0 (AX)T(AX)=y12+y22+...+yn2=0→yi=0→AX=0, 所以(i)(ii)同解。
所以最终只需要计算(10)所示的线性方程组即可。
需要说明的是,线性方程组 L U = 0 LU = 0 LU=0 中的 L L L 是Laplacian矩阵,不满秩,有无穷解。 需要用户涂鸦给定一些颜色才能求解,实际上该欠约束的线性方程组 (10) 添加约束。
构建线性系统的核心代码为:
//Y:Y通道(灰度图本身的灰度值), scribbles: 用户着色的图,mask:着色区域的mask
//A:系数矩阵,bu,bv关于U/V方程组的右侧列矩阵
void setupProblem(const cv::Mat& Y, const cv::Mat& scribbles, const cv::Mat& mask,
Eigen::SparseMatrix<double, Eigen::RowMajor>& A, Eigen::VectorXd& bu,
Eigen::VectorXd& bv, double gamma)
{
typedef Eigen::Triplet<double> TD;
auto nrows = Y.rows;
auto ncols = Y.cols;
auto nPixels = nrows * ncols;
A.resize(nPixels, nPixels);
std::vector<TD> coefficients;
coefficients.reserve(nPixels * 3);
bu.resize(nPixels);
bv.resize(nPixels);
bu.setZero();
bv.setZero();
cv::Mat yuvScribbles;
cv::cvtColor(scribbles, yuvScribbles, cv::COLOR_BGR2YUV);
yuvScribbles.convertTo(yuvScribbles, CV_64FC3);
std::vector<cv::Mat> channels;
cv::split(yuvScribbles, channels);
cv::Mat& U = channels[1];
cv::Mat& V = channels[2];
// TODO: See if we can do this more efficiently using matrix reshape
std::vector<double> y, u, v;
std::vector<bool> hasColor;
to1D(Y, y);
to1D(U, u);
to1D(V, v);
to1D(mask, hasColor);
const int numNeighbors = 8;
std::vector<double> weights;
weights.reserve(numNeighbors);
std::vector<unsigned long> neighbors;
neighbors.reserve(numNeighbors);
for (auto i = 0; i < nrows; ++i) {
for (auto j = 0; j < ncols; ++j) {
unsigned long r = i * ncols + j;
getNeighbours(i, j, nrows, ncols, neighbors);
getWeights(y, r, neighbors, weights, gamma);
coefficients.push_back(TD(r, r, 1));
for (auto k = 0u; k < neighbors.size(); ++k) {
auto s = neighbors[k];
auto w = weights[k];
if (hasColor[s]) {
// Move value to RHS of Ax = b
bu(r) += w * u[s];
bv(r) += w * v[s];
} else {
coefficients.push_back(TD(r, s, -w));
}
}
}
}
A.setFromTriplets(coefficients.begin(), coefficients.end());
}
下面给一个直观的例子:我们给出一个2行3列的图像, 现在灰度图上进行了局部着色,如(2)所示,可以抽出着色部分的U通道,接下来我们的任务是求解其他部分的U值,如(3)所示,剩余的
x
2
,
x
3
,
,
x
4
,
x
6
x_2,x_3,,x_4,x_6
x2,x3,,x4,x6 是待求解的未知数。V值求解方法一样,灰度图的灰度值本身就是Y,最后我们把YUV合起来就得到了最终的彩色图。
对于
x
1
x_1
x1:因为这里已经被着色,那么必然有:
x
1
=
u
1
x_1 = u_1
x1=u1
对于
x
2
x_2
x2:有5个邻居,邻域U的加权平均等于
x
2
x_2
x2本身的U值, 因此
x
2
−
w
21
u
1
−
w
23
x
3
−
w
24
x
4
−
w
25
u
5
−
w
26
x
6
=
0
x_2-w_{21}u_1-w_{23}x_3 -w_{24}x_4 - w_{25}u_5 -w_{26}x_6= 0
x2−w21u1−w23x3−w24x4−w25u5−w26x6=0
对于
x
3
x_3
x3:有3个邻居,
x
3
−
w
32
x
2
−
w
35
u
5
−
w
36
x
6
=
0
x_3-w_{32}x_2-w_{35}u_5 -w_{36}x_6 = 0
x3−w32x2−w35u5−w36x6=0
对于
x
4
x_4
x4:有3个邻居, 因此有:
x
4
−
w
41
u
1
−
w
42
x
2
−
w
45
u
5
=
0
x_4-w_{41}u_1-w_{42}x_2 -w_{45}u_5= 0
x4−w41u1−w42x2−w45u5=0
对于
x
5
x_5
x5:因为这里已经被着色,那么必然有:
x
5
=
u
5
x_5 = u_5
x5=u5
对于
x
6
x_6
x6:有3个邻居, 因此有:
x
6
−
w
62
x
2
−
w
63
x
3
−
w
65
u
5
=
0
x_6-w_{62}x_2-w_{63}x_3 -w_{65}u_5= 0
x6−w62x2−w63x3−w65u5=0
那么,上式可以写成如下的线性系统:(核心就是将上面各式的已知量全部移到右侧,未知量全在左侧)
( 1 0 0 0 0 0 0 1 − w 23 − w 24 0 − w 26 0 − w 32 1 0 0 − w 36 0 − w 42 0 1 0 0 0 0 0 0 1 0 0 − w 62 − w 63 0 0 1 ) ( x 1 x 2 x 3 x 4 x 5 x 6 ) = ( u 1 w 21 u 1 + w 25 u 5 w 35 u 5 w 41 u 1 + w 45 u 5 u 5 w 65 u 5 ) begin{pmatrix} 1 &0 &0 &0 & 0 & 0 \ 0 &1 &-w_{23} &-w_{24} & 0 & -w_{26}\ 0 & -w_{32} & 1&0 &0 &-w_{36} \ 0 & -w_{42} &0 & 1& 0 & 0\ 0 & 0& 0& 0 & 1&0 \ 0 & -w_{62}& -w_{63}& 0& 0& 1 end{pmatrix} begin{pmatrix} x_1 \ x_2 \ x_3 \ x_4 \ x_5 \ x_6 end{pmatrix}= begin{pmatrix} u_1 \ w_{21}u_1+w_{25}u_5 \ w_{35}u_5 \ w_{41}u_1+w_{45}u_5 \ u_5 \ w_{65}u_5 end{pmatrix} ⎝⎜⎜⎜⎜⎜⎜⎛10000001−w32−w420−w620−w23100−w630−w2401000000100−w26−w36001⎠⎟⎟⎟⎟⎟⎟⎞⎝⎜⎜⎜⎜⎜⎜⎛x1x2x3x4x5x6⎠⎟⎟⎟⎟⎟⎟⎞=⎝⎜⎜⎜⎜⎜⎜⎛u1w21u1+w25u5w35u5w41u1+w45u5u5w65u5⎠⎟⎟⎟⎟⎟⎟⎞
最后
以上就是无聊百褶裙为你收集整理的经典论文回顾: Colorization using Optimization的全部内容,希望文章能够帮你解决经典论文回顾: Colorization using Optimization所遇到的程序开发问题。
如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。
发表评论 取消回复