You are on page 1of 7

# Fast 2D Separable Symmetric/AntiSymmmetric Convolution

Pi19404
February 17, 2014

Contents

Contents
2D Seperable Symmetric/Anti-Symmmetric Convolution 3

0.1

Introduction . . . . . . . . . . . . . . . . . . . . . . . . . 0.1.1 Separable Symmetric/Anti-Symmetric 0.1.2 Vertical Convolution . . . . . . . . . . . . . 0.1.3 Horizontal Convolution . . . . . . . . . . . 0.1.4 Code . . . . . . . . . . . . . . . . . . . . . . . . . .

. . . . . . . . . . Convolution . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .

3 3 4 6 7

2 | 7

## 2D Seperable Symmetric/Anti-Symmmetric Convolution

0.1 Introduction
In the article we will look at algorithm for Fast 2D Convolution.

## 0.1.1 Separable Symmetric/Anti-Symmetric Convolution

         

This article presents a convolution algorithm involving a separable symmetric/anti symmetric kernel. Such kernels are common in image processing like blurring,edge detection etc This optimization helps in speeding up many routines . Another requirement being addressed is we may have multiple kernels that need to be applied to the same image in application such as computing the basis representation of rectangular path of the image. since we are traversing the image,we can perform computation of all these kernels simultaneously instead of independent traversals. It is to be noted that this optimization is specific to symmetric/antisymmetric separable filters. We will be assuming that all the kernel are of the same size as well Since kernels are separable we will perform vertical convolution followed by horizontal convolution. One of the considerations is to minimize the row accesses . Another consideration is to perform a single pass over the entire source image

3 | 7

  

Let

## 2 + 1 be the kernel size.

The convolution filter is initialized by accepting all the row and column filter coefficients as well as the information if the filter is symmetric or not A class called SeperableSConvolution implemented this algorithm

class SeperableSConvolution { public: SeperableSConvolution(); vector<Mat> rowk;//vector of row filter vector<Mat> colk;//vector of column filters vector<bool> symmetric; //info if filter is symmetric or not int N;//number of channels in the output image //function to set the filter parameters void setKernel(Mat row,Mat col,bool symm); //function to clear the filter parameters void clearKernel(); //apply a set of separable symmetric/anti-symmetric filters on //the source image and return a multi channel destination image ////function to perform separable filtering void apply(Mat &src,Mat &dst); };

  

2N + 1

## ,we need to access same number of rows

This if we are applying the filter at row j,we need to access elements from rows from j k to j + k where k 2 0::N
k

dst(x; y )

X
=
N

i;k

g (k

+ N )I (x; y + k )

(1)

  

## The above needs to be processed for each

(x; y )

Since we need to reduce the number of row access,access rows from j N; j + N are performed for each j,compute the convolution for each x. Since with change in x no new rows are being accessed,hence we compute convolution for each element of the present row.

4 | 7

## 2D Seperable Symmetric/Anti-Symmmetric Convolution

  

Each of the rows need to be multiplied with suitable filter coefficients. since the filter is symmetric or anti symmetric the filter coefficients g is multiplied with elements of rows j k and j + k
k

## The resultant sum of accumulated,this is performed for all the rows.

for(int y=0;y<s.height;y++) { //pointer to the source and destination float *srow0 = (float*)(src.data + src.step*y),*srow1=0; float *drow = (float*)(dst.data + dst.step*y); //performing vertical convolution //using the row kernel //computing g*f(x,y) for( x = 0; x < s.width; x++ ) { for(int l=0;l<ch;l++) { row[x*ch+l] = srow0[x]*rowk[l].at<float>(n); } } //computing g[-n/2]*f(x,y-n/2) //performing vertical convolution accessing n rows about current row //accessing a 2 rows at a time,performing computation for(int k=1;k<=n;k++) { //accessing the vertical abouts about the current row srow0 = (float*)(src.data + src.step*std::max(y-k,0)); srow1 = (float*)(src.data + src.step*std::min(y+k,s.height-1)); for(int x=0;x<s.width;x++) { //applying different vertical kernels //accumulating the sum for(int l=0;l<ch;l++) { float p=srow0[x]+(1*(symmetric[l]?1:-1))*srow1[x]; row[x*ch+l]+=rowk[l].at<float>(k)*(p); }

5 | 7

## 0.1.3 Horizontal Convolution

  

Once vertical convolution is done we proceed to perform horizontal convolution Since in horizontal convolution there is only a single row access ,it is relatively simple process. The output image is a multi channel image,containing number of channels as desired number of input kernels being applied to the source image.

for(x=0;x<s.width;x++) { //apply horizontal kernels //g*f(x,y) for(int l=0;l<ch;l++) { res[l]=row[x*ch+l]*colk[l].at<float>(n); } //accumulating the sum for g[-N/2+k]f(x-n/2+k) for(int k=1;k<=n;k++) { for(int l=0;l<ch;l++) { float p=(row[(x+k)]+(1*symmetric[l]?1:-1) *row[(x-k)])*colk[l].at<float>(k); res[l]=res[l]+p; }

} //storing the result of convolution //output image contains number of channels as different input filte for(int l=0;l<ch;l++) { drow[x*ch+l]=res[l]; }

6 | 7

## 2D Seperable Symmetric/Anti-Symmmetric Convolution

0.1.4 Code

The class SeperableSConvolution defines a class for performing separable symmetric/ant-symmetric convolution/ Code is available in repository https://github.com/pi19404/OpenVision/ at Improper/convolution.hpp and ImgProc/convolution.cpp files.

7 | 7