使用c++如何实现PatchMatch图像修复算法

  介绍

今天小编给大家分享的是使用c++如何实现PatchMatch图像修复算法,相信很多人都不太了解,为了让大家更加了解,所以给大家总结了以下内容,一起往下看吧。一定会有所收获的哦。

PatchMatch算法出自巴恩斯的论文

PatchMatch:随机通信算法结构图像编辑

PatchMatch算法就是一个找近似最近邻(最近的neigbhor)近似的方法,要比其安他算法快10倍+上。

将下面的图理解了,就基本理解了整个算法。

使用c++如何实现PatchMatch图像修复算法

看上图时,我们以蓝色为主颜色。代表原图像,矩形框代表待修复的片块,要修复patch_A块就需要在B(也是原图)中搜索一个最合适的块patch_B,而从patch_A到patch_B的偏移量,就是上图箭头,也就是抵消。

蓝色为主片块,红色是蓝色向左移一个像素,绿色是蓝色向上移一个像素。

上图(一):随机初始化(B):传播,复制;:随机扰动搜索

PatchMatch的核心思想是利用图像的连续性(一致性),一个图像一个的patch_A(蓝)色附近的片块(红色绿色)的最近邻(B中的红色绿色框)最有可能出现在patch_A的最近邻(B中的蓝色框)附近,利用这种图像的连续性大量减少搜索的范围,通过迭代的方式保证大多数点能尽快收敛。

PatchMatch算法是对所有待修复像素迭代修复的,而不是像Criminisi或FMM算法对待修复区域像素优先级排序后进行渐进修复的。

来看算法步骤:

使用c++如何实现PatchMatch图像修复算法

首先是建立图像的下采样金字塔模型,代码中设定为五层,建立模型后

对的待修复区域每个补丁块随机在B已知区域中匹配一个块,即初始化偏置地图上(图一个步骤)。

/* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * *   函数声明:初始化偏置图像   参数:没有   注释:没有   测试:没有   * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */void  PatchMatch:: InitOff (Mat 面具,Mat ,)   {//为方便起见,将所有的都附上,要求不能赋值到非搜索区域//初始化格式   Off =,垫(Mask.size (),, CV_32FC2,,标量::(0));//2维无符号32位精度浮点数      for  (int 小姐:=,0;,小姐:& lt;, Mask.rows;,我+ +)   {   时间=for  (int  j  0;, j  & lt;, Mask.cols;, j + +)   {//不考虑搜索区域,没有破损,他们的最佳偏移向量当然是0,自己   if  (Mask.at (i, j),==,搜索)   {   Off.at (i, j) [0],=, 0;,,//& lt; Vec2f>,向量,2维,浮点数   Off.at (i, j) [1],=, 0;   }//其他处理洞,采用随机偏置,,   {//先初始化2个偏置数r_col, r_row   int  r_col =, rand (), %, Mask.cols;,//rand()产生随机数,主要是产生一个偏置的初始值   int  r_row =, rand (), %, Mask.rows;   +=r_col  r_col  j  & lt;, Mask.cols  ?, r_col :, r_col 作用;Mask.cols;//边界检测   +=r_row  r_row 小姐:& lt;, Mask.rows  ?, r_row :, r_row 作用;Mask.rows;//为什么要有这个循环?因为一次的随机赋值,很可能会出现偏置后的块跑到破损区域,或者是超出限定搜索框的边界   while  (   ! (Mask.at(时间+ r_row 我,r_col  +, j),==,搜索//这里加上我,j,是因为他是一个投影到B中的搜索偏置   ,,,abs (r_row), & lt;, searchrowratio * Mask.rows))//searchrowratio=0.5,搜索的时候,确保r_row偏置不会太远,一定是在原图像的大小里   {   r_col =, rand (), %, Mask.cols;   r_row =, rand (), %, Mask.rows;//边界检测   +=r_col  r_col  j  & lt;, Mask.cols  ?, r_col :, r_col 作用;Mask.cols;   +=r_row  r_row 小姐:& lt;, Mask.rows  ?, r_row :, r_row 作用;Mask.rows;   }//赋偏置值   Off.at (i, j) [0],=, r_row;   Off.at (i, j) [1],=, r_col;   }   }   }   }

之后从低分辨率开始,对于每一层金字塔模型进行迭代:

每一次迭代都会遍历原图一个待修复区域所有像素。当遍历到当前像素时,执行下面的步骤来进行修复:

步骤一:传播(图中b步骤)

传播会计算原图一个当前像素块patch_A(蓝)色对应的b中的patch_B_1, patch_A上方(绿色)(奇数次迭代为下方)对应的b中的patch_B_2, patch_A左侧(红色)(奇数次迭代为右侧)对应的b中的patch_B_3这三个补丁块中与patch_A相似度最高的补丁块。

使用c++如何实现PatchMatch图像修复算法