Ask Your Question
0

strange warpAffine precision issue

asked 2015-05-27 12:37:54 -0600

hulo gravatar image

I am trying to use OpenCVs warpAffine to transform an image. I use the bilinear interpolation option (set by default). When using a very small transformation (e.g., translation of 0.01 pixel), the transformed image is exactly identical to the original. This is problematic since I need a big precision as further computations are performed on the transformed image.

Example:

Mat img_test = (Mat_<double>(5,5) << 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0);
Mat tfm; Mat transf_img_test;
tfm = Mat::eye(2,3,CV_64F);
tfm.at<double>(0,2) = 0.01;
warpAffine( img_test, transf_img_test, tfm, img_test.size(), INTER_LINEAR);
cout << "Original = " << img_test << endl;
cout << "Transformed = " << transf_img_test << endl;

The two images are exactly identical:

Original = [0, 0, 0, 0, 0;
        0, 0, 1, 0, 0;
        0, 0, 1, 0, 0;
        0, 0, 1, 0, 0;
        0, 0, 0, 0, 0]
Transformed = [0, 0, 0, 0, 0;
           0, 0, 1, 0, 0;
           0, 0, 1, 0, 0;
           0, 0, 1, 0, 0;
           0, 0, 0, 0, 0]

Note that when I set

tfm.at<double>(0,2) = 0.5

instead, warpAffine correctly transforms (and interpolates) the image.

edit retag flag offensive close merge delete

1 answer

Sort by ยป oldest newest most voted
0

answered 2015-05-27 19:11:51 -0600

Eduardo gravatar image

I tried different values and I compared with my own implementation (I use a classical bilinear interpolation). The results are the following (if my code is right, with OpenCV 2.4.11):

Original =
 [8, 0, 0, 2, 0;
  0, 0, 1, 0, 0;
  0, 0, 1, 0, 0;
  0, 0, 1, 0, 3;
  0, 5, 0, 0, 0]
tfm =
 [1, 0, 0.4;
  0, 1, 0]
Transformed =
 [4.75, 3.25, 0, 1.1875, 0.8125;
  0, 0, 0.59375, 0.40625, 0;
  0, 0, 0.59375, 0.40625, 0;
  0, 0, 0.59375, 0.40625, 1.78125;
  0, 2.96875, 2.03125, 0, 0]
Custom Transformed =
 [4.8, 3.2, 0, 1.2, 0.7999999999999998;
  0, 0, 0.6000000000000001, 0.3999999999999999, 0;
  0, 0, 0.6000000000000001, 0.3999999999999999, 0;
  0, 0, 0.6000000000000001, 0.3999999999999999, 1.8;
  1.2, 3, 2, 0, 0]

Original =
 [8, 0, 0, 2, 0;
  0, 0, 1, 0, 0;
  0, 0, 1, 0, 0;
  0, 0, 1, 0, 3;
  0, 5, 0, 0, 0]
tfm =
 [1, 0, 0.3;
  0, 1, 0]
Transformed =
 [5.5, 2.5, 0, 1.375, 0.625;
  0, 0, 0.6875, 0.3125, 0;
  0, 0, 0.6875, 0.3125, 0;
  0, 0, 0.6875, 0.3125, 2.0625;
  0, 3.4375, 1.5625, 0, 0]
Custom Transformed =
 [5.6, 2.4, 0, 1.4, 0.5999999999999996;
  0, 0, 0.7, 0.2999999999999998, 0;
  0, 0, 0.7, 0.2999999999999998, 0;
  0, 0, 0.7, 0.2999999999999998, 2.100000000000001;
  0.9000000000000001, 3.5, 1.5, 0, 0]

Original =
 [8, 0, 0, 2, 0;
  0, 0, 1, 0, 0;
  0, 0, 1, 0, 0;
  0, 0, 1, 0, 3;
  0, 5, 0, 0, 0]
tfm =
 [1, 0, 0.35;
  0, 1, 0]
Transformed =
 [5.25, 2.75, 0, 1.3125, 0.6875;
  0, 0, 0.65625, 0.34375, 0;
  0, 0, 0.65625, 0.34375, 0;
  0, 0, 0.65625, 0.34375, 1.96875;
  0, 3.28125, 1.71875, 0, 0]
Custom Transformed =
 [5.2, 2.8, 0, 1.3, 0.7000000000000002;
  0, 0, 0.6499999999999999, 0.3500000000000001, 0;
  0, 0, 0.6499999999999999, 0.3500000000000001, 0;
  0, 0, 0.6499999999999999, 0.3500000000000001, 1.95;
  1.05, 3.25, 1.75, 0, 0]

Original =
 [8, 0, 0, 2, 0;
  0, 0, 1, 0, 0;
  0, 0, 1, 0, 0;
  0, 0, 1, 0, 3;
  0, 5, 0, 0, 0]
tfm =
 [1, 0, 0.355;
  0, 1, 0]
Transformed =
 [5.25, 2.75, 0, 1.3125, 0.6875;
  0, 0, 0.65625, 0.34375, 0;
  0, 0, 0.65625, 0.34375, 0;
  0, 0, 0.65625, 0.34375, 1.96875;
  0, 3.28125, 1.71875, 0, 0]
Custom Transformed =
 [5.16, 2.84, 0, 1.29, 0.71;
  0, 0, 0.645, 0.355, 0;
  0, 0, 0.645, 0.355, 0;
  0, 0, 0.645, 0.355, 1.935;
  1.065, 3.225, 1.775, 0, 0]

Original =
 [8, 0, 0, 2, 0;
  0, 0, 1, 0, 0;
  0, 0, 1 ...
(more)
edit flag offensive delete link more

Comments

Thanks Eduardo. I just implemented my own warpAffine function, and it achieves the desired accuracy, even though running time is much worse than OpenCV's warpAffine. This goes in the direction of your explanation, and it seems that OpenCV's warpAffine sacrifices precision for performance...

hulo gravatar imagehulo ( 2015-05-28 02:37:15 -0600 )edit

I have same problem with warpAffine too, MATLAB imwarp vs C++ warpAffine. can you share your implementation for warpAffine. thank you

mr.ao gravatar imagemr.ao ( 2017-12-26 03:53:19 -0600 )edit

Question Tools

1 follower

Stats

Asked: 2015-05-27 12:37:54 -0600

Seen: 633 times

Last updated: May 27 '15