Memory management is essential for an image class. In opencv, the image class is cv::Mat
, which has a delicate memory management scheme. Suppose I already have my own image class SelfImage
:
class SelfImage
{
public:
int width_;
int height_;
unsigned char *pPixel_;
};
At the beginning, I will put all the image pixel contents to this class:
SelfImage myImage;
myImage.width_ = 300;
myImage.height_ = 200;
myImage.pPixel_ = new [300*200];
for(int i=0; i<300*200; i++)
myImage.pPixel_[i] = i%200;
Then my question is how I can transform this class to cv::Mat
in a very efficient way, one solution I have is:
cv::Mat mat;
mat.create( myImage.height_, myImage.width_, CV_8UC1);
mat.data = myImage.pPixel_;
I do not know whether this is a good solution. If cv::Mat::create
function will also allocate memory,then the above codes have the danger of memory leak. Any ideas?
EDIT
I have to make it clear that it would be nice if I can use cv::Mat::create
method but share the memory with SelfImage
class.The reason is that a function is defined to perfom the image class transform job void TransImageType(const SelfImage &geo_img, cv::Mat &mat)
;
cv::Mat
has a constructor where you can specify user data:
Mat::Mat(int rows, int cols, int type, void* data, size_t step=AUTO_STEP)
The documentation says the following about the data
argument:
Pointer to the user data. Matrix constructors that take data and step parameters do not allocate matrix data. Instead, they just initialize the matrix header that points to the specified data, which means that no data is copied. This operation is very efficient and can be used to process external data using OpenCV functions. The external data is not automatically deallocated, so you should take care of it.
It depends on if you want to copy the data.
From your suggestion, it seems you want to share the data. In that case, this is the best solution:
cv::Mat mat(myImage.height_, myImage.width_, CV_8U, myImage.pPixel_);
The mat
will not release the memory when it is deallocated, you will have to do it.
If you want to copy data, create a normal cv::Mat
and do std::copy
later (or memcpy
as @KeillRandor suggested).
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With