gpt4 book ai didi

c++ - opencv 的 Sysmalloc 错误

转载 作者:行者123 更新时间:2023-11-28 05:16:16 26 4
gpt4 key购买 nike

我在使用 opencv 时遇到 sysmalloc 错误。当我调试时,我发现错误发生在这里:

sm = cv::Mat::zeros(h,w,img.type());

其中h和w分别是img行和w列。我展示了它们,它们没问题。这是整个函数:

cv::Mat gsmooth(cv::Mat img,int sigma,int radius,std::string methode)
{
cv::Mat sm;
std::vector<double> hcol;
std::vector<double> hrow;
if(sigma == NULL)
{
sigma =1;
}
if(radius == NULL)
{
radius = ceil(2.5*sigma);
}
if(methode.c_str()==NULL)
{
methode ="none";
}

if(sigma == 0)
{
sm = img;
}
else
{

hcol= gKernel(2*radius+1,sigma);
hrow= gKernel(2*radius+1,sigma);
int h=img.rows;
int w=img.cols;
int c=img.channels();
switch (c)
{
case 1:
sm= cv::Mat::zeros(h,w,img.type());
break;
case 2:
sm= cv::Mat::zeros(h,w,CV_32SC2);
break;
default:
sm= cv::Mat::zeros(h,w,CV_32SC3);
}
if(!methode.compare(std::string("mirror")))
{
cv::Mat mattmp=mirror(img,radius,radius);
sm=conv2(mattmp,hcol,hrow);

int ma=img.rows;
int na=img.cols;
int nb=hcol.size();
int mb=hrow.size();
sm=sm.rowRange((mb-1)/2,(mb-1)/2+ma).colRange((nb-1)/2,(nb-1)/2+na);
}
else
{
cv::Mat sm_;
sm_=conv2(img,hcol,hrow);
int H=sm.rows;
int W=sm.cols;
int h=img.rows;
int w=img.cols;
int y=ceil(H/h);
int x=ceil(W/w);
sm=sm.rowRange(y,y+h).colRange(x,x+w);
}

}
hcol.clear();
hrow.clear();
return(sm);

}

该函数由另一个带有 cv::Mat img、两个 int 和“mirror”或“none”的 .cpp 调用。参数似乎是正确的:正确加载了 img 矩阵,而其他只是 int。

完整的错误是:*malloc.c:2372: sysmalloc: Assertion '(old_top== (((mbinptr) (((char *) &((av)->bins[((1) - 1)*2)) -__builtin_offsetof (struct malloc_chunk, fd)))) && old_size == 0) || ((unsigned long) (old_size) >= (unsigned long)((((__builtin_offsetof (struct malloc_chunk,fd_nextsize))+((2*(sizeof(size_t))) -1)) & ~((2*sizeof(size_t))) -1)))&& ((old_top)-> size & 0x1) && ((unsigned long) old_end & pagemask) ==0)' failed.*

我在 ubuntu 14.04.5 上使用 Qt 5.2、gcc 4.6 和 g++ 4.4,由于 braid lib 的兼容性问题,我不得不使用 opencv 2.4.13。

我确定我的错误是愚蠢的,也许我不能像这样声明一个零矩阵,但我不知道该怎么做,而且我没有找到任何与此问题相关的主题。

总的来说,我对使用 opencv 的 malloc 问题非常困惑。大多数时候,我使用函数在参数中获取 cv::Mat 并使用它返回函数内部声明的新矩阵,如下所示:

cv::Mat function somefunction(cv::Mat img, some arguments)
{
cv::Mat res;
//operations
return(res);
}

我这样调用函数:new_img=some_function(img, some_arguments);

我想知道这样做是否正确?

希望我已经足够具体了,如果您需要更多信息,请不要犹豫。

编辑:使用 Valgrind 我发现当我尝试使用 gKernel 时会出现问题.事实上gsmooth被调用两次,第一次一切正常,第二次调用时发生崩溃。 Valgrind 在函数的第一行指出了一个 SIGSEGV 错误:std::vector<double> kernel(size);

这是整个函数:

std::vector<double> gKernel(int size, float sigma)
{
std::vector<double>kernel(size);
double r,s =2.0* sigma * sigma;
double sum=0.0;
int radius=(size -1)/2;
int index=0;
for(int y=-radius; y<=radius;y++)
{
r=sqrt(y*y);
kernel[index]=(exp(-(r*r)/s))/(sqrt(2*M_PI*s));
sum+=kernel[index];
index++;
}
for(int i=0;i<size;i++)
{
kernel[i]/=sum;
}
return(kernel);
}

我不明白为什么声明一个 vector 可能会导致段错误?正如您在我的 gsmooth 函数中看到的那样,gKernel 的调用大小为 2*radius +1,sigma 在第一次调用中等于 60,在第二次调用中等于 50。

至少我知道我不应该用'='复制cv::Mat,而是用clonecopyTo以避免混淆像素指针。

最佳答案

可能你在某处损坏了内存,但不是在上面的代码中。 cv::Mat::zeros 的用法看起来不错。

使用Valgrind找出问题的原因。

更新

I solved my issues by replacing m.at=someint with m.at=someint in the previous lines of my code

之所以有效,是因为您的 Mat m 不是用 double 类型表示的。 m 的类型应为 CV_64F或类似于访问 double 元素。实际上你的 Mat m 类型是 CV_8U,它对应于你在修复中使用的 uchar

要更改 Mat m 的类型,您可以使用 convertTo方法。

关于c++ - opencv 的 Sysmalloc 错误,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/42577774/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com