为什么在返回对象时堆损坏?
Why heap corruption when returning an object Mat?
我不明白为什么我得到一个损坏的堆错误与这个程序(我使用OpenCV类Mat
):
class A {
private:
Mat image;
static UINT ThreadProc( LPVOID pParam ) {
A* pThis= (ClientNetwork*)pParam;
UINT nRet= pThis->DoThreadProc(); // get out of 'static mode'
return( nRet );
}
UINT ClientNetwork::DoThreadProc() {
vector<uchar> vect;
while(1) {
/**** initialize vect and get the image data to decode ****/
decode(vect);
}
}
public:
void decode(const vector<uchar>& vectorData){image=imdecode(vectorData, CV_LOAD_IMAGE_COLOR);}
Mat get_image(){return image;}
void start() {m_pcThread= AfxBeginThread(ThreadProc, this );}
}
int main() {
A* a = new A();
a->start();
while(1) {
Mat image = a->get_image();
}
delete a;
return 0;
}
似乎错误来自Mat image = a->get_image();
,因为如果我返回一个引用而不是对象的副本,我不再有错误了:
Mat* get_image(){return ℑ}
和
Mat* image = a->get_image();
我读到在c++中返回对象的副本比返回引用更优雅。所以我想知道出了什么问题。
编辑:Visual studio中断在a->decode(vect)
,但它只发生当我返回一个对象,而不是一个引用。
编辑2:我编辑了代码以反映完整的程序。我认为问题来自于共享对象a
,它同时被复制和修改。我将看看使用互斥锁是否还会出现这个问题。
使用a
而不初始化。
int main() {
A* a;
vector<uchar> vect;
while(1) {
// get the vector of data
a->decode(vect);
欢迎来到未定义行为,人口:你。
初始化a
以获得更好的结果
那么这就是线程同步问题,正如你自己所建议的。图像在无限while循环中不断被填充。在它中间的某个地方,你试图复制它。灾难的配方。在每次迭代中,您需要在DoThreadProc的循环中使用写锁。然后你需要在get_image中取一个读锁。您需要使用一个读写锁库,它不会使读取器饿死。
也可以使用互斥锁/临界区。写循环和读(get_image)都在执行工作时独占访问image。
我很好奇-你的线程过程是解码的东西在一个无限循环。你在里面想干什么?在阅读时,你期望看到什么样的画面?在循环迭代的那个时间点有图像吗?
cv::Mat
的复制构造函数不创建图像的深度副本。它只是创建一个对原始Mat
的引用,并增加其引用计数。在类的以下函数中,return
语句调用复制构造函数,返回对原始image
的引用,这可能是堆损坏的原因:
Mat get_image(){ return image; }
您应该返回image
的深层副本,如下所示,以便原始image
不会被意外修改。
Mat get_image(){ return image.clone(); }
相关文章:
- 构造函数初始化和对象损坏
- 从本机代码返回到托管代码会损坏返回的对象
- 在向量中使用不带复制且没有 noexcept 移动构造函数的对象.实际损坏的内容以及我如何确认它
- 引用可能已损坏的静态对象
- 部分损坏的对象
- 对同一对象的多个shared_ptrs,一个已损坏
- C 用向量序列化对象会导致双重自由损坏
- 如何在不存在任何数据损坏风险的情况下序列化对象
- 对象, 在 Vector 中, 在'For Loop'初始化中损坏
- 我的 QNX/BB10 C++应用程序崩溃,一个简单的C++对象似乎已损坏
- 从映射中检索后,映射中的对象已损坏
- 删除对象(另一个..)时双重释放或损坏
- 多线程对象中的堆损坏
- 对象的c++内存副本出现损坏
- 对象周围的堆栈已损坏
- 在Visual Studio调试模式下运行时,c++对象引用已损坏
- 为什么在返回对象时堆损坏?
- 使用内存复制对象时出现双自由或损坏错误
- 从复制构造函数外部修改对象成员时导致向量内存损坏,但从复制构造函数内部修改时不会
- C++对象引用损坏