MATLAB vs C ++ vs OpenCV - imresize

I have the following MATLAB code that I want to pass in C ++

Suppose Gr is a 2d matrix and 1/newscale == 0.5

 Gr = imresize(Gr, 1 / newScale); 

in the MATLAB documentation :

B = imresize (A, scale) returns image B, which is the scale size of A. Input image A can be grayscale, RGB, or binary. If the scale is from 0 to 1.0, B is less than A. If the scale is more than 1.0, B is greater than A.

So this means that I get a two-dimensional matrix == matrix_width / 2 and matrix_height / 2
How to calculate the values? The default value according to the documents comes from cubic interpolation for the nearest 4X4.

I cannot find sample code for C ++ that does the same. Could you provide a link to such a code?

I also found this function OpenCV, resize .

Does it do the same as MATLAB?

+4
source share
2 answers

Yes, you just need to know that MATLAB imresize has anti-aliasing enabled by default :

 imresize(A,scale,'bilinear') 

against. what would you get with cv::resize() , which has no anti-aliasing:

 imresize(A,scale,'bilinear','AntiAliasing',false) 

And as Amro noted, the default value in MATLAB is bicubic , so be sure to specify.

Bilinear

No code modifications are required to obtain consistent results with bilinear interpolation.

An example of an OpenCV snippet:

 cv::Mat src(4, 4, CV_32F); for (int i = 0; i < 16; ++i) src.at<float>(i) = i; std::cout << src << std::endl; cv::Mat dst; cv::resize(src, dst, Size(0, 0), 0.5, 0.5, INTER_LINEAR); std::cout << dst << std::endl; 

Output (OpenCV)

 [0, 1, 2, 3; 4, 5, 6, 7; 8, 9, 10, 11; 12, 13, 14, 15] [2.5, 4.5; 10.5, 12.5] 

MATLAB

 >> M = reshape(0:15,4,4).'; >> imresize(M,0.5,'bilinear','AntiAliasing',true) ans = 3.125 4.875 10.125 11.875 >> imresize(M,0.5,'bilinear','AntiAliasing',false) ans = 2.5 4.5 10.5 12.5 

Note that the results are the same as anti-aliasing disabled.

Bicubic difference

However, between 'bicubic' and INTER_CUBIC results are different from the weighing scheme! See here for more details . The problem is the interpolateCubic() function, which calculates cubic interpolation coefficients using the constant a = -0.75 , rather than a = -0.5 , as in MATLAB. However, if you edit imgwarp.cpp and change the code:

 static inline void interpolateCubic( float x, float* coeffs ) { const float A = -0.75f; ... 

in

 static inline void interpolateCubic( float x, float* coeffs ) { const float A = -0.50f; ... 

and rebuild OpenCV (hint: disable CUDA and gpu module for short compilation time), then you will get the same results:

MATLAB

 >> imresize(M,0.5,'bicubic','AntiAliasing',false) ans = 2.1875 4.3125 10.6875 12.8125 

Opencv

 [0, 1, 2, 3; 4, 5, 6, 7; 8, 9, 10, 11; 12, 13, 14, 15] [2.1875, 4.3125; 10.6875, 12.8125] 

Read more about cubic HERE .

+9
source

In OpenCV, the call will look like this:

 cv::Mat dst; cv::resize(src, dst, Size(0,0), 0.5, 0.5, INTER_CUBIC); 

You may then need anti-aliasing / blurring to emulate anti-aliasing, which MATLAB also performs by default (see @chappjc )

+3
source

Source: https://habr.com/ru/post/1206504/


All Articles