创建对象后丢失的缓冲区内容
float type Buffer contents lost after creating object C++
我有一个类,它包含一个浮点类型缓冲区,指向一个RGB值数组。缓冲区被创建并正确存储,但是当我通过一个函数返回该类的实例到main()时,缓冲区的内存是不可读的。下面是初始类:
namespace imaging
{
typedef float component_t;
class Image
{
protected:
component_t * buffer;
unsigned int width, height;
public:
Image(unsigned int width, unsigned int height, const component_t * data_ptr) {
this->width = width;
this->height = height;
this->setData(data_ptr);
this->buffer = const_cast<component_t *>(data_ptr);
}
component_t getRedValPixel(unsigned int x, unsigned int y) const {
int pos = x * this->width * 3;
component_t red;
red = this->buffer[pos];
return r;
}
}
}
要创建该类的实例,我使用readImage(char* filepath)方法,该方法在加载数据后具有返回语句:
return &Image(width, height, buffer);
下面是main()函数中的代码:Image* image = readIamge(filepath);
int width = image->getWidth(); //retrieves it correctly
int height = image->getHeight(); //retrieves it correctly
for (int i = 0; i < height; i++) {
for (int j = 0; j < width; j++) {
cout << image->getRedValPixel(i,j);
}
}
让我们仔细看看你的返回语句:
return &Image(width, height, buffer);
执行Image(...)
时,会创建一个临时对象。一旦它所在的表达式结束,这个临时对象将被销毁。然后你返回一个指向这个临时对象的指针,这个对象很快就会消失,给你留下一个指向不存在对象的指针。试图对该指针解引用将导致未定义行为。
从文件读取的数据可能仍在内存中的某个地方,但从返回的指针中不可用。
我建议你通过值返回对象,并学习像移动语义, 移动构造函数和3,5和0的规则。我还建议您不仅复制指向对象实际数据的指针,还要复制实际数据本身(深度复制)。
return &将返回堆栈中本地创建的对象的地址,该对象将在失去作用域(即返回语句)后立即销毁。
解决方案是在堆中分配Image对象。例如
main()
{
....
Image* image = NULL;
readImage(filepath, image );
int width = image->getWidth(); //retrieves it correctly
int height = image->getHeight(); //retrieves it correctly
for (int i = 0; i < height; i++) {
for (int j = 0; j < width; j++) {
cout << image->getRedValPixel(i,j);
}
}
delete image;
image = NULL
...
}
void readImage(char* filepath, Image* o_pBuffer )
{
.....
o_pBuffer = new Image(width, height, buffer);
return o_pBuffer;
}
或
main()
{
....
Image* image = NULL;
image = readImage(filepath );
int width = image->getWidth(); //retrieves it correctly
int height = image->getHeight(); //retrieves it correctly
for (int i = 0; i < height; i++) {
for (int j = 0; j < width; j++) {
cout << image->getRedValPixel(i,j);
}
}
delete image;
image = NULL
...
}
Image* readImage(char* filepath )
{
.....
Image* o_pBuffer = new Image(width, height, buffer);
return o_pBuffer;
}
相关文章:
- 使用基类指针创建对象时,缺少派生类析构函数
- 如何创建对象函数指针C++映射?
- C++创建对象数组
- 在 C++ 的 Switch Case 中创建对象后对对象调用方法
- 如何获取在 main() 函数中构造的类的创建对象?
- 基于文件中的条目创建对象
- 错误:创建对象后无法分配区域
- C++ 通过输入创建对象
- 堆还是堆栈用于创建对象?
- 使用 C++ 创建对象数组
- 使用unique_ptr创建对象
- C++递归地在类构造函数中创建对象
- 通过向构造函数其他对象引用页面来创建对象
- ReactiveX (rx) - 在对象上应用可观察对象,而不是在可观察对象中创建对象
- 如何在OSX上正确创建C++对象文件(.o)
- 编译器是否会创建vtable,而不考虑在c++中创建对象
- 创建对象并防止被破坏
- 创建对象后丢失的缓冲区内容
- 从内存缓冲区创建fstream对象
- opencv C++从android NV21图像数据缓冲区创建Mat对象