I'm trying to fit a 2d gauss function to an image (in cv::Mat format), and I'm using the NLopt library.
I put my object function like this:
for(i for each row)
for(j for each col)
{
//compute the gauss function value
double valuenow=x[0]*exp(-( x[3]*(j-x[1])*(j-x[1]) + 2*x[4]*(j-x[1])*(i-x[2]) + x[5]*(i-x[2])*(i-x[2]) ));
//add square residual to result
result+=(valuenow-fitdata.at<double>(i,j))*(valuenow-fitdata.at<double>(i,j));
}
return result;
My matrix is about 1000*1000 size, I'm using LN_COBYLA algorithm. When I ran this, it turned out to be extremely slow. I think there must be something wrong with the way I specify my object function, because I used to do the same thing in Matlab with lsqnonlinear, which returned in a second.
Can someone help me please? Thanks in advance.
The
at<>()
function is slow. If speed is of essence, it's not a good idea to use it inside loops. Take a pointer outside the loop and then just use that pointer inside the loop.A related question: OpenCV Mat array access, which way is the fastest for and why?